C cenaly.com
شروع رایگان

رابط‌های API و MCP سانترال تلفنی اختصاصی (PBX)

کلیدها و دسترسی‌ها، REST API‌، سرور MCP برای Claude و Cursor‌، اتصال ChatGPT و claude.ai از طریق OAuth بدون کلید، نمونه‌ها، محدودیت‌ها و خطاها

12 min read دموی پنل مدیریت
On this page 10

API و MCP برای مرکز تلفن اختصاصی شما

مرکز تلفن اختصاصی Cenaly برای برنامه‌ها و دستیارهای هوش مصنوعی شما باز است:

  • CRM، سیستم حسابداری، وب‌سایت شما — REST API: گزارش تماس‌ها، ضبط و پیاده‌سازی گفتار، تماس با یک کلیک، داخلی‌ها، انتقال تماس، قواعد تماس؛
  • Claude Code، Claude Desktop، Cursor — سرور MCP راه دور با کلید؛
  • ChatGPT، claude.ai، Perplexity، Cursor و VS Code — همان سرور MCP بدون کلید: وارد حساب خود می‌شوید و دسترسی را مجاز می‌کنید (OAuth).

همه‌چیز به نام مالک حساب و فقط با مجوزهایی کار می‌کند که او اعطا کرده است. هر تغییر در گزارش اقدامات مرکز تلفن با نام کلید یا برنامه قابل مشاهده است.

آدرس‌ها#

مورد آدرس
REST API https://api.cenaly.com/pbx-api/v1
سرور MCP (streamable HTTP) https://api.cenaly.com/pbx-api/mcp
مستندات متدها api.cenaly.com/pbx-api/v1/docs
توصیف OpenAPI 3.1 api.cenaly.com/pbx-api/v1/openapi.json
فراداده OAuth https://api.cenaly.com/.well-known/oauth-authorization-server/pbx-api

کلید و مجوزها#

کلید را فقط مالک حساب ایجاد می‌کند: تلفنی → API و MCP → کلیدها → ایجاد کلید. کارمندی با نقش «مدیر مرکز تلفن» کلیدها را نمی‌بیند — کلید به نام مالک عمل می‌کند.

  • کلید با قالب cpx_… فقط یک بار نمایش داده می‌شود — بلافاصله پس از ایجاد، همراه با قطعه‌کدهای آماده برای اتصال. نزد ما فقط اثر انگشت آن (SHA-256) نگهداری می‌شود؛ بازیابی کلید ممکن نیست — فقط می‌توان کلید جدید صادر کرد.
  • کلید را می‌توان به شعبه‌ها محدود کرد (در غیر این صورت — همه شعبه‌ها، از جمله شعبه‌های آینده) و به مدت (۳۰، ۹۰، ۳۶۵ روز یا بدون انقضا).
  • «مجوزها» مجوزها و شعبه‌های کلید را در لحظه تغییر می‌دهند: یکپارچه‌سازی به کار خود ادامه می‌دهد و مجوزهای جدید از درخواست بعدی اعمال می‌شوند.
  • «لغو» — فوری و برای همیشه: درخواست بعدی با این کلید 401 دریافت می‌کند.
  • کلیدها و اتصال‌های فعال — حداکثر ۲۰ در هر حساب.

مجوزها با مجموعه‌های آماده یا با تیک انتخاب می‌شوند:

