الانتقال إلى المحتوى الرئيسي

المقدمة

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

البدء

1

Open the Webhook Section

انتقل إلى قسم Webhook في لوحة تحكم Dodo Payments الخاصة بك. انقر فوق زر + Add Endpoint، ثم افتح القائمة المنسدلة للويب هوك لعرض التكاملات الأخرى.
لوحة تحكم Dodo Payments تظهر زر إضافة نقطة نهاية وقائمة التكاملات
2

Select Slack Integration

اختر تكامل Slack وانقر فوق Connect your Slack workspace.
بطاقة تكامل Slack وزر الاتصال
3

Grant Slack Permissions

امنح الأذونات اللازمة لتطبيق Incoming Webhooks في Slack حتى يتمكن من نشر الرسائل في القناة التي اخترتها.
شاشة أذونات OAuth لـ Slack لتطبيق Incoming Webhooks
4

Customize Transformation Code

أضف أو حرّر شفرة التحويل لتخصيص إشعارات Slack لحالتك. يمكنك استخدام القوالب الجاهزة أو كتابة المنطق الخاص بك.
محرر شفرة التحويل لتكامل Slack
5

Test and Create

اختبر شفرة التحويل باستخدام بيانات حدث مخصصة أو جاهزة. بمجرد أن ترضى عن النتيجة، انقر Create لتفعيل التكامل.
اختبر التحويل وزر الإنشاء
6

Integration Complete!

🎉 لقد أنشأت تكامل Slack بنجاح! سيتم الآن تسليم أحداث Dodo Payments إلى القناة المحددة في Slack في الوقت الفعلي.

أمثلة على كود التحويل

إشعارات المدفوعات الأساسية

هذا التحويل يرسل رسائل نصية بسيطة لأحداث المدفوعات:
payment_notifs.js
function handler(webhook) {
  switch (webhook.eventType) {
    case "payment.succeeded":
      webhook.payload = {
        text: `✅ Payment Successful\nAmount: $${(webhook.payload.data.total_amount / 100).toFixed(2)}\nCustomer: ${webhook.payload.data.customer.email}\nPayment ID: ${webhook.payload.data.payment_id}`
      };
      break;
      
    case "payment.failed":
      webhook.payload = {
        text: `❌ Payment Failed\nAmount: $${(webhook.payload.data.total_amount / 100).toFixed(2)}\nCustomer: ${webhook.payload.data.customer.email}\nReason: ${webhook.payload.data.error_message || 'Unknown'}`
      };
      break;
      
    case "payment.processing":
      webhook.payload = {
        text: `⏳ Payment Processing\nAmount: $${(webhook.payload.data.total_amount / 100).toFixed(2)}\nCustomer: ${webhook.payload.data.customer.email}`
      };
      break;
  }

  return webhook;
}

إشعارات الاشتراك الغنية

هذا التحويل ينشئ رسائل Slack غنية مع مرفقات لأحداث الاشتراك:
subscription_notifs.js
function handler(webhook) {
  switch (webhook.eventType) {
    case "subscription.active":
      webhook.payload = {
        attachments: [{
          color: "good",
          title: "🎉 Subscription Activated",
          fields: [
            {
              title: "Customer",
              value: webhook.payload.data.customer.email,
              short: true
            },
            {
              title: "Product ID",
              value: webhook.payload.data.product_id,
              short: true
            },
            {
              title: "Amount",
              value: `$${(webhook.payload.data.recurring_pre_tax_amount / 100).toFixed(2)}/${webhook.payload.data.payment_frequency_interval}`,
              short: true
            },
            {
              title: "Next Billing",
              value: new Date(webhook.payload.data.next_billing_date).toLocaleDateString(),
              short: true
            }
          ],
          footer: "Dodo Payments",
          ts: Math.floor(new Date(webhook.payload.timestamp).getTime() / 1000)
        }]
      };
      break;
      
    case "subscription.cancelled":
      webhook.payload = {
        attachments: [{
          color: "warning",
          title: "⚠️ Subscription Cancelled",
          fields: [
            {
              title: "Customer",
              value: webhook.payload.data.customer.email,
              short: true
            },
            {
              title: "Product ID",
              value: webhook.payload.data.product_id,
              short: true
            },
            {
              title: "Cancellation Date",
              value: new Date(webhook.payload.data.cancelled_at).toLocaleDateString(),
              short: true
            },
            {
              title: "Cancel at Next Billing",
              value: webhook.payload.data.cancel_at_next_billing_date ? "Yes" : "No",
              short: true
            }
          ],
          footer: "Dodo Payments",
          ts: Math.floor(new Date(webhook.payload.timestamp).getTime() / 1000)
        }]
      };
      break;
      
    case "subscription.renewed":
      webhook.payload = {
        attachments: [{
          color: "good",
          title: "🔄 Subscription Renewed",
          fields: [
            {
              title: "Customer",
              value: webhook.payload.data.customer.email,
              short: true
            },
            {
              title: "Product ID",
              value: webhook.payload.data.product_id,
              short: true
            },
            {
              title: "Amount",
              value: `$${(webhook.payload.data.recurring_pre_tax_amount / 100).toFixed(2)}`,
              short: true
            },
            {
              title: "Next Billing",
              value: new Date(webhook.payload.data.next_billing_date).toLocaleDateString(),
              short: true
            }
          ],
          footer: "Dodo Payments",
          ts: Math.floor(new Date(webhook.payload.timestamp).getTime() / 1000)
        }]
      };
      break;
  }

  return webhook;
}

