Your AI Connector Docs

الرسائل والمحادثات

تتيح لك واجهة برمجة تطبيقات الرسائل (Messages API) إرسال رسالة إلى أي جهة اتصال، وقراءة محادثة، وتصحيح أو حذف رسالة أرسلتها بالفعل، والتفاعل مع رسالة، وسحب سلسلة محادثة كاملة، وتصدير نص المحادثة، ووضع علامة على المحادثات كمقروءة أو غير مقروءة — كل ذلك دون فتح صندوق الوارد.

جميع المسارات في هذه الصفحة نسبية إلى عنوان URL الأساسي https://api.youraiconnector.com/v1. يتطلب كل طلب مفتاح واجهة برمجة التطبيقات الخاص بك — راجع المصادقة للحصول على القائمة الكاملة لطرق إرساله. تستخدم الأمثلة أدناه ترويسة X-API-Key، مع مثال cURL واحد يوضح نموذج استعلام ?apiKey= أيضًا.

كيفية عمل التسليم: إرسال رسالة لا يعني انتظار وصولها. تقبل واجهة برمجة التطبيقات رسالتك، وتستجيب فوراً بمعرف الرسالة (message ID)، ثم تقوم بتسليمها في الخلفية عبر قناة جهة الاتصال (WhatsApp، SMS، Instagram، وما إلى ذلك). لتتبع ما إذا كانت الرسالة قد تم تسليمها أو قراءتها بالفعل، استمع إلى تحديثات الحالة عبر Webhooks — لا تستخدم الاستطلاع (polling). استجابة الإرسال تؤكد فقط قبول الرسالة.


إرسال رسالة

هناك طريقتان للإرسال. اختر ما يناسب الطريقة التي تحدد بها جهة الاتصال حالياً:

  • الإرسال بواسطة معرف جهة الاتصال (contact ID) — أنت تعرف بالفعل معرف جهة الاتصال (على سبيل المثال، قمت بإنشاء جهة الاتصال من خلال واجهة برمجة التطبيقات أو حصلت عليه من webhook). استخدم POST /contacts/{contactId}/send-message.
  • الإرسال بواسطة هوية جهة الاتصال (contact identity) — أنت تعرف رقم هاتف جهة الاتصال، أو معرف Instagram، وما إلى ذلك، ولكن ليس معرفها الداخلي. استخدم POST /contacts/send ودع المنصة تعثر على جهة الاتصال الصحيحة.

كلاهما يضع الرسالة في قائمة الانتظار بنفس الطريقة ويسلمها عبر القناة التي تستخدمها جهة الاتصال. أنت لا تختار وسيلة النقل — تقوم المنصة بتوجيه جهات اتصال WhatsApp عبر WhatsApp، وجهات اتصال SMS عبر SMS، وهكذا.

الإرسال بواسطة معرف جهة الاتصال

POST /contacts/{contactId}/send-message

الحقل مطلوب الوصف
body نعم نص الرسالة المراد إرسالها.
mediaUrl لا رابط URL لملف وسائط (صورة، مستند، إلخ) لإرفاقه.
mediaContentType لا نوع MIME للوسائط المرفقة، على سبيل المثال image/jpeg.
pauseBot لا true يقوم بإيقاف الذكاء الاصطناعي مؤقتاً لهذا جهة الاتصال عند إرسال الرسالة — وذلك لتدخل بشري. راجع إيقاف أو استئناف الذكاء الاصطناعي.
clearIncompleteReply لا true يتجاهل رد البوت غير المكتمل حتى لا يستأنف العمل بعد رسالتك.

cURL

curl -X POST "https://api.youraiconnector.com/v1/contacts/contact123/send-message" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "body": "Hi! Your appointment is confirmed for tomorrow at 10:00."
  }'

JavaScript

const res = await fetch(
  "https://api.youraiconnector.com/v1/contacts/contact123/send-message",
  {
    method: "POST",
    headers: {
      "X-API-Key": "YOUR_API_KEY",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({
      body: "Hi! Your appointment is confirmed for tomorrow at 10:00.",
    }),
  }
);
const data = await res.json();
console.log(data.messageId);

Python

import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/contacts/contact123/send-message",
    headers={
        "X-API-Key": "YOUR_API_KEY",
        "Content-Type": "application/json",
    },
    json={"body": "Hi! Your appointment is confirmed for tomorrow at 10:00."},
)
print(res.json()["messageId"])

الاستجابة (200 OK):

{
  "success": true,
  "messageId": "aB3dE5fG7hI9jK1lM2nO",
  "contactId": "contact123",
  "channel": "whatsapp",
  "message": "Message created successfully. Delivery is being processed."
}

الإرسال بواسطة هوية جهة الاتصال

POST /contacts/send

استخدم هذا عندما لا يكون لديك المعرف الداخلي لجهة الاتصال. قدم نص الرسالة body بالإضافة إلى إما contact_id، أو channel مع حقل الهوية الذي يطابق تلك القناة.

الحقل مطلوب الوصف
body نعم نص الرسالة المراد إرسالها.
contact_id لا معرف جهة اتصال موجودة. عند تعيينه، لا تكون حقول الهوية أدناه مطلوبة.
channel لا القناة المراد الإرسال عبرها. مطلوبة عند عدم توفير contact_id. واحدة من القنوات الـ 14 القابلة للإرسال الخارجي: whatsapp، whatsapp_web، sms، instagram، instagram_private، messenger، telegram، chat-widget، custom، email، line، imessage، linkedin، viber.
phone_number لا رقم هاتف جهة الاتصال بالتنسيق الدولي. يُستخدم مع whatsapp و whatsapp_web و sms.
instagram_id لا معرف مستخدم Instagram الخاص بجهة الاتصال. يُستخدم مع instagram.
messenger_id لا معرف مستخدم Messenger الخاص بجهة الاتصال. يُستخدم مع messenger.
telegram_user_id لا معرف مستخدم Telegram الخاص بجهة الاتصال. يُستخدم مع telegram.
media_url لا رابط URL لملف وسائط لإرفاقه.
media_content_type لا نوع MIME للوسائط المرفقة، على سبيل المثال image/jpeg.