مجوز چه می‌دهد مجموعه‌ها
calls:read گزارش تماس‌ها و کارت تماس با مسیر CRM، دستیار هوش مصنوعی، فقط خواندن، همه
recordings:read پیوند به ضبط گفتگو (۱۰ دقیقه) و پیاده‌سازی گفتار CRM، دستیار هوش مصنوعی، فقط خواندن، همه
calls:dial تماس با یک کلیک: ابتدا تلفن کارمند زنگ می‌خورد، پس از پاسخ مرکز تلفن شماره را می‌گیرد CRM، دستیار هوش مصنوعی، همه
extensions:read داخلی‌ها، گروه‌ها، انتقال تماس، «مزاحم نشوید» CRM، دستیار هوش مصنوعی، فقط خواندن، همه
extensions:write تغییر انتقال تماس شخصی و «مزاحم نشوید» دستیار هوش مصنوعی، همه
presence:read چه کسی آزاد است، در حال تماس است، در حال گفتگو است دستیار هوش مصنوعی، فقط خواندن، همه
reports:read شاخص‌های مرکز تماس در یک دوره: سطح خدمات، انتظار، تماس‌های رهاشده، AHT، FCR، CSAT، کجا تماس‌ها را از دست می‌دهیم، تفکیک بر اساس صف‌ها، خطوط، کارمندان فقط خواندن، همه
routes:read شماره‌ها، قواعد تماس‌های ورودی و خروجی، تاریخچه قواعد فقط خواندن، همه
routes:write ایجاد، تغییر، حذف و جابه‌جایی قواعد تماس، بازگردانی از تاریخچه فقط با تیک جداگانه
config:export خروجی تنظیمات مرکز تلفن در قالب فایل فقط با تیک جداگانه
config:import بارگذاری تنظیمات از جدول‌ها: پیش‌نمایش، سپس اعمال فقط با تیک جداگانه
webhooks:write ایجاد، تغییر، بررسی و حذف وب‌هوک‌های رویدادهای تماس فقط با تیک جداگانه
daynight:write بستن شعبه تا پایان شبانه‌روز یا تا یک تاریخ، باز کردن — همان *28 از تلفن فقط با تیک جداگانه

مجوزهایی که چیزی را تغییر می‌دهند یا دقیقه مصرف می‌کنند، در پنجره با رنگ کهربایی مشخص شده‌اند. سه مجوز آخر در هیچ مجموعه‌ای، حتی در «همه»، قرار ندارند — آن‌ها را فقط می‌توان آگاهانه و با تیک جداگانه اعطا کرد.

ChatGPT، claude.ai، Perplexity، Cursor، VS Code: اتصال بدون کلید#

دستیارهای ابری نمی‌توانند کلید را در سرصفحه قرار دهند — آن‌ها سرور MCP را از طریق OAuth متصل می‌کنند. نیازی به ایجاد کلید نیست.

claude.ai: تنظیمات → اتصال‌دهنده‌ها → افزودن اتصال‌دهنده خود → https://api.cenaly.com/pbx-api/mcp را وارد کنید → اتصال.

ChatGPT: تنظیمات → برنامه‌ها و اتصال‌دهنده‌ها → پیشرفته → حالت توسعه‌دهنده را فعال کنید → ایجاد → https://api.cenaly.com/pbx-api/mcp را وارد کنید، احراز هویت — OAuth.

Perplexity: تنظیمات حساب → اتصال‌دهنده‌ها → «+ اتصال‌دهنده خود» → راه دور → https://api.cenaly.com/pbx-api/mcp را وارد کنید، احراز هویت — OAuth.

Cursor و VS Code: سرور MCP راه دور (HTTP) را با آدرس https://api.cenaly.com/pbx-api/mcp و بدون سرصفحه کلید اضافه کنید — پنجره ورود در مرورگر باز می‌شود. در Cursor: .cursor/mcp.json → {"mcpServers": {"cenaly-pbx": {"url": "https://api.cenaly.com/pbx-api/mcp"}}}؛ در VS Code: فرمان «MCP: Add Server» → HTTP.

سپس دستیار پنجره ورود Cenaly را باز می‌کند. پس از ورود خواهید دید:

  • چه کسی درخواست دسترسی می‌کند — برنامه با آدرسی که پاسخ به آن بازمی‌گردد نام‌گذاری می‌شود: «اتصال‌دهنده تأییدشده · chatgpt.com» (به همین ترتیب — claude.ai، perplexity.ai، vscode.dev، Cursor)، «برنامه روی این رایانه» یا هشدار «آدرس ناشناس». نامی که برنامه فرستاده، ریز نمایش داده می‌شود — هر کسی می‌تواند آن را بنویسد؛
  • مجوزها — آنچه برنامه درخواست می‌کند علامت‌گذاری شده است (اگر «همه‌چیز» را درخواست کند، مجموعه «دستیار هوش مصنوعی» علامت‌گذاری می‌شود)؛ مجوزهای «فقط با تیک جداگانه» هرگز از پیش علامت‌گذاری نمی‌شوند؛
  • شعبه‌ها — همه یا انتخاب‌شده‌ها.

