موصل Zoom

اربط Zoom بـ Brevo من خلال Tajo لمزامنة المشاركين في الاجتماعات وحضور الندوات كجهات اتصال تلقائيًا، وتشغيل تسلسلات متابعة ما بعد الاجتماع، وتتبع مقاييس التفاعل لأتمتة التسويق الخاصة بك.

نظرة عامة

الخاصيةالقيمة
المنصةZoom
الفئةمؤتمرات الفيديو (مخصص)
تعقيد الإعدادمتوسط
تكامل رسميلا
البيانات المُزامَنةمشاركون، أحداث، ندوات، جهات اتصال
طريقة المصادقةOAuth 2.0 / Server-to-Server OAuth

الميزات

  • مزامنة المشاركين - إنشاء جهات اتصال Brevo تلقائيًا من المشاركين في الاجتماعات
  • التقاط حضور الندوات - مزامنة المسجلين والحاضرين في الندوات
  • محفزات أحداث الاجتماع - تشغيل الأتمتة عند بدء الاجتماع وانتهائه وأحداث التسجيل
  • تتبع التفاعل - تتبع مدة الحضور ومقاييس المشاركة
  • متابعة الندوات - تشغيل تسلسلات بريد إلكتروني مستهدفة بناءً على حضور الندوة
  • إشعارات التسجيل - إرسال روابط التسجيل عبر حملات بريد إلكتروني Brevo

المتطلبات الأساسية

قبل البدء، تأكد من توفر ما يلي:

  1. حساب Zoom (خطة Pro أو أعلى)
  2. تطبيق Zoom Server-to-Server OAuth أو تطبيق OAuth عبر Zoom App Marketplace
  3. حساب Brevo مع وصول إلى API
  4. حساب Tajo مع صلاحيات الموصلات

المصادقة

Server-to-Server OAuth (موصى به)

Terminal window
# Create a Server-to-Server OAuth app at marketplace.zoom.us
export ZOOM_ACCOUNT_ID=your_account_id
export ZOOM_CLIENT_ID=your_client_id
export ZOOM_CLIENT_SECRET=your_client_secret
// الحصول على رمز الوصول عبر Server-to-Server OAuth
const tokenResponse = await fetch('https://zoom.us/oauth/token', {
method: 'POST',
headers: {
'Authorization': `Basic ${Buffer.from(
`${process.env.ZOOM_CLIENT_ID}:${process.env.ZOOM_CLIENT_SECRET}`
).toString('base64')}`,
'Content-Type': 'application/x-www-form-urlencoded'
},
body: new URLSearchParams({
grant_type: 'account_credentials',
account_id: process.env.ZOOM_ACCOUNT_ID
})
});
const { access_token } = await tokenResponse.json();

OAuth 2.0 (على مستوى المستخدم)

// عنوان URL للتفويض لـ OAuth على مستوى المستخدم
const authUrl = 'https://zoom.us/oauth/authorize?' +
new URLSearchParams({
client_id: process.env.ZOOM_CLIENT_ID,
redirect_uri: 'https://your-app.com/callback',
response_type: 'code'
});
// استبدال الكود بالرموز
const tokenResponse = await fetch('https://zoom.us/oauth/token', {
method: 'POST',
headers: {
'Authorization': `Basic ${Buffer.from(
`${process.env.ZOOM_CLIENT_ID}:${process.env.ZOOM_CLIENT_SECRET}`
).toString('base64')}`,
'Content-Type': 'application/x-www-form-urlencoded'
},
body: new URLSearchParams({
grant_type: 'authorization_code',
code: authorizationCode,
redirect_uri: 'https://your-app.com/callback'
})
});

الإعداد

الإعداد الأساسي

connectors:
zoom:
enabled: true
account_id: "${ZOOM_ACCOUNT_ID}"
client_id: "${ZOOM_CLIENT_ID}"
client_secret: "${ZOOM_CLIENT_SECRET}"
sync:
participants: true
webinars: true
recordings: true
webhook:
secret_token: "${ZOOM_WEBHOOK_SECRET}"
verification_token: "${ZOOM_VERIFICATION_TOKEN}"
lists:
meeting_participants: 15
webinar_attendees: 16
webinar_registrants: 17

تعيين الحقول

field_mapping:
email: email
name: FIRSTNAME
join_time: MEETING_JOIN_DATE
duration: MEETING_DURATION
webinar_title: WEBINAR_NAME
attendance_status: ATTENDANCE_STATUS
registration_source: UTM_SOURCE

نقاط نهاية واجهة البرمجة

نقطة النهايةالطريقةالوصف
https://api.zoom.us/v2/usersGETسرد المستخدمين
https://api.zoom.us/v2/users/{userId}/meetingsGETسرد الاجتماعات
https://api.zoom.us/v2/meetings/{meetingId}GETالحصول على تفاصيل الاجتماع
https://api.zoom.us/v2/past_meetings/{meetingId}/participantsGETسرد المشاركين في الاجتماعات السابقة
https://api.zoom.us/v2/users/{userId}/webinarsGETسرد الندوات
https://api.zoom.us/v2/webinars/{webinarId}/registrantsGETسرد المسجلين في الندوات
https://api.zoom.us/v2/webinars/{webinarId}/participantsGETسرد المشاركين في الندوات
https://api.zoom.us/v2/meetings/{meetingId}/recordingsGETالحصول على تسجيلات الاجتماع
https://api.zoom.us/v2/webhooksPOSTالاشتراك في webhooks

أمثلة على الكود

تهيئة الموصل