القنوات التي يمكن تحديدها عن طريق الهوية. ست قنوات فقط من أصل 14 تقبل حقل هوية بدلاً من contact_id: يتم البحث عن whatsapp و whatsapp_web و sms بواسطة phone_number، و instagram بواسطة instagram_id، و messenger بواسطة messenger_id، و telegram بواسطة telegram_user_id. القنوات الثماني الأخرى — instagram_private و chat-widget و custom و email و line و imessage و linkedin و viber — ليس لها هوية عامة يمكن البحث عنها، لذا فإن الإرسال عبر تلك القنوات يتطلب contact_id؛ تمرير channel بمفرده يُرجع 400 يخبرك بأن contact_id مطلوب.

cURL (باستخدام نموذج استعلام ?apiKey=)

curl -X POST "https://api.youraiconnector.com/v1/contacts/send?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "channel": "whatsapp",
    "phone_number": "+31612345678",
    "body": "Hi! Your appointment is confirmed."
  }'

JavaScript

const res = await fetch("https://api.youraiconnector.com/v1/contacts/send", {
  method: "POST",
  headers: {
    "X-API-Key": "YOUR_API_KEY",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    channel: "whatsapp",
    phone_number: "+31612345678",
    body: "Hi! Your appointment is confirmed.",
  }),
});
const data = await res.json();
console.log(data.message_id, data.channel);

Python

import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/contacts/send",
    headers={
        "X-API-Key": "YOUR_API_KEY",
        "Content-Type": "application/json",
    },
    json={
        "channel": "whatsapp",
        "phone_number": "+31612345678",
        "body": "Hi! Your appointment is confirmed.",
    },
)
data = res.json()
print(data["message_id"], data["channel"])

الاستجابة (201 Created):

{
  "success": true,
  "message_id": "aB3dE5fG7hI9jK1lM2nO",
  "contact_id": "contact123",
  "channel": "whatsapp"
}

لماذا قد يتم رفض الرسالة: لا يمكن لجهة اتصال قامت بتفعيل وضع عدم الإزعاج أو الوضع الخاص تلقي رسائل صادرة — سيفشل الطلب مع 422. إذا لم تطابق أي جهة اتصال المعرف أو الهوية التي قدمتها، ستحصل على 404.


سرد رسائل جهة اتصال

GET /contacts/{contactId}/messages

يعيد رسائل جهة الاتصال، الأحدث أولاً، مع ترقيم صفحات يعتمد على المؤشر.

معامل الاستعلام مطلوب الوصف
limit لا حجم الصفحة. القيمة الافتراضية 50، والحد الأقصى 100.
cursor لا قيمة next_cursor من استجابة سابقة. يعيد الرسائل الأقدم من المؤشر.
filter لا التصفية حسب نوع المحتوى: all (افتراضي)، text، media، أو tool_use.
direction لا التصفية حسب الاتجاه: all (افتراضي)، inbound (مستلمة من جهة الاتصال)، أو outbound (مرسلة بواسطتك).

ملاحظة حول التصفية وترقيم الصفحات: يتم تطبيق عوامل التصفية filter و direction على كل صفحة بعد قراءتها، لذا قد تحتوي الصفحة المفلترة على عناصر أقل من limit. لا يزال next_cursor يتقدم عبر المحادثة الكاملة، لذا استمر في التنقل بين الصفحات حتى تصبح next_cursor مساوية لـ null.

cURL

curl "https://api.youraiconnector.com/v1/contacts/contact123/messages?limit=50&direction=inbound" \
  -H "X-API-Key: YOUR_API_KEY"

JavaScript

const params = new URLSearchParams({ limit: "50", direction: "inbound" });
const res = await fetch(
  `https://api.youraiconnector.com/v1/contacts/contact123/messages?${params}`,
  { headers: { "X-API-Key": "YOUR_API_KEY" } }
);
const data = await res.json();
console.log(data.messages, data.next_cursor);

Python

import requests

res = requests.get(
    "https://api.youraiconnector.com/v1/contacts/contact123/messages",
    headers={"X-API-Key": "YOUR_API_KEY"},
    params={"limit": 50, "direction": "inbound"},
)
data = res.json()
print(data["messages"], data["next_cursor"])

الاستجابة (200 OK):

{
  "success": true,
  "contact_id": "contact123",
  "messages": [
    {
      "id": "aB3dE5fG7hI9jK1lM2nO",
      "body": "Hi! Thanks for reaching out.",
      "direction": "inbound",
      "channel": "whatsapp",
      "status": "delivered",
      "type": null,
      "timestamp": "2026-06-01T10:00:00.000Z",
      "media_url": null,
      "media_content_type": null,
      "bot_reply": false
    }
  ],
  "next_cursor": "cD4eF6gH8iJ0kL2mN3oP"
}

حقول الرسالة