«مجاز کردن» شما را به دستیار بازمی‌گرداند و او بلافاصله ابزارهای مرکز تلفن را می‌بیند. اتصال در تلفنی → API و MCP → کلیدها با برچسب OAuth و آدرس برنامه ظاهر می‌شود — همان‌جا مجوزها تغییر می‌کنند و دسترسی لغو می‌شود. اتصال مجدد همان برنامه مجوزهای آن را به‌روزرسانی می‌کند، نه اینکه اتصال دومی ایجاد کند.

فقط مالک حساب می‌تواند اتصال‌ها را مجاز کند.

Claude Code، Claude Desktop، Cursor: اتصال با کلید#

Claude Code — با یک فرمان:

claude mcp add --transport http telephony https://api.cenaly.com/pbx-api/mcp --header "Authorization: Bearer cpx_…"

Claude Desktop، Cursor (.cursor/mcp.json) و سایر کلاینت‌ها با فایل تنظیمات:

{
  "mcpServers": {
    "telephony": {
      "type": "http",
      "url": "https://api.cenaly.com/pbx-api/mcp",
      "headers": { "Authorization": "Bearer cpx_…" }
    }
  }
}

قطعه‌های آماده با کلید شما بلافاصله پس از ساخت کلید نمایش داده می‌شوند. دستیار هوش مصنوعی فقط ابزارهایی را می‌بیند که کلید مجاز کرده است و می‌تواند به «چه کسی امروز زنگ زد و تماس برقرار نشد»، «با تلفن آنا به این مهمان پس‌تماس بگیر»، «برای من انتقال تماس به موبایل را روشن کن» پاسخ دهد.

REST API#

کلید — در سرآیند Authorization: Bearer <ключ> (یا X-Api-Key). اگر کلید یک شعبه داشته باشد، می‌توان پارامتر location را نفرستاد؛ اگر چند شعبه داشته باشد، پاسخ 400 location_required آن‌ها را فهرست می‌کند.

روش مسیر دسترسی کارکرد
GET /v1/me — دسترسی‌ها، شعبه‌ها و محدودیت‌های کلید
GET /v1/locations — شعبه‌های کلید و مرکز تلفن آن‌ها
GET /v1/calls calls:read دفترچه تماس‌ها: since، until، direction، status (answered، missed، ai)، number، extension، limit تا 100، cursor
GET /v1/calls/{id} calls:read تماس با مسیر: کدام قاعده اجرا شد، تلفن چه کسی زنگ خورد، چه کسی پاسخ داد
GET /v1/calls/{id}/recording recordings:read پیوند ضبط به مدت 10 دقیقه
GET /v1/calls/{id}/transcript recordings:read پیاده‌سازی متن و خلاصه گفتگو
POST /v1/dial calls:dial تماس با یک کلیک: { "extension": "101", "number": "+995555123456" }
GET /v1/dial/{commandId} calls:dial وضعیت تماس با یک کلیک
GET /v1/extensions extensions:read داخلی‌ها، گروه‌ها، انتقال تماس، «مزاحم نشوید»
PUT /v1/extensions/{ext}/forwarding extensions:write انتقال تماس شخصی داخلی
PUT /v1/extensions/{ext}/dnd extensions:write «مزاحم نشوید»: { "on": true }
GET /v1/presence presence:read چه کسی همین حالا آزاد است
GET /v1/metrics reports:read شاخص‌های مرکز تماس برای یک دوره: from، to (تاریخ‌های محلی شعبه YYYY-MM-DD، پیش‌فرض — 7 روز گذشته)، compare (prev، year، prev,year یا خالی)، sections (metrics,loss,queues,lines,operators,directions,heatmap,daily)، callbacks=true — و همچنین سرعت پس‌تماس
GET /v1/routes routes:read شماره‌ها، قواعد تماس ورودی و خروجی
GET /v1/routes/history routes:read تاریخچه تغییرات قواعد
POST، PUT، DELETE /v1/routes/inbound…، /v1/routes/outbound… routes:write قواعد تماس یکی‌یکی: ساخت، تغییر فیلدهای ارسالی، حذف، جابه‌جایی، بازگردانی
GET، POST /v1/config/export، /v1/config/import config:export، config:import تنظیمات در قالب فایل؛ بارگذاری — پیش‌نمایش، سپس اعمال
GET /v1/events calls:read رویدادهای تماس شعبه در 7 روز (تا 2000): since (شناسه رویداد یا زمان)، types، limit (تا 500 در هر پاسخ)
GET، POST، PATCH، DELETE /v1/webhooks… webhooks:write وبهوک‌ها: فهرست، ساخت، تغییر، حذف؛ …/rotate-secret، …/test، …/deliveries
GET، PUT /v1/open-closed routes:read، daynight:write بسته است یا نه و تا چه زمانی؛ بستن تا پایان شبانه‌روز { "closed": true }، تا تاریخ { "closed": true, "until": "2026-10-05T09:00" } یا باز کردن