import { TajoClient } from '@tajo/sdk';
const tajo = new TajoClient({
apiKey: process.env.TAJO_API_KEY,
brevoApiKey: process.env.BREVO_API_KEY
});
await tajo.connectors.connect('zoom', {
accountId: process.env.ZOOM_ACCOUNT_ID,
clientId: process.env.ZOOM_CLIENT_ID,
clientSecret: process.env.ZOOM_CLIENT_SECRET
});

مزامنة المشاركين في الاجتماع

// استرجاع المشاركين في الاجتماعات السابقة
const response = await fetch(
`https://api.zoom.us/v2/past_meetings/${meetingId}/participants`,
{
headers: {
'Authorization': `Bearer ${accessToken}`,
'Content-Type': 'application/json'
}
}
);
const { participants } = await response.json();
for (const participant of participants) {
if (participant.user_email) {
await tajo.contacts.sync({
email: participant.user_email,
attributes: {
FIRSTNAME: participant.name,
MEETING_DURATION: participant.duration,
MEETING_JOIN_DATE: participant.join_time,
ATTENDANCE_STATUS: 'attended'
},
listIds: [15]
});
}
}

مزامنة حضور الندوات

// الحصول على حضور الندوة ومزامنتهم مع Brevo
const attendeesResponse = await fetch(
`https://api.zoom.us/v2/past_webinars/${webinarId}/participants`,
{
headers: { 'Authorization': `Bearer ${accessToken}` }
}
);
const { participants: attendees } = await attendeesResponse.json();
for (const attendee of attendees) {
await tajo.contacts.sync({
email: attendee.user_email,
attributes: {
FIRSTNAME: attendee.name,
WEBINAR_NAME: webinarTitle,
ATTENDANCE_STATUS: 'attended',
MEETING_DURATION: attendee.duration
},
listIds: [16]
});
}

التعامل مع Zoom Webhooks

app.post('/webhooks/zoom', async (req, res) => {
// التعامل مع تحدي التحقق من عنوان URL لـ Zoom
if (req.body.event === 'endpoint.url_validation') {
const hashForValidation = crypto
.createHmac('sha256', process.env.ZOOM_WEBHOOK_SECRET)
.update(req.body.payload.plainToken)
.digest('hex');
return res.json({
plainToken: req.body.payload.plainToken,
encryptedToken: hashForValidation
});
}
// التحقق من توقيع webhook
const message = `v0:${req.headers['x-zm-request-timestamp']}:${JSON.stringify(req.body)}`;
const hash = crypto
.createHmac('sha256', process.env.ZOOM_WEBHOOK_SECRET)
.update(message)
.digest('hex');
const signature = `v0=${hash}`;
if (req.headers['x-zm-signature'] !== signature) {
return res.status(401).send('Unauthorized');
}
const { event, payload } = req.body;
await tajo.connectors.handleWebhook('zoom', {
topic: event,
payload: payload
});
res.status(200).send('OK');
});

حدود المعدل

الفئةالحدملاحظات
استدعاءات API الخفيفة30 طلب/ثانيةGET للمستخدم، معلومات الاجتماع
استدعاءات API المتوسطة20 طلب/ثانيةسرد المشاركين والندوات
استدعاءات API الثقيلة10 طلبات/ثانيةالتقارير والتسجيلات
الحد اليومي5,000+يعتمد على مستوى الخطة

ترويسات حدود المعدل

يُعيد Zoom الترويسات X-RateLimit-Limit وX-RateLimit-Remaining وRetry-After. طبّق منطق التراجع بناءً على هذه الترويسات لتجنب أخطاء 429.

استكشاف الأخطاء وإصلاحها

المشكلةالسببالحل
401 Unauthorizedالرمز منتهيحدّث رمز Server-to-Server OAuth
مشاركون مفقودونالاجتماع لم ينتهِانتظر حتى ينتهي الاجتماع للحصول على البيانات الكاملة
فشل التحقق من Webhookسر خاطئتحقق من سر webhook في Zoom Marketplace
لا توجد بيانات بريد إلكترونيمشاركون ضيوففعّل التسجيل لالتقاط عناوين البريد الإلكتروني
حد المعدل 429طلبات كثيرة جدًاطبّق التراجع الأُسّي

وضع التصحيح

connectors:
zoom:
debug: true
log_level: verbose
log_webhooks: true

أفضل الممارسات

  1. استخدم Server-to-Server OAuth - مصادقة أبسط بدون تفاعل مستخدم
  2. فعّل تسجيل الندوات - مطلوب لالتقاط عناوين البريد الإلكتروني للحضور
  3. عالج بعد انتهاء الاجتماع - تكون بيانات المشاركين كاملة فقط بعد انتهاء الاجتماعات
  4. قسّم حسب نوع الحدث - خصّص قوائم Brevo مختلفة للاجتماعات مقابل الندوات
  5. تتبع مقاييس التفاعل - استخدم المدة ووقت الانضمام لتسجيل العملاء المحتملين
  6. أرسل متابعات التسجيل - أتمِت تسليم روابط التسجيل عبر Brevo

الأمان

  • OAuth 2.0 - مصادقة Server-to-Server أو OAuth على مستوى المستخدم
  • التحقق من Webhook - التحقق من توقيع HMAC-SHA256
  • التحقق من URL - التحقق من التحدي والاستجابة لنقاط نهاية webhook
  • صلاحيات مقيدة - اطلب أدنى نطاقات OAuth المطلوبة
  • تدوير الرموز - رموز Server-to-Server تنتهي تلقائيًا (ساعة واحدة)
  • نقل مشفر - TLS 1.2+ لجميع اتصالات API

موارد ذات صلة

Subscribe to updates

developer-docs

Drop your email or phone number — we'll send you what matters next.

auto-detect
مساعد AI

مرحباً! اسألني أي شيء عن الوثائق.