تتيح قناة الهاتف لـpipeline في betool الردّ على المكالمات وإجراءها. والصوت في الوقت الفعلي، والنسخ النصّي بالبثّ، وتركيب الكلام بالبثّ، والمقاطعة (barge-in) — كلها مدعومة.
البنية
خلف الكواليس:
- يتولّى LiveKit نقل الصوت في الوقت الفعلي.
- يربط LiveKit-SIP خدمة LiveKit بخطّ ناقلك (SIP).
- ينسّق worker مخصّص المكالمة: النسخ (STT)، و LLM، وتركيب الكلام (TTS).
تعمل هذه الحزمة كـعملية منفصلة عن الواجهة الخلفية الرئيسية. ولا تقوم أنت بتهيئتها مباشرةً — بل يُعِدّ مشغّل نسختك جسر SIP.
مزوّدو الصوت
| الدور | المزوّدون | الافتراضي |
|---|---|---|
| النسخ (STT) | Deepgram، faster-whisper (يُنفَّذ محليًا) | Deepgram |
| التركيب (TTS) | ElevenLabs، Cartesia، OpenAI، Deepgram Aura | ElevenLabs |
يمكن الاطّلاع على كتالوج الأصوات لكل مزوّد TTS في لوحة الإدارة، مع الاستماع إلى عيّنة قبل الاختيار. أمّا الـ LLM فهو ما تختاره أنت (نموذج مُدار، أو BYOK، أو نموذج خاص — راجع ربط مفتاح LLM).
المتطلبات المسبقة
- خطّ SIP من ناقل.
- رقم وارد و/أو القدرة على إجراء مكالمات صادرة.
- وصول إلى مزوّدي STT / TTS المختارين.
في العرض المُدار، يمكن لـbetool توفير خطّ SIP ومزوّدي الصوت نيابةً عنك.
تصميم pipeline صوتي (مكالمة واردة)
يبدأ الـpipeline الصوتي بعقدة Start تحمل المستقبِل phone_gateway. ومع كل دورة كلام منسوخة، يستقبل الـpipeline على وجه الخصوص:
user_messageوphone.transcript— دورة الكلام المنسوخةphone.call— المكالمة: المُعرِّف، رقما المتصل / المتصَل به، الاتجاه (inbound/outbound)، الخطphone.from— رقم المتصلphone.caller_timezone— المنطقة الزمنية المستنتَجة من رمز الاتصال (فارغة عندما يغطّي الرمز عدّة مناطق زمنية)
يقرأ TTS بصوت مسموع النصَّ الذي يُنتجه الـpipeline.
إعدادات المستقبِل
يضبط المستقبِل phone_gateway سلوك المكالمة، دون كود:
- الترحيب — عدّة صيغ لرسالة الترحيب (تُختار إحداها عشوائيًا)، وترحيب مستقلّ للمكالمات الصادرة، ومهلة قبل الترحيب.
- الصمت — تذكير بعد صمت مطوَّل، ثم رسالة وداع وإنهاء المكالمة إذا استمرّ الصمت؛ والمدة القصوى للمكالمة.
- المقاطعة (barge-in) — مفعّلة افتراضيًا: يستطيع المتصل مقاطعة الوكيل. المدة والحدّ الأدنى لعدد الكلمات كي تُحتسَب المقاطعة.
- كشف نهاية الدور — نمط الكشف ومهل انتهاء الكلام.
- عبارات الانتظار (Fillers) — عبارات انتظار تُنطق حين يتأخّر الردّ، وعبارات مخصّصة أثناء تنفيذ أداة (tool)، أو خلفية صوتية للانتظار (لوحة مفاتيح، مكتب، موسيقى انتظار). معطّلة افتراضيًا.
- الصوت — المزوّد والنموذج واللغة والصوت لـ STT / TTS، مع الإعدادات الدقيقة للصوت (الثبات، السرعة…).
- تصنيفات المكالمة — قائمة مغلقة من رموز النتيجة التي يمكن للوكيل تعيينها على المكالمة.
ما يستطيع الوكيل فعله أثناء المكالمة
تتوفّر الأدوات الهاتفية لوكلاء أي pipeline يكون فيه phone_gateway في الأعلى:
phone_gateway.transfer_call— تحويل المكالمة إلى رقم آخر (SIP REFER). يُتحقَّق من الرقم وفق تنسيق E.164؛ ويتمّ التحويل بعد نطق الردّ الجاري.phone_gateway.hangup_call— إنهاء المكالمة، بعد رسالة الوداع.phone_gateway.set_call_disposition— تصنيف المكالمة بأحد الرموز المُهيّأة.
يستطيع الوكيل أيضًا إرسال SMS أثناء المكالمة (الأداة allmysms.send_sms، راجع SMS): على هذه القناة، يكون المستلِم مقفلًا على محاور المكالمة. وإذا كان الرقم محجوبًا، يُرفض الإرسال.
اقتراح مواعيد
يُنتج حساب التوافر (العملية free_slots في العقدة compute) مواعيد جاهزة للنطق، في المنطقة الزمنية للمتصل. وبالجمع مع قراءة التقويم (Google أو Microsoft)، يستطيع وكيل صوتي أن يذكر بعض المواعيد المتاحة ثم يحجز الموعد.
المكالمات الصادرة
يستطيع pipeline إجراء مكالمة عبر العقدة phone_call: مثلًا معاودة الاتصال بعميل محتمل فور وصوله، أو المتابعة مع قائمة.
| الحقل | الدور |
|---|---|
trunk_id | الخط المستخدَم للاتصال |
voice_model | النموذج الذي يدير المحادثة (يجب أن يحمل الـ Start الخاص به المستقبِل phone_gateway) |
to_number | الرقم المطلوب الاتصال به (قابل للقولبة)، مُطبَّع وفق تنسيق E.164 |
call_vars | متغيّرات تُمرَّر إلى المحادثة (phone.outbound.vars) — مثلًا الاسم الأول، القابل للاستخدام في الترحيب الصادر |
allowed_days / allowed_hours / timezone | النافذة الزمنية المسموح بها: خارجها، لا تُجرى المكالمة |
max_in_flight / max_per_day | الحدود القصوى للمكالمات المتزامنة (3 افتراضيًا) واليومية (100 افتراضيًا) |
output_key | مفتاح الإخراج (الافتراضي phone.call_result) |
الضمانات:
- Exactly-once — إعادة التشغيل لا تُعيد أبدًا طلب رقم سبق الاتصال به.
- الرفض قبل الطلب إذا لم يعُد لدى المؤسسة أرصدة.
- لا مكالمات في وضع المحاكاة — تُتجاهَل العقدة أثناء تنفيذ تجريبي (dry-run).
تُعيد العقدة التحكّم بمجرد أن يرنّ الهاتف: ok تعني «أُطلقت المكالمة»، لا «تمّ الردّ». ولمعرفة النتيجة، أضِف إلى الـ Start الخاص بالنموذج المستقبِل phone_call_outcome: فهو يُشغِّل الـpipeline بعد انتهاء المكالمة، مع phone.outcome — تمّ الردّ أم لا (answered، no_answer، rejected، unknown)، والمدة، وعدد الأدوار، والتصنيف الذي عيّنه الوكيل.
أفضل الممارسات
- اجعل المهام موجزة. زمن التفكير مهم: وكيل يتردّد لمدة 4 ثوانٍ يبدو متجمّدًا في المكالمة. فضّل النماذج السريعة إلا في الدورات الحاسمة للقرار.
- أبقِ المقاطعة (barge-in) مفعّلة. يجب أن يتمكّن المتصل من مقاطعة الوكيل. وهذا هو الإعداد الافتراضي.
- هيّئ عبارات انتظار (fillers) للدورات التي تستدعي أدوات: الصمت الطويل يُقلق المتصل.
التكاليف
راجع التسعير. ليس للمكالمة سعر بالدقيقة في حدّ ذاتها: بل تُفوتَر بحسب مكوّناتها — النسخ (بحسب مدة الصوت)، وتركيب الكلام (بحسب عدد الأحرف)، و LLM (بحسب التوكِنات، إلا في BYOK).
القيود المعروفة
- القناة الهاتفية صوتية فقط. أمّا الفيديو فيمرّ عبر لبنات أخرى (توليد الفيديو ودبلجته مع HeyGen)، لا عبر المكالمة.
- التحويل إلى إنسان يتطلّب خطّ SIP يدعم REFER.
- لا يستطيع الوكيل تحديد هوية المتصل دون تكامل CRM: فهو لا يعرف سوى الرقم المعروض.