توضیح کامل فیلدها — در صفحه مستندات و در OpenAPI.

چه کسی امروز زنگ زد و تماس برقرار نشد:

curl -H "Authorization: Bearer cpx_…" \
  "https://api.cenaly.com/pbx-api/v1/calls?status=missed&since=$(date -u +%Y-%m-%dT00:00:00Z)"

پس‌تماس با مشتری از تلفن داخلی 101:

curl -X POST -H "Authorization: Bearer cpx_…" -H "Content-Type: application/json" \
  -d '{"extension":"101","number":"+995555123456"}' "https://api.cenaly.com/pbx-api/v1/dial"

شاخص‌های سپتامبر با مقایسه با اوت و سپتامبر سال گذشته — برای پنل BI خودتان:

curl -H "Authorization: Bearer cpx_…" \
  "https://api.cenaly.com/pbx-api/v1/metrics?from=2026-09-01&to=2026-09-30&compare=prev,year"

در پاسخ metrics — همان اعدادی که در صفحه مخابرات → دفترچه تماس‌ها → تحلیلات دیده می‌شود: تماس‌های ورودی، پاسخ‌داده‌شده و ازدست‌رفته، سطح سرویس (آستانه و هدف — از تنظیمات صف)، میانگین و حداکثر انتظار، سهم رهاشده‌های بدون تماس کوتاه، AHT، FCR، سهم انتقال‌ها و ربات، CSAT. compare.prev و compare.year — همان فیلدها برای دوره گذشته و همان دوره یک سال پیش. مقایسه با سال گذشته برای دوره‌های تا 400 روز محاسبه می‌شود.

روشن کردن انتقال تماس به موبایل، اگر کارمند در 15 ثانیه پاسخ نداد:

curl -X PUT -H "Authorization: Bearer cpx_…" -H "Content-Type: application/json" \
  -d '{"forward":{"noAnswer":{"kind":"number","number":"+995599000111"},"noAnswerSec":15}}' \
  "https://api.cenaly.com/pbx-api/v1/extensions/101/forwarding"

ابزارهای MCP#

همان عملیات‌هایی که در REST وجود دارد. کلاینت فقط ابزارهایی را می‌بیند که با کلید یا اتصال مجاز شده‌اند:

ابزارها دسترسی
list_locations —
list_calls, get_call calls:read
get_call_recording, get_call_transcript recordings:read
call_number, get_dial_status calls:dial
list_extensions extensions:read
set_forwarding, set_do_not_disturb extensions:write
get_presence presence:read
get_call_metrics reports:read
list_routes, list_route_history routes:read
save_inbound_rule, delete_inbound_rule, move_inbound_rule, save_outbound_rule, delete_outbound_rule, move_outbound_rule, set_outbound_calls, restore_route_version routes:write
export_config config:export
import_config config:import
get_call_events calls:read
list_webhooks, save_webhook, delete_webhook, rotate_webhook_secret, test_webhook, list_webhook_deliveries webhooks:write
get_open_closed routes:read
set_open_closed daynight:write

سرور بدون نشست کار می‌کند (streamable HTTP، JSON-RPC 2.0): initialize، tools/list، tools/call.

OAuth برای توسعه‌دهندگان کانکتورهای خودشان#