إشعارات إدارة النزاعات

هذا التحويل يتعامل مع أحداث النزاع بألوان ملائمة وأهمية:
dispute_notifs.js
function handler(webhook) {
  switch (webhook.eventType) {
    case "dispute.opened":
      webhook.payload = {
        attachments: [{
          color: "danger",
          title: "🚨 New Dispute Opened",
          fields: [
            {
              title: "Payment ID",
              value: webhook.payload.data.payment_id,
              short: true
            },
            {
              title: "Amount",
              value: `$${(webhook.payload.data.amount / 100).toFixed(2)}`,
              short: true
            },
            {
              title: "Status",
              value: webhook.payload.data.dispute_status,
              short: true
            },
            {
              title: "Stage",
              value: webhook.payload.data.dispute_stage,
              short: true
            },
            {
              title: "Remarks",
              value: webhook.payload.data.remarks || "No remarks",
              short: false
            }
          ],
          footer: "Dodo Payments - Action Required",
          ts: Math.floor(new Date(webhook.payload.timestamp).getTime() / 1000)
        }]
      };
      break;
      
    case "dispute.won":
      webhook.payload = {
        attachments: [{
          color: "good",
          title: "✅ Dispute Won",
          fields: [
            {
              title: "Payment ID",
              value: webhook.payload.data.payment_id,
              short: true
            },
            {
              title: "Amount",
              value: `$${(webhook.payload.data.amount / 100).toFixed(2)}`,
              short: true
            },
            {
              title: "Status",
              value: webhook.payload.data.dispute_status,
              short: true
            },
            {
              title: "Resolution",
              value: "Dispute resolved in your favor",
              short: false
            }
          ],
          footer: "Dodo Payments",
          ts: Math.floor(new Date(webhook.payload.timestamp).getTime() / 1000)
        }]
      };
      break;
      
    case "dispute.lost":
      webhook.payload = {
        attachments: [{
          color: "danger",
          title: "❌ Dispute Lost",
          fields: [
            {
              title: "Payment ID",
              value: webhook.payload.data.payment_id,
              short: true
            },
            {
              title: "Amount",
              value: `$${(webhook.payload.data.amount / 100).toFixed(2)}`,
              short: true
            },
            {
              title: "Status",
              value: webhook.payload.data.dispute_status,
              short: true
            },
            {
              title: "Impact",
              value: "Funds will be debited from your account",
              short: false
            }
          ],
          footer: "Dodo Payments - Review Required",
          ts: Math.floor(new Date(webhook.payload.timestamp).getTime() / 1000)
        }]
      };
      break;
  }

  return webhook;
}

معالج شامل لجميع الأحداث