الحقل الوصف
id المعرف الفريد للرسالة.
body محتوى نص الرسالة.
direction inbound (مستلمة من جهة الاتصال) أو outbound (مرسلة من حسابك).
channel القناة التي تم إرسال أو استلام الرسالة عبرها (مثل whatsapp، sms، instagram).
status حالة التسليم الحالية، مثل Created، sent، delivered، read، failed.
type نوع الرسالة. رسائل النص العادي لها النوع null؛ ويتم تمييز نشاط أداة المساعد الآلي بـ tool_use.
timestamp وقت إنشاء الرسالة بتنسيق ISO 8601.
media_url رابط URL لملف وسائط مرفق، إن وجد.
media_content_type نوع MIME للوسائط المرفقة، إن وجدت.
bot_reply true عندما يتم إنشاء الرسالة بواسطة المساعد الذكي.
score تقييمك للرسالة: 1 إعجاب، -1 عدم إعجاب، 0 عندما لم يتم تقييمها. راجع تقييم أو تمييز رسالة بنجمة.
is_important true عندما يتم تمييز الرسالة بنجمة.
is_deleted true عندما يتم حذف الرسالة. تظل الرسائل المحذوفة في القائمة ولكن حقول body و media_url الخاصة بها تكون فارغة.
reactions تفاعلات الرموز التعبيرية على الرسالة، من كلا الطرفين. تكون دائمًا مصفوفة — فارغة عند عدم وجود تفاعلات. يحتوي كل إدخال على emoji، وfrom_phone_number، وfrom_me (true عندما يكون التفاعل خاصًا بك) وreacted_at.

سرد جلسات المحادثة

جلسة المحادثة هي نافذة محادثة واحدة مع جهة اتصال: تبدأ عندما يبدأون في التحدث وتغلق عند انتهاء المحادثة. الجلسات هي الطريقة التي تقوم بها بتقسيم سجل طويل إلى محادثات قابلة للقراءة بدلاً من قائمة واحدة لا تنتهي.

الجلسات الأخيرة عبر جميع جهات الاتصال

GET /chat-sessions/recent

تُرجع الجلسات التي بدأت في آخر X ساعة، مرتبة من الأحدث، عبر كل جهة اتصال في الحساب.

معلمة الاستعلام مطلوبة الوصف
hours نعم عدد الساعات التي يجب الرجوع إليها. يجب أن يكون رقمًا صحيحًا موجبًا.
status لا إرجاع الجلسات ذات الحالة التالية فقط: ChatSessionOpened أو ChatSessionClosed.
limit لا الحد الأقصى لعدد الجلسات المراد إرجاعها. القيمة الافتراضية 100، والحد الأقصى 100.
includeMessages لا true تضيف مصفوفة messages إلى كل جلسة. معطلة افتراضيًا لأنها تجعل الاستجابة أكبر بكثير.

cURL

curl "https://api.youraiconnector.com/v1/chat-sessions/recent?hours=24&status=ChatSessionClosed" \
  -H "X-API-Key: YOUR_API_KEY"

JavaScript

const params = new URLSearchParams({ hours: "24", status: "ChatSessionClosed" });
const res = await fetch(`https://api.youraiconnector.com/v1/chat-sessions/recent?${params}`, {
  headers: { "X-API-Key": "YOUR_API_KEY" },
});
const data = await res.json();
console.log(data.data.total_sessions, data.data.sessions);

Python

import requests

res = requests.get(
    "https://api.youraiconnector.com/v1/chat-sessions/recent",
    headers={"X-API-Key": "YOUR_API_KEY"},
    params={"hours": 24, "status": "ChatSessionClosed"},
)
data = res.json()["data"]
print(data["total_sessions"], data["sessions"])

الاستجابة (200 OK):

{
  "success": true,
  "data": {
    "hours_ago": 24,
    "total_sessions": 2,
    "sessions": [
      {
        "session_id": "session456",
        "contact_id": "contact123",
        "contact_name": "Jane Doe",
        "contact_phone": "+31612345678",
        "contact_email": "jane@example.com",
        "start_date_time": "2026-06-01T09:55:00.000Z",
        "end_date_time": "2026-06-01T10:20:00.000Z",
        "status": "ChatSessionClosed",
        "tag": "Booking enquiry"
      }
    ]
  }
}

جميع الجلسات لجهة اتصال واحدة

GET /chat-sessions/{contactId}

تُرجع كل جلسة محادثة لجهة اتصال واحدة. تستخدم نفس معلمات status و limit و includeMessages المذكورة أعلاه — hours لا تنطبق هنا.

cURL

curl "https://api.youraiconnector.com/v1/chat-sessions/contact123?limit=20" \
  -H "X-API-Key: YOUR_API_KEY"

الاستجابة (200 OK):

{
  "success": true,
  "data": {
    "contact_id": "contact123",
    "contact_name": "Jane Doe",
    "total_sessions": 2,
    "sessions": [
      {
        "id": "session456",
        "start_date_time": "2026-06-01T09:55:00.000Z",
        "end_date_time": "2026-06-01T10:20:00.000Z",
        "status": "ChatSessionClosed",
        "tag": "Booking enquiry"
      }
    ]
  }
}

تختلف أسماء حقول معرف الجلسة بين نقطتي النهاية. تسميها قائمة الجلسات الأخيرة session_id (كما أنها تحمل تفاصيل جهة الاتصال، نظرًا لأن الجلسات تأتي من جهات اتصال متعددة)؛ بينما تسميها قائمة كل جهة اتصال id. أي من القيمتين هي ما تمرره كـ {sessionId} عند جلب السلسلة الكاملة أدناه.

عند includeMessages=true، تكتسب كل جلسة مصفوفة messages تحتوي إدخالاتها على id، وbody، وdirection، وtimestamp، وtype، وchannel، وstatus.


جلب سلسلة محادثة

GET /contacts/{contactId}/chat-sessions/{sessionId}/messages