سرور مجوزدهی از مشخصات مجوزدهی MCP پیروی می‌کند — هر کلاینتی که از آن پشتیبانی کند مناسب است:

  1. درخواست به MCP بدون توکن، 401 با هدر WWW-Authenticate: Bearer resource_metadata="https://api.cenaly.com/.well-known/oauth-protected-resource/pbx-api/mcp" دریافت می‌کند.
  2. فراداده‌های منبع (RFC 9728) سرور مجوزدهی را معرفی می‌کنند — https://api.cenaly.com/pbx-api؛ فراداده‌های آن (RFC 8414) در نشانی https://api.cenaly.com/.well-known/oauth-authorization-server/pbx-api (و …/pbx-api/.well-known/openid-configuration) قرار دارد.
  3. ثبت پویا کلاینت (RFC 7591): POST /pbx-api/oauth/register. نشانی بازگشت فقط localhost / 127.0.0.1 (هر پورتی) یا نشانی یک کانکتور شناخته‌شده است (claude.ai، claude.com، chatgpt.com، chat.openai.com، vscode.dev، www.perplexity.ai، enterprise.perplexity.ai؛ برای Cursor نیز دقیقاً cursor://anysphere.cursor-mcp/oauth/callback). روش ورود کلاینت — none (کلاینت عمومی)، client_secret_post یا client_secret_basic.
  4. کد مجوزدهی با PKCE (فقط S256): GET /pbx-api/oauth/authorize → پنجره ورود و رضایت مالک → بازگشت به نشانی شما با code، state و iss. پارامتر resource — نشانی سرور MCP است.
  5. توکن‌ها: POST /pbx-api/oauth/token. کد یک‌بارمصرف است و ۲ دقیقه اعتبار دارد (code_verifier نادرست آن را باطل می‌کند)؛ توکن دسترسی — ۱ ساعت؛ توکن تازه‌سازی — ۹۰ روز، با هر تازه‌سازی توکن جدید صادر می‌شود و توکن قبلی از کار می‌افتد.
  6. لغو: POST /pbx-api/oauth/revoke (RFC 7009) اتصال را به‌طور کامل باطل می‌کند — مانند «لغو» در پنجره «API و MCP».

توکن دسترسی همه‌جا که کلید پذیرفته می‌شود پذیرفته می‌شود: هم در MCP و هم در REST، با همان دسترسی‌ها و شعبه‌هایی که مالک مجاز کرده است.

محدودیت‌ها و خطاها#

  • برای هر کلید یا اتصال: ۱۲۰ درخواست در دقیقه و ۲۰ ۰۰۰ در شبانه‌روز (REST و MCP با هم).
  • تماس با یک کلیک — جداگانه: ۱۰ در دقیقه و ۳۰۰ در شبانه‌روز.
  • ژورنال — تا ۱۰۰ تماس در هر درخواست؛ در ژورنال مرکز تلفن، شعبه — آخرین ۴۰۰ تماس در ۹۰ روز.
کد خطا چه باید کرد
401 api_key_missing، api_key_invalid کلید وجود ندارد، لغو شده یا منقضی شده است؛ توکن OAuth منقضی شده — آن را تازه کنید
403 scope_required کلید آن دسترسی را ندارد — آن را در «دسترسی‌ها» اضافه کنید
400 location_required کلید چند شعبه دارد — location را ارسال کنید
404 location_not_found شعبه وجود ندارد یا کلید به شعبه‌های دیگری محدود شده است
429 rate_limited محدودیت تمام شده، پس از Retry-After ثانیه دوباره تلاش کنید

رویدادهای تماس#

در زمان واقعی — وب‌هوک‌های مرکز تلفن: تلفنی → API و MCP → وب‌هوک‌ها یا POST /v1/webhooks با کلیدی که مجوز webhooks:write دارد. روی نشانی https شما در عرض چند ثانیه برای هر رویداد یک POST می‌آید: call.started (آغاز شد: جهت، چه کسی، به کجا، خط)، call.ringing (زنگ خوردن برای چه کسی — یکی برای هر تلفن)، call.answered (چه کسی پاسخ داد)، call.transferred (چه کسی و به چه کسی انتقال داد)، call.ended (نتیجه، مدت، گفتگو، چه کسی پاسخ داد). وب‌هوک را می‌توان به شعبه‌ها و انواع رویداد محدود کرد.

{ "id": "1727771234.56:2", "type": "call.answered", "createdAt": "2026-10-01T10:00:05Z",
  "locationId": "…", "webhookId": "wh_…", "attempt": 1,
  "data": { "callId": "1727771234.56", "seq": 2, "direction": "inbound",
            "from": { "number": "+995555123456" }, "party": { "extension": "101", "name": "Анна" } } }

امضا — سرآیند X-Cenaly-Signature: t=<زمان unix>,v1=<HMAC-SHA256 از "t.بدنه" با رمز وب‌هوک>. دوباره محاسبه کنید، در زمان ثابت مقایسه کنید و t قدیمی‌تر از 5 دقیقه را رد کنید. رمز whsec_… فقط یک بار نشان داده می‌شود؛ «رمز جدید» رمز پیشین را بی‌درنگ باطل می‌کند.

تحویل — ظرف 10 ثانیه با 2xx پاسخ دهید. در غیر این صورت با فاصله‌های 10 ثانیه، 30 ثانیه، 2، 5، 10، 15 و 15 دقیقه دوباره می‌فرستیم (8 تلاش، حدود یک ساعت)؛ ارسال دوباره همان id را دارد — با آن موارد تکراری را کنار بگذارید. گزارش تحویل‌ها (کد پاسخ، زمان، تلاش) در پنجره وب‌هوک و GET /v1/webhooks/{id}/deliveries است؛ «بررسی» یک webhook.ping خدماتی می‌فرستد. اگر نشانی 3 شبانه‌روز پیاپی هیچ تحویلی را نپذیرد، وب‌هوک خودش خاموش می‌شود: برای مالک ایمیل می‌آید، در پنجره «وب‌هوک‌ها» نشان «به‌طور خودکار خاموش شد» و دکمه «روشن کردن» ظاهر می‌شود (یا PATCH /v1/webhooks/{id} با { "enabled": true }).

بدون سرور خودتان — همان جریان با نظرسنجی: GET /v1/events?since=<id آخرین رویداد> یا ابزار MCP با نام get_call_events (رویدادهای شعبه در 7 روز گذشته، تا 2000؛ در هر پاسخ تا 500، more: true — با همان since جلوتر بروید).

پس از پردازش ضبط — تماس همراه با رونویسی و تحلیل از طریق وب‌هوک منبع «وب‌هوک» در بخش «تماس‌ها» می‌آید.

«باز / بسته» — PUT /v1/open-closed با { "closed": true } شعبه را تا پایان شبانه‌روز می‌بندد (مانند *28 از تلفن: تماس‌ها با قواعد «خارج از ساعت کاری» انجام می‌شوند)، false آن را باز می‌کند؛ GET نشان می‌دهد آیا بسته است و توسط چه کسی. با "until" — تا آن لحظه بسته است (نه بیشتر از 30 روز)، سپس خودش باز می‌شود: زمان بدون جابه‌جایی (2026-10-05T09:00) در منطقه زمانی شعبه خوانده می‌شود؛ false آن را هم برمی‌دارد. تیک «بستن با کد *28» در مسیریابی باید فعال باشد (در غیر این صورت 409).

امنیت#

  • کلید یک بار نشان داده می‌شود و نزد ما فقط به‌صورت اثر انگشت نگهداری می‌شود؛ کلید افشاشده با یک دکمه باطل می‌شود.
  • اتصال OAuth را فقط مالک می‌تواند مجاز کند، و مشخص است که دسترسی به کدام نشانی داده می‌شود؛ اتصال مجاز را می‌توان به مجوزها و شعبه‌ها محدود کرد و هر لحظه لغو کرد.
  • شماره‌های تلفن داده‌های شخصی مشتریان شما هستند: مجوز دسترسی به گزارش و ضبط‌ها را فقط به یکپارچه‌سازی‌هایی بدهید که واقعاً به آن نیاز دارند.
  • همه تغییرات از طریق کلید یا اتصال در گزارش اقدامات مرکز تلفن با نام کلید یا برنامه ثبت می‌شود.
Was this article helpful?