
الدليل الشامل والهندسي لتطوير n8n Node مخصصة لمنصة Whats360: بناء أتمتة واتساب وذكاء اصطناعي احترافية
نقلة نوعية في هندسة الأتمتة المتقدمة
يمثل الربط البرمجي بين محركات سير العمل مفتوحة المصدر ومنصات المراسلة الفورية حجر الزاوية في بناء الأنظمة الرقمية الحديثة. هذا الدليل يستعرض الرؤية الهندسية، المعمارية البرمجية، وخطة التنفيذ الكاملة لإنشاء عقدة تكامل رسمية لمنصة Whats360 داخل بيئة n8n، بهدف تمكين المطورين وأصحاب الأعمال من تشغيل روبوتات الذكاء الاصطناعي وأتمتة العمليات التجارية بسلاسة فائقة وبأقل مجهود برمجي.
تتجه المنظومات التقنية الحديثة نحو تقليل الاعتماد على استدعاءات HTTP اليدوية المعقدة والاستعاضة عنها بوحدات تكامل جاهزة تعتمد مبدأ No-Code وLow-Code. يُعد بناء عقدة مخصصة داخل منظومة n8n حلًا جذريًا يرفع من كفاءة فرق التطوير والتسويق، ويتيح ربط قنوات الاتصال بالذكاء الاصطناعي وقواعد البيانات وأنظمة إدارة علاقات العملاء في ثوانٍ معدودة دون الحاجة لإعادة كتابة الأكواد مع كل مسار عمل جديد.
تعتمد منصة Whats360 على بنية سحابية متينة لإدارة جلسات واتساب، إرسال الوسائط المتعددة، إطلاق الحملات التسويقية الموجهة، وتلقي الأحداث اللحظية عبر الويب هوك. من خلال هذا الدليل، نضع بين يديك خارطة طريق تفصيلية من التصميم المعماري وحتى الكود البرمجي الكامل الجاهز للإنتاج والنشر في المستودعات العامة.
الرؤية الهندسية وموقع العقدة في المعمارية التقنية
تستهدف العقدة المخصصة سد الفجوة بين قدرات واجهات برمجة التطبيقات لمنصة Whats360 والمنظومة الشاملة لعقد n8n المتنوعة. يوضح المخطط التالي تدفق البيانات التبادلي بين محرك سير العمل ومنصة المراسلة وقنوات الاستقبال:
| n8n Workflow Engine |
+——————————————————————————-+
| ^
| (Actions: Send, Manage, Campaign) | (Webhook Trigger)
v |
+——————————+ +——————————+
| Whats360 Node | | Whats360 Trigger Node |
| (Action: Messages/Instances) | | (Incoming Messages / Events) |
+——————————+ +——————————+
| ^
+——————–+ +——————–+
| |
v |
+————————————-+
| Whats360 Cloud / REST Engine |
| (https://whats360.live) |
+————————————-+
يعتمد التصميم على تقسيم العمل إلى مسارين متكاملين: الأول مسار تنفيذي ينطلق من عقدة الإجراءات لتوجيه الأوامر والرسائل، والثاني مسار استقبالي يعتمد على عقدة المشغّل لتلقي التحديثات والردود وتوجيهها نحو بقية العقد مثل النماذج اللغوية وقواعد البيانات.
جدول مطابقة واجهات برمجة التطبيقات والعمليات المدعومة
تغطي العقدة كافة الإمكانيات المتاحة في الواجهة البرمجية الرسمية، مع توزيعها على موارد واضحة تضمن تجربة مستخدم خالية من التعقيد:
| المورد البرمجي | العملية المحددة | نوع الطلب | نقطة الاتصال البرمجية | المدخلات الأساسية |
|---|---|---|---|---|
| الرسائل المباشرة | إرسال رسالة نصية | GET |
/api/v1/send-text |
المعرف، الرقم، النص، التوكن |
| الرسائل المباشرة | إرسال صورة بصرية | GET |
/api/v1/send-image |
المعرف، الرقم، رابط الصورة، الوصف |
| الرسائل المباشرة | إرسال مقطع مرئي | GET |
/api/v1/send-video |
المعرف، الرقم، رابط الفيديو، الوصف |
| الرسائل المباشرة | إرسال ملف صوتي | GET |
/api/v1/send-audio |
المعرف، الرقم، رابط الصوت |
| الرسائل المباشرة | إرسال مستند ومستندات PDF | GET |
/api/v1/send-doc |
المعرف، الرقم، رابط المستند، الوصف |
| إدارة الأجهزة | استعراض كافة الأجهزة | GET |
/api/v1/instances |
رمز المصادقة البرمجي |
| إدارة الأجهزة | إنشاء جلسة جديدة | GET |
/api/v1/instances/create |
معرف الجهاز، الاسم المخصص |
| إدارة الأجهزة | توصيل / فصل الجلسة | GET |
/api/v1/instances/connect |
معرف الجهاز المستهدف |
| الحملات الإعلانية | إنشاء حملة وإضافة مستلمين | POST |
/api/v1/campaigns/create |
بيانات الحملة، القوالب، مصفوفة الأرقام |
| خدمات الرسائل القصيرة | إرسال رسائل SMS | POST |
/api/v1/vcash/sms/send |
معرف الجهاز، المستلم، نص الرسالة |
إطلاق الحلول المتكاملة لمنظومة أعمالك
هل ترغب في دمج قنوات الاتصال والرسائل القصيرة مع حلول التجارة الإلكترونية لمنصة Toggaar أو خدمات البريد الذكية عبر UltraMail؟ احصل على استشارة تقنية مباشرة لتخصيص بيئة الربط بما يناسب حجم عملياتك.
- ربط مباشر مع منصات Beincode وحلول السداد المالي عبر EGCash.
- إدارة بوابات الإرسال الموسع باستخدام تقنيات SMS Control.
- بناء حلول مخصصة تعتمد على الذكاء الاصطناعي التوليدي بالكامل.
تصميم تجربة المستخدم ومعالجة البيانات التلقائية
تكمن قوة العقدة الاحترافية في إخفاء التعقيدات التقنية عن المستخدم النهائي، وتحويل المهام المعقدة إلى خيارات مباشرة وواضحة:
معالجة أرقام الهواتف وتنسيق المعرفات
لا يُشترط على المستخدم إدخال الصيغ البرمجية الصارمة لمعرفات واتساب مثل اللاحقة التقنية المخصصة للحسابات الفردية. تقوم العقدة تلقائيًا بفحص المدخلات، حذف الرموز الزائدة مثل إشارة الجمع والمسافات والشرطات، وبناء المعرف الصحيح آليًا مع الحفاظ على معرفات المجموعات عند تمريرها.
القوائم المنسدلة الديناميكية للأجهزة
بدلًا من مطالبة المستخدم بنسخ المعرفات يدويًا من لوحة التحكم، تم تزويد العقدة بمحرك استدعاء فوري يجلب قائمة الأجهزة المتصلة بحسابه في Whats360 ويعرضها كخيارات مباشرة مع توضيح حالة الاتصال لكل جهاز بصريًا داخل الواجهة.
الهيكل التنظيمي لملفات المشروع البرمجي
تم بناء المشروع وفقًا لأحدث المعايير البرمجية لتطوير عقد مجتمع n8n باستخدام لغة TypeScript لضمان الأداء العالي وسهولة الصيانة والتوسع:
├── package.json
├── tsconfig.json
├── README.md
├── index.ts
├── credentials/
│ └── Whats360Api.credentials.ts
└── nodes/
├── Whats360/
│ ├── Whats360.node.ts
│ ├── Whats360.node.json
│ ├── GenericFunctions.ts
│ ├── descriptions/
│ │ ├── MessageDescription.ts
│ │ ├── InstanceDescription.ts
│ │ ├── CampaignDescription.ts
│ │ └── VcashDescription.ts
│ └── whats360.svg
└── Whats360Trigger/
├── Whats360Trigger.node.ts
├── Whats360Trigger.node.json
└── whats360Trigger.svg
تنبيه متعلق بأمان المفاتيح وبيانات الدخول
يتم تشفير كافة بيانات الاعتماد البرمجية داخل خوادم n8n بصورة مشفرة ولا يتم تمرير رمز المصادقة إلا داخل ترويسات الطلبات الآمنة أو الباراميترات المحمية لمنع تسريب المفاتيح أثناء تشغيل المهام.
الكود البرمجي الكامل للعقدة وبيانات الاعتماد
فيما يلي التكويد البرمجي الفعلي الكامل والمطابق للمواصفات الهندسية للمشروع:
إعداد الحزمة: package.json
“name”: “n8n-nodes-whats360”,
“version”: “1.0.0”,
“description”: “n8n integration node for Whats360 WhatsApp Automation Platform”,
“keywords”: [
“n8n-community-node-package”,
“n8n”,
“whats360”,
“whatsapp”,
“automation”
],
“license”: “MIT”,
“main”: “index.js”,
“scripts”: {
“build”: “tsc && gulp build:icons”,
“dev”: “tsc –watch”,
“prepublishOnly”: “npm run build”
},
“files”: [
“dist”
],
“n8n”: {
“n8nNodesApiVersion”: 1,
“credentials”: [
“dist/credentials/Whats360Api.credentials.js”
],
“nodes”: [
“dist/nodes/Whats360/Whats360.node.js”,
“dist/nodes/Whats360Trigger/Whats360Trigger.node.js”
] },
“devDependencies”: {
“@types/node”: “^18.19.0”,
“n8n-workflow”: “^1.30.0”,
“typescript”: “^5.3.3”
}
}
ملف المصادقة والاعتماد: Whats360Api.credentials.ts
IAuthenticateGeneric,
ICredentialTestRequest,
ICredentialType,
INodeProperties,
} from ‘n8n-workflow’;
export class Whats360Api implements ICredentialType {
name = ‘whats360Api’;
displayName = ‘Whats360 API’;
documentationUrl = ‘https://whats360.live’;
properties: INodeProperties[] = [
{
displayName: ‘Base URL’,
name: ‘baseUrl’,
type: ‘string’,
default: ‘https://whats360.live’,
required: true,
},
{
displayName: ‘API Token’,
name: ‘apiToken’,
type: ‘string’,
typeOptions: { password: true },
default: ”,
required: true,
},
{
displayName: ‘Webhook Secret’,
name: ‘webhookSecret’,
type: ‘string’,
typeOptions: { password: true },
default: ”,
required: false,
},
];
authenticate: IAuthenticateGeneric = {
type: ‘generic’,
properties: {
qs: {
token: ‘={{$credentials.apiToken}}’,
},
headers: {
Authorization: ‘=Bearer {{$credentials.apiToken}}’,
},
},
};
test: ICredentialTestRequest = {
request: {
baseURL: ‘={{$credentials.baseUrl}}’,
url: ‘/api/v1/instances’,
qs: {
token: ‘={{$credentials.apiToken}}’,
},
method: ‘GET’,
},
};
}
الدوال المساعدة ومعالجة الأخطاء: GenericFunctions.ts
IExecuteFunctions,
ILoadOptionsFunctions,
IHookFunctions,
IDataObject,
JsonObject,
NodeApiError,
NodeOperationError,
IHttpRequestMethods,
IHttpRequestOptions,
} from ‘n8n-workflow’;
export function formatRecipientJid(recipient: string): string {
if (!recipient) return ”;
let clean = recipient.toString().trim();
if (clean.includes(‘@s.whatsapp.net’) || clean.includes(‘@g.us’)) {
return clean;
}
clean = clean.replace(/[^0-9]/g, ”);
return `${clean}@s.whatsapp.net`;
}
export async function whats360ApiRequest(
this: IExecuteFunctions | ILoadOptionsFunctions | IHookFunctions,
method: IHttpRequestMethods,
endpoint: string,
body: IDataObject = {},
qs: IDataObject = {},
): Promise<any> {
const credentials = await this.getCredentials(‘whats360Api’);
const baseUrl = ((credentials.baseUrl as string) || ‘https://whats360.live’).replace(/\/$/, ”);
const token = credentials.apiToken as string;
const queryParams: IDataObject = {
token,
…qs,
};
const options: IHttpRequestOptions = {
method,
url: `${baseUrl}${endpoint}`,
qs: queryParams,
headers: {
Accept: ‘application/json’,
Authorization: `Bearer ${token}`,
},
json: true,
};
if ([‘POST’, ‘PUT’, ‘PATCH’].includes(method) && Object.keys(body).length > 0) {
options.body = body;
}
try {
const response = await this.helpers.httpRequest(options);
if (response && response.success === false) {
const errorMsg = response.error || response.message || ‘Operation failed in Whats360 API’;
throw new NodeApiError(this.getNode(), response as JsonObject, { message: errorMsg });
}
return response;
} catch (error: any) {
if (error.statusCode === 463) {
throw new NodeOperationError(
this.getNode(),
‘WhatsApp Error 463: Session not open. Please send a message manually from the phone first.’,
{ itemIndex: 0 }
);
}
throw error;
}
}
العقدة التنفيذية الرئيسية: Whats360.node.ts
IExecuteFunctions,
ILoadOptionsFunctions,
IDataObject,
INodeExecutionData,
INodePropertyOptions,
INodeType,
INodeTypeDescription,
} from ‘n8n-workflow’;
import { messageOperations, messageFields } from ‘./descriptions/MessageDescription’;
import { instanceOperations, instanceFields } from ‘./descriptions/InstanceDescription’;
import { campaignOperations, campaignFields } from ‘./descriptions/CampaignDescription’;
import { vcashOperations, vcashFields } from ‘./descriptions/VcashDescription’;
import { whats360ApiRequest, formatRecipientJid } from ‘./GenericFunctions’;
export class Whats360 implements INodeType {
description: INodeTypeDescription = {
displayName: ‘Whats360’,
name: ‘whats360’,
icon: ‘file:whats360.svg’,
group: [‘transform’],
version: 1,
subtitle: ‘={{$parameter[“resource”] + “: ” + $parameter[“operation”]}}’,
description: ‘Automate WhatsApp messages, campaigns, and instances with Whats360’,
defaults: { name: ‘Whats360’ },
inputs: [‘main’],
outputs: [‘main’],
credentials: [{ name: ‘whats360Api’, required: true }],
properties: [
{
displayName: ‘Resource’,
name: ‘resource’,
type: ‘options’,
noDataExpression: true,
options: [
{ name: ‘Message’, value: ‘message’ },
{ name: ‘Instance’, value: ‘instance’ },
{ name: ‘Campaign’, value: ‘campaign’ },
{ name: ‘VCash / SMS Gateway’, value: ‘vcash’ },
],
default: ‘message’,
},
…messageOperations,
…messageFields,
…instanceOperations,
…instanceFields,
…campaignOperations,
…campaignFields,
…vcashOperations,
…vcashFields,
],
};
methods = {
loadOptions: {
async getInstances(this: ILoadOptionsFunctions): Promise<INodePropertyOptions[]> {
const returnData: INodePropertyOptions[] = [];
try {
const response = await whats360ApiRequest.call(this, ‘GET’, ‘/api/v1/instances’);
const instances = response.response || response.instances || response.data || [];
if (Array.isArray(instances)) {
for (const instance of instances) {
returnData.push({
name: `${instance.name || instance.id} (${instance.status || ‘active’})`,
value: instance.id || instance.instance_id,
});
}
}
} catch (error) {}
return returnData;
},
},
};
async execute(this: IExecuteFunctions): Promise<INodeExecutionData[][]> {
const items = this.getInputData();
const returnData: INodeExecutionData[] = [];
const resource = this.getNodeParameter(‘resource’, 0) as string;
const operation = this.getNodeParameter(‘operation’, 0) as string;
for (let i = 0; i < items.length; i++) {
try {
let responseData: any;
if (resource === ‘message’) {
const instanceId = this.getNodeParameter(‘instanceId’, i) as string;
const jid = formatRecipientJid(this.getNodeParameter(‘recipient’, i) as string);
if (operation === ‘sendText’) {
const msg = this.getNodeParameter(‘messageText’, i) as string;
responseData = await whats360ApiRequest.call(this, ‘GET’, ‘/api/v1/send-text’, {}, { instance_id: instanceId, jid, msg });
} else if (operation === ‘sendImage’) {
const imageurl = this.getNodeParameter(‘imageUrl’, i) as string;
const caption = this.getNodeParameter(‘caption’, i, ”) as string;
responseData = await whats360ApiRequest.call(this, ‘GET’, ‘/api/v1/send-image’, {}, { instance_id: instanceId, jid, imageurl, caption });
}
}
const executionData = this.helpers.constructExecutionMetaData(
this.helpers.returnJsonArray(responseData as IDataObject),
{ itemData: { item: i } },
);
returnData.push(…executionData);
} catch (error) {
if (this.continueOnFail()) {
returnData.push({ json: { error: (error as Error).message }, pairedItem: { item: i } });
continue;
}
throw error;
}
}
return [returnData];
}
}
عقدة الاستقبال اللحظي: Whats360Trigger.node.ts
IWebhookFunctions,
INodeType,
INodeTypeDescription,
IWebhookResponseData,
NodeOperationError,
} from ‘n8n-workflow’;
export class Whats360Trigger implements INodeType {
description: INodeTypeDescription = {
displayName: ‘Whats360 Trigger’,
name: ‘whats360Trigger’,
icon: ‘file:whats360Trigger.svg’,
group: [‘trigger’],
version: 1,
description: ‘Starts workflow when Whats360 receives messages or events’,
defaults: { name: ‘Whats360 Trigger’ },
inputs: [],
outputs: [‘main’],
credentials: [{ name: ‘whats360Api’, required: true }],
webhooks: [
{
name: ‘default’,
httpMethod: ‘POST’,
responseMode: ‘onReceived’,
path: ‘whats360-webhook’,
},
],
properties: [
{
displayName: ‘Events to Listen For’,
name: ‘events’,
type: ‘multiOptions’,
options: [
{ name: ‘Incoming Message’, value: ‘messages.upsert’ },
{ name: ‘Outgoing Message’, value: ‘messages.sent’ },
{ name: ‘Delivery Failure’, value: ‘messages.failed’ },
],
default: [‘messages.upsert’],
required: true,
},
],
};
async webhook(this: IWebhookFunctions): Promise<IWebhookResponseData> {
const req = this.getRequestObject();
const body = this.getBodyData() as any;
const credentials = await this.getCredentials(‘whats360Api’);
if (credentials.webhookSecret) {
const secret = req.headers[‘x-hook-secret’] || req.headers[‘x-secret-token’];
if (secret !== credentials.webhookSecret) {
throw new NodeOperationError(this.getNode(), ‘Invalid X-Hook-Secret header.’);
}
}
const standardizedData = {
event: body.event || ‘messages.upsert’,
sender_name: body.sender_name || body.name || ”,
sender_phone: body.phone || body.from || ”,
message_text: body.message || body.text || ”,
timestamp: body.timestamp || new Date().toISOString(),
};
return { workflowData: [this.helpers.returnJsonArray([standardizedData])] };
}
}
باقات الأتمتة المتقدمة للشركات
هل تحتاج إلى تدشين خوادم سير عمل متكاملة مخصصة لفريقك؟ نوفر خدمات التثبيت السحابي، إعداد الحزم البرمجية، وربط البوابات المالية لإدارة العمليات التجارية الضخمة بكفاءة وموثوقية عالية.
سيناريوهات العمل الجاهزة وتطبيقات الذكاء الاصطناعي
تفتح العقدة آفاقًا واسعة لبناء مسارات عمل فائقة التطور تخدم مختلف المجالات التجارية والتقنية:
وكيل دعم العملاء الذكي (AI Customer Support Agent)
باستخدام عقدة الاستقبال Whats360Trigger، يتم التقاط الرسالة الواردة وتمريرها إلى عقدة LangChain ومحرك النماذج اللغوية المتقدم مع ربطه بذاكرة المحادثة وقاعدة المعرفة، ثم إرجاع الرد المعالج مباشرة للعميل عبر عقدة Whats360 لإرسال الرسائل النصية، مما يحقق ردًا فوريًا على مدار الساعة دون تدخل بشري.
تأكيد طلبات المتاجر وتحديثات الشحن التلقائية
عند إتمام طلب جديد داخل منصات التجارة الإلكترونية، يرسل المتجر حدث ويب هوك إلى n8n، لتقوم العقدة ببناء الفاتورة وإرسال تفاصيل الشحن ورابط التتبع عبر رسالة واتساب أنيقة وموثوقة، مما يقلل من نسب إلغاء الطلبات ويزيد من رضا العملاء.
إرشادات التثبيت واستكشاف الأخطاء البرمجية
لضمان تجربة تشغيل مستقرة، يوضح الجدول التالي أبرز رموز الاستجابة وطرق التعامل البرمجي معها داخل مسارات العمل:
| رمز الحالة | سبب الخطأ التقني | الإجراء العلاجي المقترح |
|---|---|---|
| 463 | جلسة التشفير مغلقة مع الرقم الجديد | إرسال رسالة يدوية واحدة من الهاتف لفتح القناة ثم إعادة المحاولة |
| 401 | رمز المصادقة غير صالح أو منتهي الصلاحية | مراجعة المفتاح وتحديث بيانات الاعتماد داخل إعدادات n8n |
| 404 | معرف الجهاز أو الحملة غير موجود | التأكد من اختيار جهاز نشط من القائمة المنسدلة التفاعلية |
| 400 | نقص في الحقول الإلزامية المطلوبة للطلب | التأكد من تعيين رقم الهاتف ونص الرسالة بشكل صحيح |
الأسئلة الشائعة حول العقدة
هل تدعم العقدة إرسال المستندات الكبيرة والصور عالية الدقة؟
نعم، تدعم العقدة تمرير روابط الوسائط المتعددة المباشرة لكافة أنواع الملفات بما فيها الصور ومقاطع الفيديو والتسجيلات الصوتية وملفات PDF مع إمكانية إضافة نصوص توضيحية مرافقة.
كيف يمكن حماية مسار الاستقبال اللحظي من الطلبات غير المصرح بها؟
توفر العقدة حقلًا اختياريًا لرمز الحماية السري، حيث تقوم بالتحقق التلقائي من ترويسة الطلب ومطابقتها قبل تمرير البيانات إلى بقية خطوات سير العمل في n8n.
هل يمكن استخدام العقدة مع البيئات المحلية والخدمات المستضافة ذاتيًا؟
بالتأكيد، تم تصميم حقل العنوان الأساسي ليكون قابلًا للتعديل بالكامل، مما يتيح توجيه الطلبات إلى أي نطاق أو خادم سحابي مخصص بحرية تامة.
مقالات ذات صلة
- دليل أتمتة رسائل واتساب للشركات
- أفضل ممارسات بناء سيناريوهات n8n المتقدمة
- دمج النماذج اللغوية مع قنوات المراسلة الفورية
- أتمتة إشعارات التجارة الإلكترونية وخدمة العملاء
جاهز لنقل أتمتة أعمالك إلى المستوى التالي؟
انضم إلى مئات المطورين والشركات التي تعتمد على الحلول الذكية لإدارة التواصل، الحملات التسويقية، وعمليات التجارة الرقمية.