تجمع جلسة الدردشة رسائل جهة الاتصال في نافذة محادثة واحدة. تُرجع نقطة النهاية هذه سلسلة الرسائل الكاملة لجلسة واحدة، بدءاً من الأقدم، إلى جانب البيانات الوصفية للجلسة. يمكنك العثور على معرفات الجلسة لجهة اتصال من خلال نقاط نهاية جلسات الدردشة.

cURL

curl "https://api.youraiconnector.com/v1/contacts/contact123/chat-sessions/session456/messages" \
  -H "X-API-Key: YOUR_API_KEY"

JavaScript

const res = await fetch(
  "https://api.youraiconnector.com/v1/contacts/contact123/chat-sessions/session456/messages",
  { headers: { "X-API-Key": "YOUR_API_KEY" } }
);
const data = await res.json();
console.log(data.session, data.messages);

Python

import requests

res = requests.get(
    "https://api.youraiconnector.com/v1/contacts/contact123/chat-sessions/session456/messages",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()
print(data["session"], data["messages"])

الاستجابة (200 OK):

{
  "success": true,
  "contact_id": "contact123",
  "session": {
    "id": "session456",
    "status": "ChatSessionClosed",
    "start_date_time": "2026-06-01T09:55:00.000Z",
    "end_date_time": "2026-06-01T10:20:00.000Z",
    "tag": "Booking enquiry"
  },
  "messages": [
    {
      "id": "aB3dE5fG7hI9jK1lM2nO",
      "body": "Hi! Thanks for reaching out.",
      "direction": "inbound",
      "channel": "whatsapp",
      "status": "delivered",
      "type": null,
      "timestamp": "2026-06-01T09:55:00.000Z",
      "media_url": null,
      "media_content_type": null,
      "bot_reply": false
    }
  ]
}

يُبلغ كائن session عن status (ChatSessionOpened أثناء النشاط، وChatSessionClosed بمجرد الانتهاء)، وstart_date_time، وend_date_time، وtag يمكن قراءته من قبل البشر. تستخدم مصفوفة messages نفس حقول الرسائل المستخدمة في نقطة نهاية القائمة.


تحرير وحذف والتفاعل مع الرسائل

تغير نقاط النهاية هذه الرسالة بعد إرسالها. اثنتان منها تتواصلان مع قناة جهة الاتصال بالإضافة إلى نسختك الخاصة، لذا اقرأ مقدمة القسم قبل ربطها — ما هو ممكن يعتمد كليًا على القناة التي تتم عليها المحادثة.

ما تسمح به كل قناة

الإجراء القنوات التي يمكنها تغيير نسخة جهة الاتصال المهلة الزمنية
تعديل رسالة مرسلة أداة الدردشة، WhatsApp Web، Telegram، LinkedIn لا توجد مهلة لأداة الدردشة، 15 دقيقة على WhatsApp Web، 48 ساعة على Telegram، 60 دقيقة على LinkedIn
الحذف للجميع أداة الدردشة، WhatsApp Web، Telegram، LinkedIn 60 دقيقة على LinkedIn؛ القنوات الأخرى ليس لها حد معلن
التفاعل برمز تعبيري WhatsApp Web، Telegram لا توجد

في جميع القنوات الأخرى — واجهة برمجة تطبيقات WhatsApp Business، والرسائل القصيرة (SMS)، وInstagram، وMessenger، والبريد الإلكتروني، وLINE، والقنوات المخصصة — لا يزال الحذف يزيل الرسالة من صندوق الوارد الخاص بك، لكن جهة الاتصال تحتفظ بنسختها، كما أن التعديل أو التفاعل غير ممكن على الإطلاق.

تعديل رسالة

POST /contacts/{contactId}/messages/{messageId}/edit

يعيد كتابة رسالة أرسلتها بالفعل، على جهاز جهة الاتصال وفي نسختك الخاصة.

الحقل مطلوب الوصف
body نعم نص الرسالة الجديد. يجب ألا يكون فارغاً ويمكن أن يصل إلى 4096 حرفاً كحد أقصى.

على عكس الحذف، يفشل هذا بشكل واضح عندما ترفض القناة ذلك: ستحصل على 409 وستبقى نسختك مطابقة تماماً لما لدى جهة الاتصال، لأن إظهار تعديل لم يتلقوه سيؤدي إلى عدم تطابق بين الطرفين. يخبرك الحقل edit_reason بالسبب — نافذة التعديل الخاصة بالقناة قد أُغلقت، أو القناة غير متصلة، أو حدث خطأ ما.

cURL

curl -X POST "https://api.youraiconnector.com/v1/contacts/contact123/messages/msg_1/edit" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "body": "Sorry - I meant Thursday at 3pm." }'

JavaScript

const res = await fetch(
  "https://api.youraiconnector.com/v1/contacts/contact123/messages/msg_1/edit",
  {
    method: "POST",
    headers: {
      "X-API-Key": "YOUR_API_KEY",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({ body: "Sorry - I meant Thursday at 3pm." }),
  }
);
const data = await res.json();
console.log(data.edited, data.edit_reason);

Python

import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/contacts/contact123/messages/msg_1/edit",
    headers={
        "X-API-Key": "YOUR_API_KEY",
        "Content-Type": "application/json",
    },
    json={"body": "Sorry - I meant Thursday at 3pm."},
)
data = res.json()
print(data.get("edited"), data.get("edit_reason"))

الاستجابة (200 OK):

{
  "success": true,
  "contact_id": "contact123",
  "message_id": "msg_1",
  "edited": true,
  "edit_reason": "edit_dispatched"
}

إذا لم تقبل القناة التعديل، ستحصل على 409 بدلاً من ذلك، ولن يتم تغيير أي شيء:

{
  "success": false,
  "error": "The message could not be edited",
  "edit_reason": "channel_disconnected"
}

