تخطي إلى المحتوى

المطورون

الويب هوك وZapier

ترسل الويب هوك طلب HTTP إلى خادمك لحظة وقوع أمر ما في مساحة العمل، مثل إيقاف تطبيق مؤقتًا أو النقر على رابط ذكي. استخدمها لتحديث أنظمتك الخاصة، أو النشر في Slack، أو ربط mapps.one بـ Zapier أو Make أو n8n دون كتابة خادم. تتوفر الويب هوك في خطة Studio، مع ما يصل إلى 10 نقاط نهاية لكل مساحة عمل.

إضافة نقطة نهاية

  1. في لوحة التحكم، افتح المطورون ← الويب هوك واختر إضافة نقطة نهاية. يمكن لمالكي مساحة العمل والمسؤولين القيام بذلك.
  2. أدخل عنوان URL عامًا من نوع https، واختر الأحداث المطلوب إرسالها (أو جميع الأحداث) وأضف وصفًا.
  3. انسخ سر التوقيع واحفظه مع الأسرار الأخرى الخاصة بخادمك.
  4. اختر إرسال حدث تجريبي للتحقق من أن نقطة النهاية تستجيب.

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

الأحداث

النوعيُرسَل عندما
app.createdأُضيف تطبيق إلى مساحة العمل.
app.updatedتغيّرت تفاصيل التطبيق أو روابطه أو إعدادات صفحته.
app.deletedحُذف تطبيق.
app.status_changedأصبح تطبيق مباشرًا، أو أُوقف مؤقتًا، أو عُلِّق.
app.metadata_fetchedاستُوردت البيانات الوصفية من المتجر لأحد التطبيقات.
legal.publishedنُشرت سياسة خصوصية أو مستند شروط خدمة.
domain.verifiedتم التحقق من نطاق مخصص.
link.clickedكل نقرة على الرابط الذكي. وقد يعني ذلك عددًا كبيرًا من الطلبات لتطبيق رائج.
analytics.daily_summaryإجماليات نقرات اليوم السابق لكل تطبيق، تُرسَل مرة واحدة يوميًا.

تنسيق الطلب

يُرسَل كل حدث كطلب POST بنص JSON.

الترويسةالقيمة
Content-Typeapplication/json
User-Agentmapps.one-Webhooks/1.0
X-Mapps-Eventنوع الحدث، مثل link.clicked
X-Mapps-Deliveryمعرّف الحدث. ويبقى كما هو في كل إعادة محاولة.
X-Mapps-Timestampوقت Unix لمحاولة التسليم هذه
X-Mapps-Signaturet={timestamp},v1={signature}

نص الطلب غلاف له البنية نفسها في كل الأحداث:

{
  "id": "evt_01j8c3m9t5v2x7z4b6d8f0h2k4",
  "type": "app.status_changed",
  "created_at": "2026-09-14T09:41:07+00:00",
  "workspace": {
    "id": "01j8a0f4c7d2e9h6k3m5n8q1r4",
    "name": "Habitly Labs"
  },
  "data": {
    "app": {
      "id": "01j8b2k6r3xq9v7m4n5p0s1t2w",
      "slug": "habitly",
      "name": "Habitly"
    },
    "status": "paused"
  }
}

يعتمد محتوى data على الحدث. وتتضمن الأحداث المتعلقة بتطبيق كائن app يحتوي على id وslug وname الخاصة بالتطبيق.

link.clicked

"data": {
  "app": { "id": "01j8b2k6r3xq9v7m4n5p0s1t2w", "slug": "habitly", "name": "Habitly" },
  "click": {
    "occurred_at": "2026-09-14 09:41:07",
    "os": "iOS",
    "device_type": "mobile",
    "country": "TR",
    "source": "instagram",
    "destination": "app_store",
    "utm_source": "instagram",
    "utm_medium": "social",
    "utm_campaign": "launch"
  }
}

يكون occurred_at بتوقيت UTC. وقيمة device_type هي mobile أو tablet أو desktop. وقيمة destination مفتاح متجر أو web أو landing. والحقول غير المعروفة قيمتها null. ولا تُطلق زيارات الروبوتات هذا الحدث أبدًا.

app.metadata_fetched

"data": {
  "app": { "id": "01j8b2k6r3xq9v7m4n5p0s1t2w", "slug": "habitly", "name": "Habitly" },
  "source": "app_store"
}

التحقق من التوقيعات

تحقق من التوقيع في كل طلب، لتتأكد من أنه صادر من mapps.one ولم يُعدَّل في الطريق:

  1. اقرأ t وv1 من ترويسة X-Mapps-Signature.
  2. احسب HMAC-SHA256 لـ {t}.{raw request body} باستخدام سر التوقيع الخاص بنقطة النهاية، بصيغة ست عشرية بأحرف صغيرة.
  3. قارن النتيجة بـ v1 باستخدام مقارنة ثابتة الوقت.
  4. ارفض الطلب إذا كان الفرق بين t وساعة خادمك أكثر من خمس دقائق، لمنع الطلبات المُعاد إرسالها.