هذا التحويل يتعامل مع جميع أنواع الأحداث بتنسيق متسق:
all_events_notifs.js
function handler(webhook) {
  const event = webhook.payload.data;
  const timestamp = new Date(webhook.payload.timestamp).toLocaleString();
  
  let color, emoji, title, fields = [];
  
  switch (webhook.eventType) {
    case "payment.succeeded":
      color = "good";
      emoji = "✅";
      title = "Payment Successful";
      fields = [
        { title: "Amount", value: `$${(event.total_amount / 100).toFixed(2)}`, short: true },
        { title: "Customer", value: event.customer.email, short: true },
        { title: "Payment ID", value: event.payment_id, short: true },
        { title: "Method", value: event.payment_method || "Unknown", short: true }
      ];
      break;
      
    case "payment.failed":
      color = "danger";
      emoji = "❌";
      title = "Payment Failed";
      fields = [
        { title: "Amount", value: `$${(event.total_amount / 100).toFixed(2)}`, short: true },
        { title: "Customer", value: event.customer.email, short: true },
        { title: "Reason", value: event.error_message || "Unknown", short: false }
      ];
      break;
      
    case "subscription.active":
      color = "good";
      emoji = "🎉";
      title = "Subscription Activated";
      fields = [
        { title: "Customer", value: event.customer.email, short: true },
        { title: "Product ID", value: event.product_id, short: true },
        { title: "Amount", value: `$${(event.recurring_pre_tax_amount / 100).toFixed(2)}/${event.payment_frequency_interval}`, short: true },
        { title: "Next Billing", value: new Date(event.next_billing_date).toLocaleDateString(), short: true }
      ];
      break;
      
    case "subscription.cancelled":
      color = "warning";
      emoji = "⚠️";
      title = "Subscription Cancelled";
      fields = [
        { title: "Customer", value: event.customer.email, short: true },
        { title: "Product ID", value: event.product_id, short: true },
        { title: "Cancellation Date", value: new Date(event.cancelled_at).toLocaleDateString(), short: true },
        { title: "Cancel at Next Billing", value: event.cancel_at_next_billing_date ? "Yes" : "No", short: true }
      ];
      break;
      
    case "refund.succeeded":
      color = "good";
      emoji = "💰";
      title = "Refund Processed";
      fields = [
        { title: "Amount", value: `$${(event.amount / 100).toFixed(2)}`, short: true },
        { title: "Refund ID", value: event.refund_id, short: true },
        { title: "Payment ID", value: event.payment_id, short: true },
        { title: "Reason", value: event.reason || "Not specified", short: true }
      ];
      break;
      
    case "dispute.opened":
      color = "danger";
      emoji = "🚨";
      title = "New Dispute Opened";
      fields = [
        { title: "Payment ID", value: event.payment_id, short: true },
        { title: "Amount", value: `$${(event.amount / 100).toFixed(2)}`, short: true },
        { title: "Status", value: event.dispute_status, short: true },
        { title: "Stage", value: event.dispute_stage, short: true },
        { title: "Remarks", value: event.remarks || "No remarks", short: false }
      ];
      break;
      
    case "license_key.created":
      color = "good";
      emoji = "🔑";
      title = "License Key Created";
      fields = [
        { title: "License ID", value: event.id, short: true },
        { title: "Product ID", value: event.product_id, short: true },
        { title: "License Key", value: event.key.substring(0, 8) + "...", short: true },
        { title: "Expires", value: event.expires_at ? new Date(event.expires_at).toLocaleDateString() : "Never", short: true }
      ];
      break;
      
    default:
      // Handle any other events with a generic format
      color = "warning";
      emoji = "ℹ️";
      title = webhook.eventType.replace(/_/g, ' ').replace(/\b\w/g, l => l.toUpperCase());
      fields = [
        { title: "Event Type", value: webhook.eventType, short: true },
        { title: "Timestamp", value: timestamp, short: true }
      ];
  }
  
  webhook.payload = {
    attachments: [{
      color: color,
      title: `${emoji} ${title}`,
      fields: fields,
      footer: "Dodo Payments",
      ts: Math.floor(new Date(webhook.payload.timestamp).getTime() / 1000)
    }]
  };

  return webhook;
}

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

لجعل إشعارات Slack فعّالة:
  • استخدم مرفقات رسائل غنية مع ألوان وحقول وتنسيقات لزيادة الوضوح وسهولة اتخاذ الإجراءات.
  • تضمّن دومًا البيانات الرئيسية مثل المبالغ ورسائل العملاء والمعرّفات للتعرف السريع.
  • اختر الألوان التي تتناسب مع نوع الحدث: الأخضر (good) للنجاح، الأحمر (danger) للخصومات أو الأخطاء، الأصفر (warning) للإلغاءات، والأزرق (#36a64f) للأحداث الإعلامية.
  • أضف الطوابع الزمنية لتتبع وقت كل حدث.
تعامل مع البيانات الحساسة: احرص على عدم تضمين معلومات حساسة مثل مفاتيح الترخيص الكاملة أو البيانات الشخصية في رسائل Slack. فكّر في اقتطاع القيم الحساسة أو إخفائها.

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

  • تحقق من أن عنوان URL لويب هوك Slack صحيح ونشط
  • تأكد من أن شفرة التحويل هي JavaScript صالحة
  • تأكد من أن أنواع الأحداث المحددة يتم تشغيلها
  • تحقق من أن تطبيق Slack الخاص بك يمتلك الأذونات اللازمة
  • تحقق من بوابة إدارة الويب هوك لسجلات أخطاء التحويل
  • تأكد من أن بنية الحمولة في الويب هوك تتطابق مع شفرة التحويل الخاصة بك
  • اختبر شفرة التحويل باستخدام بيانات تجريبية
  • تأكد من وجود جميع الحقول المطلوبة في حمولة الويب هوك
  • تأكد من أن الأحداث التي تريد تلقيها مفعلة في تكوين ويب هوك Dodo Payments الخاص بك
  • تحقق من أن أنواع الأحداث محددة في تكوين موصل Slack الخاص بك
  • تأكد من أن نقطة النهاية الخاصة بك مكوّنة بشكل صحيح لاستقبال الأحداث