الرسالة التي تم حذفها بالفعل، والقناة التي لا تدعم التعديل على الإطلاق، والرسالة القديمة جداً بالنسبة لقناتها، جميعها تعيد 400 — الطلب لا يصل أبداً إلى القناة.

حذف رسالة واحدة

DELETE /contacts/{contactId}/messages/{messageId}

يزيل الرسالة من محادثتك، وفي حال كانت القناة تسمح بذلك، يسحب نسخة جهة الاتصال أيضاً. لا يوجد نص للطلب (request body).

يستجيب هذا دائماً بـ 200 عندما تكون الرسالة موجودة، حتى لو تعذر سحب نسخة جهة الاتصال — نسختك قد حُذفت بالفعل، لذا فإن إظهار خطأ سيكون مضللاً. اقرأ الحقول الثلاثة في الاستجابة لتخبر المستخدم بما حدث فعلياً:

الحقل الوصف
revoke_supported ما إذا كانت هذه القناة قادرة على سحب الرسائل على الإطلاق.
revoked ما إذا تمت إزالة النسخة الموجودة على جهاز جهة الاتصال.
revoke_reason سبب عدم إزالتها، عندما تكون revoked هي false — على سبيل المثال revoke_window_closed أو already_deleted.

cURL

curl -X DELETE "https://api.youraiconnector.com/v1/contacts/contact123/messages/msg_1" \
  -H "X-API-Key: YOUR_API_KEY"

JavaScript

const res = await fetch(
  "https://api.youraiconnector.com/v1/contacts/contact123/messages/msg_1",
  { method: "DELETE", headers: { "X-API-Key": "YOUR_API_KEY" } }
);
const data = await res.json();
console.log(data.revoked, data.revoke_reason);

Python

import requests

res = requests.delete(
    "https://api.youraiconnector.com/v1/contacts/contact123/messages/msg_1",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()
print(data["revoked"], data["revoke_reason"])

الاستجابة (200 OK):

{
  "success": true,
  "contact_id": "contact123",
  "message_id": "msg_1",
  "revoke_supported": true,
  "revoked": true,
  "revoke_reason": "revoke_dispatched"
}

لا تتم إزالة الرسائل المحذوفة من سجل المحادثة. بل تبقى في GET /contacts/{contactId}/messages مع is_deleted: true و body فارغ و media_url.

حذف عدة رسائل دفعة واحدة

POST /contacts/{contactId}/messages/bulk-delete

يمسح مجموعة من الرسائل من جانبك فقط. يتم إفراغ محتويات الرسائل والمرفقات، ولكن لا يتم سحب أي شيء من جهاز جهة الاتصال — لسحب رسالة أيضاً، احذفها واحدة تلو الأخرى باستخدام نقطة نهاية الرسالة الواحدة أعلاه.

الحقل مطلوب الوصف
message_ids نعم مصفوفة غير فارغة من معرفات الرسائل، بحد أقصى 500 لكل طلب. يتم قبول messageIds كاسم مستعار.

cURL

curl -X POST "https://api.youraiconnector.com/v1/contacts/contact123/messages/bulk-delete" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "message_ids": ["msg_1", "msg_2"] }'

JavaScript

const res = await fetch(
  "https://api.youraiconnector.com/v1/contacts/contact123/messages/bulk-delete",
  {
    method: "POST",
    headers: {
      "X-API-Key": "YOUR_API_KEY",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({ message_ids: ["msg_1", "msg_2"] }),
  }
);
console.log((await res.json()).deleted);

Python

import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/contacts/contact123/messages/bulk-delete",
    headers={
        "X-API-Key": "YOUR_API_KEY",
        "Content-Type": "application/json",
    },
    json={"message_ids": ["msg_1", "msg_2"]},
)
print(res.json()["deleted"])

الاستجابة (200 OK):

{
  "success": true,
  "contact_id": "contact123",
  "deleted": 2
}

التفاعل مع رسالة

POST /contacts/{contactId}/messages/{messageId}/react

يضع تفاعل الرموز التعبيرية (إيموجي) الخاص بك على رسالة، أو يسحبه بإرسال سلسلة نصية فارغة. لا يتم المساس بتفاعلات جهة الاتصال أبداً.

الحقل مطلوب الوصف
emoji نعم الرمز التعبيري للتفاعل به، أو "" لإزالة تفاعلك. يجب أن يكون سلسلة نصية واحدة بدون مسافات، وبحد أقصى 16 حرفاً.

مثل التعديل، يفشل هذا الإجراء بدلاً من إظهار تفاعل لم تصل لجهة الاتصال، ويخبرك الفشل ما إذا كانت إعادة المحاولة تستحق العناء:

  • 422 — لا يمكن تسليمها أبداً في هذه المحادثة: القناة لا تدعم التفاعلات، أو الرسالة ليس لها معرف من جانب القناة، أو الرمز التعبيري خارج المجموعة التي تسمح بها القناة.
  • 409 — القناة كانت غير قابلة للوصول مؤقتاً. قد تنجح إعادة المحاولة.

cURL

curl -X POST "https://api.youraiconnector.com/v1/contacts/contact123/messages/msg_1/react" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "emoji": "👍" }'

JavaScript

const res = await fetch(
  "https://api.youraiconnector.com/v1/contacts/contact123/messages/msg_1/react",
  {
    method: "POST",
    headers: {
      "X-API-Key": "YOUR_API_KEY",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({ emoji: "👍" }),
  }
);
const data = await res.json();
console.log(data.reactions);

Python

import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/contacts/contact123/messages/msg_1/react",
    headers={
        "X-API-Key": "YOUR_API_KEY",
        "Content-Type": "application/json",
    },
    json={"emoji": "👍"},
)
print(res.json()["reactions"])

الاستجابة (200 OK):

