ما واجهة البرمجة (API)
واجهة البرمجة عقد يتحادث عبره برنامجان: أحدهما يرسل طلبا بشكل متفق عليه، والآخر يعيد استجابة بشكل متفق عليه، دون أن يحتاج أي منهما لمعرفة كيف يعمل الآخر من الداخل. وكل شيء تقريبا على الويب تضغط زره فيجلب بيانات من مكان آخر، خلفه API.
- الدرس 11 من 14
- مبتدئ
- مجاني، دون تسجيل
العقد بين برنامجين، لوحا بلوح
برنامجك
لا يلزمه أن يعرف كيف يعمل الطرف الآخر من الداخل
الخدمة المقابلة
لا يعطي إلا ما يقوله العقد، وبقدر ما تسمح به الحصة
الجسر بناه الطرف الآخر وهو قادر على تغييره. ولهذا يوجد رقم إصدار في عنوان الـAPI: فما دام الإصدار الأول حيا يبقى شكل الاستجابة كما هو.
آخر مراجعة: تُراجع الحقائق وأسماء الأدوات في هذا الدرس مقابل مصادرها في هذا التاريخ.
مثال يستطيع هذا الموقع نفسه أن يريك إياه
افتح أداة فحص سرعة الموقع المجانية في هذا الموقع وأعطها عنوانا. فما يجري خلف ذلك الزر هو تعريف الـAPI بالضبط، وله ثلاثة أطراف.
متصفحك يرسل العنوان إلى خادمنا، وخادمنا يسلّم العنوان نفسه إلى خدمة PageSpeed من غوغل، وغوغل يعيد نصا مبنيا بصيغة JSON مليئا بالأرقام، وخادمنا يأخذ منه بضعة أرقام ويعطيها للصفحة. ولا إنسان في هذه السلسلة، ولا واحد من هذه البرامج الثلاثة يعرف كيف كُتب الآخر من الداخل.
والـAPI هو هذا العقد: مجموعة عناوين، كل منها يأخذ مدخلا محددا ويعطي مخرجا محددا. واسمه اختصار لواجهة برمجة التطبيقات، وكلمة الواجهة هي أهم أجزائه. تماما كمقبس الكهرباء: شكل المقبس هو العقد، ولا يلزمك أن تعرف من أين تأتي الكهرباء.
ونقطة هي أقصر طريق للتعلم: أغلب واجهات الويب اليوم ليست شيئا غريبا، بل مجرد عنوان إنترنت يعيد نص JSON بدل صفحة HTML. فإن كنت تعرف كيف تفتح رابطا في متصفح، فأنت قادر على إجراء أول اتصال API.
لكل اتصال أربع قطع
القطعة الأولى هي العنوان، ويسمى كل واحد نقطة نهاية ويؤدي عملا محددا. والثانية هي الطريقة: GET تعني أريد شيئا، وPOST تعني أرسل شيئا ليُسجَّل. والثالثة هي المعاملات أي المدخلات، والرابعة هي الاستجابة.
وللاستجابة نفسها جزآن يرى المبتدئون واحدا منهما عادة. الأول رمز الحالة: ٢٠٠ يعني تم، و٤٠٠ يعني أن في طلبك خللا، و٤٠٤ يعني لا وجود لذلك، و٤٢٩ يعني أنك طلبت بسرعة زائدة، و٥٠٠ يعني أن شيئا تعطل عندهم. والجزء الثاني هو الجسم، وهو JSON غالبا.
وقراءة رمز الحالة هي ما ينقذ وقتك. فالرقم ٤ في أوله يعني أن الخلل من جهة الطالب وأن الطلب هو ما يجب إصلاحه؛ والرقم ٥ يعني أن الخلل من جهة الخدمة وأن إصلاح طلبك لا يفيد. ومن لا يعرف هذا التمييز يقضي ساعات يفتش في شفرته بينما كانت الخدمة المقابلة معطلة.
وAPI هذا الموقع بالشكل نفسه. لدينا ست نقاط نهاية تحت اسم النطاق rgb/v1: أربع منها بـGET لفحص النطاق والسيو والسرعة والأمان، واثنتان بـPOST لنموذج التواصل ولعدّ المشاهدات. ولكل استجابة غلاف ثابت: مفتاح يقول هل نجحت، ثم إما البيانات وإما رسالة الخطأ. وهذا الاتساق أهم لمستهلك الـAPI من أي وثائق.
المفاتيح وحدود المعدل: لماذا لا وجود لـAPI مجاني بلا حدود
كل اتصال API يكلف الطرف الآخر شيئا، ولهذا وُجدت أداتان لضبطه. الأولى المفتاح: سلسلة تحدد هويتك ليُعرف لمن هذه الطلبات. والثانية حد المعدل: سقف لعدد الطلبات في مدة زمنية، وحين تتجاوزه تكون الاستجابة ٤٢٩.
وحادثة حقيقية على هذا الموقع تبين لماذا يهم الاثنان. فأداة السرعة عندنا عملت مدة مع API غوغل بلا أي مفتاح، وكانت تجيب إجابة صحيحة. ثم بدأت الطلبات نفسها، دون أي تغيير من جهتنا، تعود بـ٤٢٩ وفي نص الخطأ حصة يومية صفر. وكان الحل سطرا واحدا: الحصول على مفتاح ووضعه في إعدادات الموقع. والدرس الباقي: سلوك API اليوم ليس عقد الغد، خصوصا حين تستعمل خدمة بلا مفتاح.
والجهة الأخرى مفيدة أيضا: فلـAPI موقعنا حدود، لأنه عام ولا يطلب أي مفتاح. والسقوف لكل زائر في نافذة خمس دقائق: ٢٠ فحص نطاق، و١٠ فحوص سيو، و١٠ فحوص أمان، و٦ فحوص سرعة، لأن كل فحص سرعة هو بنفسه اتصال مكلف بخدمة خارجية. ولنموذج التواصل ميزانيته الخاصة: ٥ إرسالات في الساعة.
وإن كتبت يوما API عاما بنفسك، فخذ هذا تجربة لا نصيحة: ضع حد المعدل من اليوم الأول ولو بدا بلا فائدة. فإضافته بعد أن يبدأ سكربت بقصف خدمتك تأتي متأخرة دائما.
حين يكتب الزائر المدخل: الحارس الذي ينساه الجميع
أدوات هذا الموقع تشترك في خاصية تفصلها عن API عادي: فالعنوان الذي يُفحص يكتبه الزائر، ثم يرسل خادمنا طلبا إلى ذلك العنوان. أي أن غريبا يستطيع أن يقول لخادمنا بأي مكان يتصل.
وإن لم يُكبح ذلك، أمكن لأحدهم أن يكتب عنوانا داخليا في الشبكة بدل موقعه هو. فيفتح خادمنا، وهو داخل الشبكة ويصل إلى مواضع لا يصلها متصفح غريب، ذلك العنوان ويعرض له النتيجة. ويسمى هذا الصنف من الثغرات SSRF، وعلاجه معروف.
والحارس الذي كتبناه في شفرة هذا الموقع يفعل أربعة أشياء وترتيبها مهم. يقبل http وhttps فقط؛ ويقبل المنفذين ٨٠ و٤٤٣ فقط؛ ويرفض عنوانا يحمل في داخله اسم مستخدم وكلمة سر؛ والأهم أنه يحوّل اسم النطاق إلى عناوين IP ويفحص كل عنوان يعود، فيرفض الطلب كله إن كان واحد منها خاصا أو محجوزا.
وذلك البند الأخير هو الذي يُنسى عادة. فمنع العناوين التي تحمل IP خاصا مباشرة سهل ويفعله الجميع؛ لكن من يريد تجاوز هذا الحارس يسجل نطاقا عاديا في مظهره يشير إلى IP داخلي. والطريق الوحيد لمنع ذلك هو خطوة التحويل وفحص نتيجتها، لا النظر إلى شكل العنوان.
أربعة فحوص قبل أن يتصل الخادم بعنوان الزائر
-
http وhttps فقط
يُرفض كل مخطط آخر، لأن هذين وحدهما لازمان لهذا العمل.
-
المنفذان ٨٠ و٤٤٣ فقط
المنفذ غير القياسي يعني عادة أن أحدهم يسعى إلى خدمة أخرى على المضيف نفسه.
-
بلا اسم مستخدم أو كلمة سر في العنوان
العنوان الذي يحمل اعتمادات في داخله إما خطأ وإما فخ.
-
تحويل الاسم وفحص كل عنوان يعود
أهم خطوة وهي التي تُنسى: فنطاق عادي قد يشير إلى IP داخلي.
هذا الترتيب لـAPI يأخذ عنوانا من الزائر. فإن لم يكن لـAPI عندك مدخل كهذا، فهذا الحارس غير لازم وتلزم أشياء أخرى مكانه.
الـAPI الذي لا تملكه سيتوقف يوما
حين يتصل برنامجك بخدمة أخرى، تكون قد صنعت اعتمادا لا تسيطر عليه. فقد تبطؤ الخدمة، أو تنقطع، أو تغير شكل استجابتها، أو تسحب حصتها المجانية. ولا شيء من ذلك نادر، والبرنامج المكتوب لحالة النجاح وحدها يتعطل في ذلك اليوم.
وثلاثة دفاعات بسيطة تكفي غالبا. الأول مهلة زمنية: فلكل اتصال خارجي سقف انتظار، وإلا صار بطؤهم بطأك. والثاني ذاكرة مؤقتة: احفظ الاستجابة مدة قصيرة كي لا يستدعي مدخل متكرر اتصالا جديدا. والثالث خطة ثانية: فحين لا يأتي جواب، على البرنامج أن يعرف ماذا يقول.
وأداة السرعة في هذا الموقع فيها الثلاثة وهي مثال حي: تحفظ نتيجة كل عنوان عشر دقائق، فإن فُحص العنوان نفسه ثانية لم يُجرَ أي اتصال بغوغل؛ وإن لم تأت استجابة من تلك الخدمة، جرى فحص محلي أبسط بدل عرض خطأ، كي لا يبقى الزائر خالي اليدين.
ونقطة لا تُتعلم عادة إلا بعد احتراق مرة أو مرتين: ترقيم الإصدارات. فذلك v1 في اسم نطاق الـAPI عندنا يعني أنه إن تغير شكل الاستجابة يوما، أُنشئ إصدار ثان ولم ينكسر من كان متصلا بالإصدار الأول. وهذا في API عام احترام للمستهلك، وكلفته ثلاثة أحرف زائدة في العنوان.
المسار السريع مع الذكاء الاصطناعي
ما يختصره الذكاء الاصطناعي فعلا هنا هو قراءة وثائق API غير مألوف والوصول إلى أول اتصال صحيح؛ وهو العمل الذي كان يستغرق نصف يوم. لكن النسخة التي تنجح تختلف عن «اكتب لي الشفرة» في أمر واحد: فبدل الشفرة تطلب أولا اتصالا تجريبيا واحدا تستطيع أنت تنفيذه ورؤيته. فكتابة الشفرة بعد رؤية استجابة حقيقية عمل عشر دقائق؛ وكتابتها قبل ذلك تخمين.
- خذ صفحة وثائق ذلك الـAPI وأرسل نص الصفحة نفسها لا رابطها فقط. فإن لم يرَ النموذج الصفحة أجاب من ذاكرته، ووثائق الـAPI تتغير سريعا.
- بالوصفة أدناه اطلب اتصالا تجريبيا واحدا يمكن تنفيذه بلا مفتاح أو بمفتاح تجريبي، ونفّذه أنت. وأول ما تراه رمز الحالة، وهو يقول لك في أي مرحلة أنت.
- وحين تحصل على الاستجابة الحقيقية، أعدها إليه وقل إنك تحتاج هذه الحقول الثلاثة فقط. فالآن يرى النموذج شكل البيانات الحقيقي وتوافق الشفرة التي يكتبها ما يعود فعلا.
- وأخيرا اطلب منه إضافة حالات الفشل: مهلة زمنية، ورمز ٤٢٩، واستجابة ليست JSON أصلا. وهذه الثلاث هي بالضبط ما لا يحدث في اليوم الأول ويحدث حتما في الشهر الثاني.
وصفة جاهزة للنسخ
إليك نص وثائق هذا الـAPI:
{نص صفحة الوثائق}
ما أريد فعله: {مثلا الحصول على حالة طلب برقمه}
أجب بهذا الترتيب:
١. أعطني اتصالا تجريبيا واحدا أستطيع تنفيذه في الطرفية الآن، بالطريقة والعنوان والمعاملات الصحيحة. وإن لزم مفتاح فقل من أين يُؤخذ وفي أي جزء من الطلب يوضع.
٢. قل عن أي الحقول أبحث في الاستجابة الناجحة.
٣. اذكر رموز الحالة التي تعيدها هذه النقطة وماذا يعني كل رمز.
٤. قل ما حد المعدل أو الحصة. وإن لم تذكره الوثائق فاكتب أنها لم تذكره ولا تخمّن.
ولا تكتب أي شفرة للتطبيق بعد؛ الاتصال التجريبي فقط.
قبل أن تثق بالناتج: افحص أمرين بنفسك قبل تنفيذ أي اتصال يعطيك إياه نموذج. الأول ماذا يفعل ذلك الاتصال: فـ<code>GET</code> يقرأ فقط عادة، أما <code>POST</code> و<code>DELETE</code> فقد يغيران شيئا في حسابك الحقيقي والتراجع ليس بيدك. والثاني أن مفتاح الـAPI سر: فلا تضع مفتاحا حقيقيا في أمر تكتبه في محادثة، وإن فعلت مرة فألغِ ذلك المفتاح وأنشئ آخر. وأمر يتكرر كل مرة: إن لم تقل الوثائق شيئا عن سقف الطلبات، فالنموذج يخترع عادة رقما معقولا. وذلك الرقم لم يأت من مكان.
الذكاء الاصطناعي في هذا العمل
في هذا الموضوع يجيد النموذج اللغوي عملين وهناك عمل ينبغي ألا يفعله البتة. يجيد: قراءة وثائق طويلة واستخراج الأسطر القليلة التي تلزمك، وكتابة شفرة تحوّل استجابة JSON إلى شيء قابل للاستعمال. ولا ينبغي: إنتاج الوثائق من ذاكرته. فإن لم تعطه صفحة الوثائق، اخترع أسماء الحقول والمعاملات بثقة تامة وقضيت ساعة في تنقيح شفرة ما كان لها أن تعمل أصلا.
أدوات تساعد فعلا
- Claude مناسب لوصفة هذه الصفحة، لأن نص الوثائق الطويل يمكن لصقه كاملا ثم إعطاء استجابة الـAPI الحقيقية في المحادثة نفسها. وإيران ليست في أي من قائمتي الدول المدعومة لدى أنثروبيك؛ قرأنا ذلك في صفحة أنثروبيك نفسها.
- Claude Code أنفع حين تكتب تكاملا كاملا لا اتصالا واحدا، لأنه يرى شفرة المشروع ويستطيع تنفيذ الاتصال التجريبي بنفسه. يُثبَّت مجانا لكنه لا يعمل دون اشتراك كلود أو حساب في كونسول أنثروبيك.
- Gemini لتحويل استجابة JSON إلى شفرة وللأعمال الميكانيكية المتكررة يكفي نموذج سريع رخيص. وصفحة غوغل نفسها تقول إن تطبيق جيميناي على الويب يعمل في أكثر من ٢٣٠ دولة وإقليما، وإيران ليست في تلك القائمة.
اين ينقلب ضدك
الخطر المحدد في هذا الموضوع نقطة نهاية أو معامل لا وجود له. فالنموذج يعرف شكل الواجهات الشائعة جيدا، ولذلك حين لا يكون قد رأى الوثائق ينتج شيئا يشبه API حقيقيا: أسماء الحقول معقولة، والبنية تبدو صحيحة، ولا شيء منها موجود في خدمتك. وأنثروبيك نفسها تسمي هذا الصنف من الثقة بلا سند هلوسة في وثائقها وتشرح طرق تقليله؛ وأبسطها لهذا العمل إعطاء نص الوثائق.
والخطر الثاني يخص المفتاح. فمفتاح الـAPI كلمة سر برنامجك، ومن يملكه يستطيع أن يرسل طلبات على حسابك وينفق حصتك. فالمفتاح الحقيقي لا يذهب إلى محادثة ولا إلى شفرة داخل مستودع؛ ومكانه ملف إعدادات خارج المستودع، وهو ما قلناه في درس Git. ولمعرفة كيف يمكن الدفع لكل أداة من إيران انظر دليل الشراء.
المصادر: MDN: an overview of HTTP MDN: HTTP response status codes Anthropic: reduce hallucinations Anthropic: supported countries Google: where the Gemini web app is available
حدود هذه النصيحة
هذا الدرس عن واجهات الويب، تلك التي تعمل عبر HTTP وتعيد JSON، لأنها أغلب ما تصادفه اليوم. وتُركت أمور عمدا: التوثيق الأثقل مثل OAuth اللازم حين يتصل برنامجك بحساب مستخدم في خدمة أخرى، والويب هوك حيث ينعكس الاتجاه وتتصل بك الخدمة المقابلة، وأساليب مثل GraphQL بعقد مختلف. وحد يصح هنا أيضا: رمز الحالة ٢٠٠ يقول فقط إن الاتصال تم وإن جوابا قد جاء. أما صحة محتوى ذلك الجواب فضمانة منفصلة لا يقدمها أي API.
من عملنا نحن
كل ما قيل في هذا الدرس عن API هذا الموقع قُرئ من ملف واحد في قالب الموقع ويمكن رؤيته هناك: ست نقاط نهاية تحت اسم النطاق rgb/v1، أربع بـGET واثنتان بـPOST، لا تطلب أي منها مفتاحا وكلها محدودة المعدل لكل زائر. وفي تلك الشفرة أمران قلما يُريان في الدروس. الأول حارس SSRF الذي لا ينظر إلى شكل العنوان فحسب: بل يحوّل اسم النطاق إلى عناوين IP ويرفض الطلب كله إن كان أي من العناوين العائدة خاصا أو محجوزا. والثاني ما تفعله أداة السرعة حين لا تجيب الخدمة الخارجية: فبدل عرض خطأ تُجري فحصا محليا أبسط، وتُحفظ نتيجة كل عنوان عشر دقائق كي لا يُجرى اتصال متكرر. وقصة المفتاح حقيقية أيضا: فذلك الاتصال نفسه عمل مدة بلا مفتاح، ثم بدأ يعيد ٤٢٩ بحصة يومية صفر، وأُصلح بإضافة مفتاح واحد في إعدادات الموقع.
اسئلة متابعة حقيقية
ما الفرق بين API وخدمة الويب؟
خدمة الويب هي API متاح عبر الشبكة. وليس كل API يعبر شبكة؛ فالمكتبة التي تستدعيها داخل برنامجك لها API أيضا. لكن في الحديث اليومي تُستعمل الكلمتان بالمعنى نفسه عادة.
من أين أبدأ لأول اتصال API؟
من API عام لا يطلب مفتاحا ويعمل بـGET؛ افتح عنوانه في متصفح وانظر إلى الـJSON. وحين يصير شكل الاستجابة مألوفا، أجرِ الاتصال نفسه بأداة مثل curl ثم من داخل الشفرة. وهذا الترتيب يحذف ساعات من الحيرة.
حصلت على ٤٢٩، ماذا يعني؟
يعني أنك تجاوزت سقف عدد الطلبات وعليك الانتظار، لا أن في شفرتك خللا. انظر أولا هل قالت الخدمة في استجابتها كم تنتظر؛ ثم إن كانت الاتصالات متكررة فاحفظ الاستجابة مؤقتا ليقل عددها.