استخدم نص الطلب الخام. احسب التوقيع على البايتات نفسها التي استلمتها بالضبط، قبل أي تحليل لـ JSON. فإعادة ترميز JSON قد تغيّر الشرطات المائلة أو أحرف Unicode وتُفسد التوقيع.

PHP

<?php

$secret = getenv('MAPPS_WEBHOOK_SECRET');
$body = file_get_contents('php://input');

parse_str(str_replace(',', '&', $_SERVER['HTTP_X_MAPPS_SIGNATURE'] ?? ''), $parts);

$timestamp = (int) ($parts['t'] ?? 0);
$expected = hash_hmac('sha256', $timestamp.'.'.$body, $secret);

if (! hash_equals($expected, (string) ($parts['v1'] ?? '')) || abs(time() - $timestamp) > 300) {
    http_response_code(400);
    exit;
}

$event = json_decode($body, true);

if ($event['type'] === 'link.clicked') {
    // Store $event['data']['click'] ...
}

http_response_code(200);

في Laravel، اقرأ نص الطلب باستخدام $request->getContent() والترويسة باستخدام $request->header('X-Mapps-Signature')، واستثنِ المسار من حماية CSRF.

Node.js (Express)

import crypto from 'node:crypto';
import express from 'express';

const app = express();
const secret = process.env.MAPPS_WEBHOOK_SECRET;

app.post('/webhooks/mapps', express.raw({ type: 'application/json' }), (req, res) => {
  const header = req.get('X-Mapps-Signature') ?? '';
  const parts = Object.fromEntries(header.split(',').map((pair) => pair.split('=')));
  const timestamp = Number(parts.t);
  const body = req.body.toString('utf8');

  const expected = crypto.createHmac('sha256', secret).update(`${timestamp}.${body}`).digest();
  const received = Buffer.from(parts.v1 ?? '', 'hex');
  const valid = received.length === expected.length && crypto.timingSafeEqual(received, expected);

  if (!valid || Math.abs(Date.now() / 1000 - timestamp) > 300) {
    return res.sendStatus(400);
  }

  const event = JSON.parse(body);

  if (event.type === 'link.clicked') {
    // Store event.data.click ...
  }

  res.sendStatus(200);
});

app.listen(3000);

الاستجابات وإعادة المحاولة

  • استجب بأي حالة 2xx خلال 10 ثوانٍ. ونفّذ الأعمال البطيئة في مهمة خلفية بعد أن تستجيب.
  • لا تُتبَع عمليات إعادة التوجيه، لذا استخدم عنوان URL النهائي.
  • يجب أن يكون عنوان URL عامًا ومن نوع https. وتُرفض عناوين الشبكات الخاصة والمحلية.
  • إذا انتهت مهلة نقطة النهاية أو أعادت أي حالة غير 2xx، نعيد المحاولة حتى خمس مرات إضافية: بعد نحو دقيقة واحدة، و5 دقائق، و30 دقيقة، وساعتين، و6 ساعات. ولكل محاولة طابع زمني وتوقيع جديدان.
  • قد يصل الحدث نفسه أكثر من مرة، وقد تصل الأحداث بغير ترتيبها. استخدم X-Mapps-Delivery، وهو id الحدث، لتجاهل التكرارات، وcreated_at لترتيبها.
  • بعد 20 محاولة فاشلة متتالية، تُوقَف نقطة النهاية ولا يُرسَل إليها أي شيء آخر. أصلح المشكلة، ثم أعد تشغيلها من لوحة التحكم.

Zapier وMake وn8n

يمكنك ربط mapps.one بآلاف التطبيقات دون تشغيل خادم.

Zapier

  1. أنشئ Zap يستخدم Webhooks by Zapier كمشغّل واختر Catch Hook.
  2. انسخ عنوان URL الخاص بالويب هوك الذي يمنحك إياه Zapier.
  3. في mapps.one، أضف نقطة نهاية بعنوان URL هذا واختر الأحداث التي تريدها، مثل app.status_changed أو analytics.daily_summary.
  4. اختر إرسال حدث تجريبي في mapps.one، ثم Test trigger في Zapier. ويمكنك الآن استخدام حقول الحمولة، مثل data.app.name، في الخطوات التالية.

أمثلة: انشر رسالة في Slack عند إيقاف تطبيق مؤقتًا، أو أضف نقرات كل يوم إلى جدول في Google Sheets، أو أرسل بريدًا إلكترونيًا إلى عميل عند التحقق من نطاقه.

Make وn8n

في Make، استخدم المشغّل Webhooks → Custom webhook. وفي n8n، استخدم العقدة Webhook مع طريقة POST. ثم أضف عنوان URL كنقطة نهاية في mapps.one كما هو موضح أعلاه.

بناء تكامل

إذا كنت تبني تكاملًا مع mapps.one ليستخدمه الآخرون، فأنشئ الاشتراك عبر API عند ربط المستخدم للتكامل (POST /api/v1/webhooks)، وألغِ الاشتراك عند فصله (DELETE /api/v1/webhooks/{id})، واستخدم GET /api/v1/events لأداة اختيار الأحداث، وGET /api/v1/workspace لاختبار الاتصال. راجع مرجع API.