{
  "success": true,
  "contact_id": "contact123",
  "message_id": "msg_1",
  "reaction_supported": true,
  "reaction_reason": "reaction_dispatched",
  "reactions": [
    {
      "emoji": "👍",
      "from_phone_number": "+31612345678",
      "from_me": true,
      "reacted_at": "2026-06-01T10:05:00.000Z"
    }
  ]
}

مصفوفة reactions هي المجموعة الكاملة للتفاعلات الموجودة حالياً على الرسالة، الخاصة بك والخاصة بجهة الاتصال. عند 409 أو 422 يتم إرجاعها دون تغيير، لذا فإن العميل الذي يعرض البيانات مباشرة منها لا يظهر أبداً تفاعلاً لم يتم تسليمه.

تقييم أو تمييز رسالة بنجمة

PATCH /contacts/{contactId}/messages/{messageId}

يقيم رسالة بإبهام لأعلى أو لأسفل و/أو يضع عليها نجمة كرسالة مهمة. هذا مجرد تنظيم من جانبك فقط — لا يتم إرسال أي شيء إلى جهة الاتصال.

الحقل مطلوب الوصف
score لا 1 إعجاب، -1 عدم إعجاب، 0 مسح التقييم.
is_important لا true تمييز الرسالة بنجمة، false إزالة النجمة عنها. يجب أن تكون قيمة منطقية (boolean) حقيقية، وليست السلسلة النصية "true".

أرسل واحدة على الأقل من الاثنتين، وإلا ستحصل على 400. يتم كتابة ما ترسله فقط، لذا فإن تمييز رسالة بنجمة لا يؤدي أبداً إلى مسح تقييمها والعكس صحيح — كما أن الاستجابة تعيد فقط الحقول التي أرسلتها.

cURL

curl -X PATCH "https://api.youraiconnector.com/v1/contacts/contact123/messages/msg_1" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "score": 1, "is_important": true }'

JavaScript

await fetch("https://api.youraiconnector.com/v1/contacts/contact123/messages/msg_1", {
  method: "PATCH",
  headers: {
    "X-API-Key": "YOUR_API_KEY",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({ score: 1, is_important: true }),
});

Python

import requests

requests.patch(
    "https://api.youraiconnector.com/v1/contacts/contact123/messages/msg_1",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={"score": 1, "is_important": True},
)

الاستجابة (200 OK):

{
  "success": true,
  "contact_id": "contact123",
  "message_id": "msg_1",
  "score": 1,
  "is_important": true
}

وضع علامة مقروء على الرسائل

يمكنك مسح حالة غير مقروء إما لرسائل محددة أو للمحادثة بأكملها.

وضع علامة مقروء على رسائل محددة

POST /contacts/{contactId}/messages/mark-read

قم بتمرير معرفات الرسائل لوضع علامة مقروء عليها.

الحقل مطلوب الوصف
message_ids نعم مصفوفة غير فارغة من معرفات الرسائل (حتى 500 لكل طلب).

cURL

curl -X POST "https://api.youraiconnector.com/v1/contacts/contact123/messages/mark-read" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "message_ids": ["aB3dE5fG7hI9jK1lM2nO", "cD4eF6gH8iJ0kL2mN3oP"]
  }'

JavaScript

const res = await fetch(
  "https://api.youraiconnector.com/v1/contacts/contact123/messages/mark-read",
  {
    method: "POST",
    headers: {
      "X-API-Key": "YOUR_API_KEY",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({
      message_ids: ["aB3dE5fG7hI9jK1lM2nO", "cD4eF6gH8iJ0kL2mN3oP"],
    }),
  }
);
const data = await res.json();
console.log(data.marked_read);

Python

import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/contacts/contact123/messages/mark-read",
    headers={
        "X-API-Key": "YOUR_API_KEY",
        "Content-Type": "application/json",
    },
    json={"message_ids": ["aB3dE5fG7hI9jK1lM2nO", "cD4eF6gH8iJ0kL2mN3oP"]},
)
print(res.json()["marked_read"])

الاستجابة (200 OK):

{
  "success": true,
  "contact_id": "contact123",
  "marked_read": 2
}

وضع علامة مقروء على الدردشة بأكملها

POST /contacts/{contactId}/mark-read

يمسح شارة غير مقروء لمحادثة جهة الاتصال بأكملها في صندوق الوارد. لا يلزم وجود نص طلب.

cURL

curl -X POST "https://api.youraiconnector.com/v1/contacts/contact123/mark-read" \
  -H "X-API-Key: YOUR_API_KEY"

JavaScript

const res = await fetch(
  "https://api.youraiconnector.com/v1/contacts/contact123/mark-read",
  { method: "POST", headers: { "X-API-Key": "YOUR_API_KEY" } }
);
const data = await res.json();
console.log(data.success);

Python

import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/contacts/contact123/mark-read",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
print(res.json()["success"])

الاستجابة (200 OK):

{
  "success": true,
  "contact_id": "contact123"
}

وضع علامة غير مقروء على المحادثة بأكملها

POST /contacts/{contactId}/mark-unread

يعيد شارة “غير مقروء” إلى المحادثة — مفيد عندما يفتح شخص ما في فريقك محادثة ولكنه يعيدها إليك. لا يلزم وجود نص طلب (request body).

هذه علامة خاصة بصندوق الوارد فقط: فهي لا تغير وقت آخر قراءة للمحادثة، لذا لا يتم إرسال إيصال قراءة إلى جهة الاتصال في القنوات التي تدعم ذلك.

cURL

curl -X POST "https://api.youraiconnector.com/v1/contacts/contact123/mark-unread" \
  -H "X-API-Key: YOUR_API_KEY"

الاستجابة (200 OK):

{
  "success": true,
  "contact_id": "contact123"
}

تصدير محادثة

تمنحك عمليات التصدير محادثة كاملة كنص قابل للقراءة، بدلاً من التنقل بين صفحات الرسائل. تقبل كل نقطة نهاية للتصدير filter من نوع all (الافتراضي)، أو text، أو media، أو tool_use، بما يتطابق مع الفلتر الموجود في قائمة الرسائل.

تصدير محادثة جهة اتصال واحدة

GET /chat-exports/{contactId}

معامل الاستعلام مطلوب الوصف
format لا txt (الافتراضي) يعيد رابط تنزيل لنص عادي. json يعيد الرسائل كبيانات مهيكلة في الاستجابة.
filter لا all (الافتراضي)، أو text، أو media، أو tool_use.

cURL

curl "https://api.youraiconnector.com/v1/chat-exports/contact123?format=json" \
  -H "X-API-Key: YOUR_API_KEY"

Python

import requests

res = requests.get(
    "https://api.youraiconnector.com/v1/chat-exports/contact123",
    headers={"X-API-Key": "YOUR_API_KEY"},
    params={"format": "json"},
)
print(res.json()["data"]["messages"])

الاستجابة مع format=json (200 OK):

{
  "success": true,
  "data": {
    "contact": {
      "id": "contact123",
      "name": "Jane Doe",
      "phone": "+31612345678",
      "email": "jane@example.com"
    },
    "messages": [
      {
        "body": "Hi! I have a question about my order.",
        "direction": "inbound",
        "timestamp": "2026-06-01T09:55:00.000Z",
        "type": "text",
        "media_url": null,
        "media_content_type": null,
        "name": null,
        "args": null
      }
    ]
  }
}

مع format=txt (الافتراضي)، يكون data بدلاً من ذلك رابط تنزيل لملف النص الذي تم إنشاؤه:

{
  "success": true,
  "data": "https://storage.googleapis.com/.../chat-export-contact123-....txt"
}

رابط التنزيل قصير الأجل. قم بجلب الملف بمجرد حصولك على الرابط بدلاً من تخزينه — اطلب تصديراً جديداً عندما تحتاج إلى النص مرة أخرى.

تصدير كل المحادثات الأخيرة

GET /chat-exports/recent

تصدير محادثات جميع جهات الاتصال التي كانت نشطة في آخر X ساعة، في طلب واحد.

معلمة الاستعلام مطلوبة الوصف
hours نعم عدد ساعات النشاط التي يجب البحث فيها. يجب أن يكون رقماً صحيحاً موجباً.
format لا json (الافتراضي) يُرجع إدخالاً واحداً لكل جهة اتصال. txt يُرجع ملف نصي واحد قابل للتنزيل يحتوي على كل محادثة.
limit لا الحد الأقصى لعدد جهات الاتصال المراد تصديرها. الافتراضي 50، والحد الأقصى 100.
filter لا all (الافتراضي)، أو text، أو media، أو tool_use.

cURL

curl "https://api.youraiconnector.com/v1/chat-exports/recent?hours=24&limit=25" \
  -H "X-API-Key: YOUR_API_KEY"

الاستجابة (200 OK):

{
  "success": true,
  "data": {
    "hours_ago": 24,
    "total_contacts": 2,
    "exports": [
      {
        "contactId": "contact123",
        "contactName": "Jane Doe",
        "phoneNumber": "+31612345678",
        "email": "jane@example.com",
        "messageCount": 12,
        "chatExport": "Acme Export - Jane Doe\nPhone: +31612345678\n..."
      }
    ]
  }
}

مع format=txt تكون الاستجابة هي الملف النصي نفسه، ويتم إرساله كتنزيل بدلاً من JSON.

يقوم هذا الطلب الواحد بسحب السجل الكامل لكل جهة اتصال مطابقة، لذا اجعل hours و limit معتدلين في الحسابات المزدحمة.

إرسال نسخة من المحادثة بالبريد الإلكتروني إلى جهة الاتصال

POST /chat-exports/{contactId}/email

إرسال نسخة من محادثة جهة الاتصال الخاصة بهم عبر البريد الإلكتروني — تدفق “أرسل لي هذه الدردشة بالبريد الإلكتروني”، الذي يتم تشغيله من نظامك الخاص.

الحقل مطلوب الوصف
recipient_email لا المكان الذي سيتم الإرسال إليه. يتم تعيينه افتراضياً على عنوان البريد الإلكتروني المخزن لجهة الاتصال.
via لا auto (الافتراضي) يختار أفضل مسار، transactional يرسلها كبريد إلكتروني للنظام، email_channel يرسلها من قناة البريد الإلكتروني المتصلة بك.
note لا سطر قصير منك يظهر فوق نسخة المحادثة. حتى 1000 حرف.

cURL

curl -X POST "https://api.youraiconnector.com/v1/chat-exports/contact123/email" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "note": "Here is a copy of our chat, as promised." }'

الاستجابة (200 OK):

{
  "success": true,
  "data": {
    "via": "transactional",
    "recipientEmail": "jane@example.com",
    "messageCount": 42,
    "omittedCount": 0
  }
}

يخبرك omittedCount بعدد الرسائل الأقدم التي تم استبعادها للحفاظ على طول معقول للبريد الإلكتروني. تعني 200 أن نسخة المحادثة قد تم إنشاؤها ووضعها في قائمة الانتظار للإرسال، وليس أنها وصلت إلى صندوق الوارد بعد.


إيقاف أو استئناف الذكاء الاصطناعي لجهة اتصال واحدة

PUT /contacts/{contactId}

اضبط is_bot_active على false لإيقاف رد الذكاء الاصطناعي على جهة اتصال واحدة، وأعد ضبطه على true لإعادة المحادثة إليه. هذا هو مفتاح التحكم الذي تحتاجه عندما يتدخل شخص بشري في المحادثة: الرسائل الصادرة التي ترسلها عبر API يتم تسليمها حتى أثناء إيقاف البوت مؤقتاً.

cURL

curl -X PUT "https://api.youraiconnector.com/v1/contacts/contact123" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "is_bot_active": false }'

JavaScript

await fetch("https://api.youraiconnector.com/v1/contacts/contact123", {
  method: "PUT",
  headers: {
    "X-API-Key": "YOUR_API_KEY",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({ is_bot_active: false }),
});

Python

import requests

requests.put(
    "https://api.youraiconnector.com/v1/contacts/contact123",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={"is_bot_active": False},
)

الاستجابة

{
  "success": true,
  "contact_id": "contact123"
}

الإيقاف المؤقت كجزء من الرد

إذا كان هناك شخص بشري يتولى المحادثة عن طريق إرسال رد، يمكنك إيقاف البوت مؤقتاً في نفس الطلب بدلاً من إجراء استدعاء ثانٍ. يقبل POST /contacts/{contactId}/send-message علامتين اختياريتين:

الحقل الوصف
pauseBot true يقوم بإيقاف الذكاء الاصطناعي مؤقتاً لهذا جهة الاتصال عند إرسال الرسالة.
clearIncompleteReply true يتجاهل رد البوت غير المكتمل حتى لا يستأنف العمل بعد ذلك.
curl -X POST "https://api.youraiconnector.com/v1/contacts/contact123/send-message" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "body": "Hi, Sarah here - taking over from the assistant.",
    "pauseBot": true,
    "clearIncompleteReply": true
  }'

يتضمن الرد "botPaused": true عند تطبيق الإيقاف المؤقت.

وضع علامة على جهة اتصال كخاصة باستخدام POST /contacts/bulk-flag يؤدي أيضاً إلى إيقاف البوت مؤقتاً لها. راجع جهات الاتصال للحصول على قائمة الحقول الكاملة.


بناء صندوق الوارد الخاص بك

كل ما يحتاجه صندوق الوارد موجود في هذه الصفحة وفي جهات الاتصال:

ما تحتاجه نقطة النهاية
سرد المحادثات GET /contacts
قراءة محادثة GET /contacts/{contactId}/messages
سرد جلسات دردشة جهة اتصال GET /chat-sessions/{contactId}
معرفة ما ورد مؤخراً GET /chat-sessions/recent
قراءة جلسة دردشة واحدة GET /contacts/{contactId}/chat-sessions/{sessionId}/messages
إرسال رد يدوي POST /contacts/{contactId}/send-message
تصحيح رد أرسلته للتو POST /contacts/{contactId}/messages/{messageId}/edit
إزالة رسالة DELETE /contacts/{contactId}/messages/{messageId}
مسح عدة رسائل POST /contacts/{contactId}/messages/bulk-delete
التفاعل باستخدام رمز تعبيري POST /contacts/{contactId}/messages/{messageId}/react
تقييم أو تمييز رسالة بنجمة PATCH /contacts/{contactId}/messages/{messageId}
وضع علامة مقروء POST /contacts/{contactId}/mark-read
إعادة الدردشة إلى الفريق POST /contacts/{contactId}/mark-unread
تصدير نسخة محادثة GET /chat-exports/{contactId}
إيقاف أو استئناف الذكاء الاصطناعي PUT /contacts/{contactId} مع is_bot_active

للحصول على تحديثات مباشرة، اشترك في أحداث New Message و Replies و Human Alerted و Chat Concluded باستخدام Webhooks بدلاً من استطلاع هذه الـ API بشكل دوري.


أخطاء واجهة برمجة تطبيقات الرسائل

تُرجع نقاط نهاية الرسائل غلاف الخطأ القياسي:

{
  "success": false,
  "error": "Contact not found"
}
الحالة متى يحدث ذلك في نقطة نهاية الرسالة
400 حقل مطلوب مفقود أو معلمة غير صالحة (limit، أو hours، أو filter، أو direction، أو status سيئة، أو مصفوفة message_ids فارغة أو تتجاوز 500، أو cursor غير صالح، أو تعديل body فارغ أو طويل جداً، أو score خارج -1/0/1، أو رمز تعبيري بمسافات أو يتجاوز 16 حرفاً). يتم إرجاعها أيضاً عندما لا يمكن تعديل الرسالة على الإطلاق — تم حذفها، أو لا تحتوي قناتها على تعديل، أو تجاوزت نافذة التعديل الخاصة بتلك القناة.
404 لم يتم العثور على جهة الاتصال، أو جلسة الدردشة، أو أحد معرفات الرسائل المقدمة.
409 لن تقبل القناة التغيير في الوقت الحالي. لم يتم كتابة أي شيء: عند التعديل، يوضح edit_reason السبب؛ عند التفاعل، كانت القناة غير قابلة للوصول مؤقتاً وقد تنجح إعادة المحاولة.
422 لا يمكن لجهة الاتصال تلقي رسائل صادرة (عدم الإزعاج، أو خاصة، أو قناة غير مدعومة)، أو لا يمكن تسليم تفاعل في هذه المحادثة أبداً (يوضح reaction_reason السبب).

الرموز المشتركة التي يمكن أن تُرجعها كل نقطة نهاية — 401، و 403 (خطتك لا تتضمن الوصول إلى واجهة برمجة التطبيقات)، و 429 (حد المعدل)، و 500 — مدرجة مع إرشادات إعادة المحاولة في الأخطاء والترقيم.


الخطوات التالية