واجهة REST API
العنوان، وكيف يسجّل سكربت الدخول، وكيف تُختار المؤسّسة، وكيف تبدو الأخطاء، مع أمثلة كاملة بـ curl.
كل ما تفعله وحدة التحكّم والـ CLI، تفعلانه عبر واجهة HTTP API واحدة. الـ CLI
مبنيّة عليها وليس لها باب خاص: كل ما يستطيعه isogrid، يستطيعه سكربت يحمل
بيانات الاعتماد نفسها بـ curl.
هذه الصفحة دليل لاستخدام تلك الواجهة: العنوان، وكيف يسجّل سكربت الدخول، والطلبات التي تحتاجها أغلب الفرق. وهي لا تسرد كل نقطة وصول. فإن احتجت إلى واحدة لا تظهر هنا، فالـ CLI تغطّي المجال نفسه، والفريق يعطيك الطلب الدقيق عند الحاجة.
العنوان
كل طلب يُرسل إلى https://api.isogrid.skyvault.pro/api/v1.
تصف الأمثلة أدناه ما تقبله الواجهة اليوم. تحقّق منها مجدّدًا بعد ترقية المنصّة بدل أن تفترض أن حقلًا ما زال موجودًا.
تسجيل الدخول من سكربت
يحمل كل طلب رمزًا:
Authorization: Bearer <token>
وهذا الرمز، في حالة السكربت، هو بيانات اعتماد CLI: رمز طويل العمر يبدأ بـ
skv_، تنشئه أنت، باسمك، لمؤسّسة واحدة. تنشئه بالـ CLI وتوافق عليه في
المتصفّح. ولا يوجد في وحدة التحكّم نموذج يسلّم رمزًا دون هذه الموافقة.
export ISOGRID_CONFIG_HOME="$(mktemp -d)"
isogrid --api https://api.isogrid.skyvault.pro login --name my-script
jq -r '.contexts[].token' "$ISOGRID_CONFIG_HOME/config.json"
rm -rf "$ISOGRID_CONFIG_HOME"
استخدام ISOGRID_CONFIG_HOME مؤقّت يُبقي تسجيل الدخول على جهازك كما هو. وتشرح
صفحة تثبيت واجهة سطر الأوامر كيف تحصل على isogrid.
ما ينبغي معرفته عن بيانات الاعتماد:
- هي مثبّتة على المؤسّسة الظاهرة في صفحة الموافقة. تحقّق منها قبل أن توافق.
- لا تتجاوز أبدًا ما تملكه. تُقاطَع صلاحياتها مع دورك ومجموعاتك في كل طلب، فتضييق صلاحياتك يضيّق صلاحيات السكربت أيضًا.
- ضيّقها. أضف
--scopeبما يحتاج إليه السكربت فقط، مثل--scope application:create,application:write-any. ودون--scope، تقترح صفحة الموافقة ما يناسب دورك وتزيل أنت العلامة عن الباقي. انظر النشر من CI/CD لمعرفة النطاقات التي يحتاج إليها النشر. - تدوم 90 يومًا ما لم تختر مدّة أقصر في صفحة الموافقة.
- هناك أشياء لا تستطيعها أبدًا، مهما طلبت: الفوترة، وتعيين المسؤولين، وإنشاء بيانات الاعتماد أو إبطالها. هذه تحتاج إليك أنت، مسجّلًا دخولك في وحدة التحكّم.
- أبطِلها من صفحة CLI في وحدة التحكّم حين يُستغنى عن السكربت أو حين يُحتمل أن الرمز تسرّب.
تفترض الأمثلة أدناه:
export ISOGRID_API=https://api.isogrid.skyvault.pro/api/v1
export ISOGRID_TOKEN=skv_...
أبقِ الرمز خارج سجلّ أوامر الصدفة وخارج مستودعك، كما تفعل مع كلمة مرور.
اختيار المؤسّسة
قد ينتمي الشخص إلى عدّة مؤسّسات، فكل ما يخصّ إحداها يحتاج إلى معرفة أيّها. تقول ذلك بترويسة، تعطي فيها slug المؤسّسة أو id الخاص بها:
X-Organization: acme
وتُقبل القيمة نفسها معاملًا في العنوان، ?organization=acme، للحالات التي
تكون فيها الترويسة غير مريحة.
مع بيانات اعتماد CLI يمكنك إغفالها: فبيانات الاعتماد تخصّ مؤسّسة واحدة أصلًا
وكل طلب يعمل فيها. وتسمية مؤسّسة أخرى تُرفض بـ 403، ويذكر الخطأ المؤسّسة التي
ثُبّتت عليها بيانات الاعتماد.
كيف يبدو الخطأ
لكل رفض الشكل نفسه، أيًّا كان الخلل:
{
"error": {
"code": "permission_denied",
"message": "Your role in Acme (developer) does not allow this",
"details": {
"required_permission": "application:create",
"role": "developer",
"organization": "acme"
}
}
}
message مكتوب ليُعرض على إنسان. وcode هو ما ينبغي أن يتفرّع عليه السكربت.
وdetails يختلف باختلاف الخطأ وقد يكون فارغًا.
| الحالة | code |
المعنى |
|---|---|---|
401 |
unauthenticated |
لا رمز، أو رمز مجهول أو منتهي الصلاحية أو مُبطَل. |
402 |
insufficient_credits |
لا تستطيع المؤسّسة دفع ثمن ما طُلب. يذكر details المبلغ المطلوب. |
403 |
permission_denied |
لا يحقّ لك، أو لبيانات الاعتماد هذه، فعل ذلك. |
404 |
not_found |
غير موجود، أو ليس لك أن تراه. |
409 |
conflict |
يتعارض مع ما هو موجود: اسم مأخوذ، أو منتَج لا سعر له بعد في تلك المنطقة. |
422 |
validation_error |
الطلب غير سليم الصياغة. يسمّي details.fields كل حقل وما الخطأ فيه. |
503 |
no_capacity |
لا تستطيع المنصّة استضافة هذا الآن. الطلب لم يكن خاطئًا؛ أعد المحاولة لاحقًا. |
مع curl، استخدم -f (أو --fail-with-body للاحتفاظ بالرسالة) حتى يُفشل
الرفضُ سكربتك بدل أن يُمرَّر إلى الأمر التالي.
القوائم والصفحات
القوائم الرئيسية (التطبيقات، قواعد البيانات، خوادم قواعد البيانات، الشبكات، المناطق، الصور) تعيد صفحة واحدة في كل مرّة:
{ "items": [ ... ], "total": 37, "limit": 50, "offset": 0 }
limit قيمته الافتراضية 50 وأقصاه 200. وoffset هو موضع بداية الصفحة. لقراءة
كل شيء، أضف limit إلى offset حتى يبلغ total.
ليست كل القوائم مقسّمة هكذا. بعض القوائم القصيرة (عمليات بناء تطبيق، أنواع النسخ في منطقة) تعيد مصفوفة بسيطة. وتبيّن الأمثلة أدناه شكل كل واحدة.
ما يستغرق وقتًا
إنشاء شيء يعود قبل أن يعمل ذلك الشيء. يخبرك الجواب بأن الشيء موجود ويعطيك
id الخاص به؛ ثم تقرأ حالته حتى تستقرّ.
| ما طلبته | جواب الطلب | ثم اقرأ | إلى أن |
|---|---|---|---|
| تطبيق | 201، مع التطبيق |
GET /applications/{id}/status |
يصير deployment_status هو running أو failed |
| عملية بناء | 202، مع build_id |
GET /applications/{id}/builds/{build_id} |
يصير status هو succeeded، أو أحد failed وno_dockerfile وrestricted وcancelled |
| إعادة نشر | 202 |
GET /applications/{id}/status |
كما في التطبيق |
| قاعدة بيانات | 202، مع قاعدة البيانات |
GET /databases/{id} |
يصير status هو ready أو failed |
قيمة deployment_status لتطبيق هي إحدى none أو queued أو deploying أو
starting أو running أو degraded أو stopped أو failed. وتعني degraded
أنه يعمل لكن ليس كاملًا: نسخ عاملة أقلّ من المطلوب، أو نسخ لا تكفّ عن إعادة
التشغيل. ويقول message المرافق السبب بالكلمات.
استعلم كل بضع ثوانٍ، لا في حلقة متلاحقة. ومخرجات البناء تُقرأ بالطريقة نفسها:
يعيد GET /applications/{id}/builds/{build_id}/logs?after=0 الأسطر المكتوبة
حتى الآن مع last_id؛ مرّره في after لتحصل على الجديد فقط.
أمثلة كاملة
من أنا، وأين أستطيع النشر
curl -fsS "$ISOGRID_API/me" -H "Authorization: Bearer $ISOGRID_TOKEN"
يعيد حسابك والمؤسّسات التي تنتمي إليها. وهذه المناطق المفتوحة لك، وأنواع النسخ التي تعرضها منطقة مع أسعارها:
curl -fsS "$ISOGRID_API/clusters" -H "Authorization: Bearer $ISOGRID_TOKEN" \
| jq '.items[] | {id, slug, name}'
curl -fsS "$ISOGRID_API/pricing/applications/$CLUSTER_ID" \
-H "Authorization: Bearer $ISOGRID_TOKEN" \
| jq '.[] | {id, name, vcpu, memory_mb, prices}'
في الواجهة تُسمّى المنطقة cluster، ويُسمّى نوع النسخة resource_tier.
سرد تطبيقاتك
curl -fsS "$ISOGRID_API/applications?limit=20" \
-H "Authorization: Bearer $ISOGRID_TOKEN" \
| jq '.items[] | {id, slug, deployment_status, public_url}'
إنشاء تطبيق من صورة
curl -fsS -X POST "$ISOGRID_API/applications" \
-H "Authorization: Bearer $ISOGRID_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"name": "hello",
"source": "registry",
"external_image": "nginx:1.27",
"port": 80,
"is_public": true
}'
الجواب هو التطبيق، مع id وslug الخاصّين به، والعنوان الذي سيجيب عليه في
public_url. وأول نشر له موضوع في الطابور أصلًا.
معاني الحقول، وما يحدث حين تغفل أحدها:
| الحقل | المعنى | إن أُغفل |
|---|---|---|
name |
إلزامي. | |
source |
registry لصورة؛ وgithub أو gitlab للبناء من مستودع. |
github |
external_image |
صورة في أي سجلّ، باسمها الكامل: nginx:1.27، ghcr.io/acme/web:main. |
|
external_registry_id |
السجلّ المحفوظ الذي تُسحب الصورة ببيانات اعتماده. | يجب أن تكون الصورة عامّة. |
cluster_id |
المنطقة. | منطقة الشبكة التي سمّيتها، وإلّا فالمنطقة الافتراضية للمنصّة. |
resource_tier_id |
نوع النسخة. | أصغر ما تعرضه المنطقة. |
network_id |
الشبكة الخاصة التي يعمل عليها. | شبكة مؤسّستك في تلك المنطقة. |
port |
المنفذ الذي تستمع عليه الحاوية. | 8080 لصورة. |
replicas |
عدد النسخ، من 1 إلى 10. | 1 |
environment |
إعدادات غير سرّية، في صورة كائن من السلاسل النصّية. | لا شيء. |
is_public |
هل يمكن الوصول إليه من الإنترنت. | false |
الصورة الموجودة في سجلّ مؤسّستك تُسمّى بـ image_id بدل ذلك (يسردها
GET /images). وللبناء من مستودع، أرسل repository_full_name (acme/api)،
وdefault_branch إن لم يكن main؛ ويجب أن يكون المستودع مربوطًا بمؤسّستك
مسبقًا، كما تشرح صفحة مستودعات Git.
الأسرار لا توضع في environment. أرسلها في secrets؛ فهي تُحفظ على حدة ولا
يعيدها أي طلب أبدًا.
قراءة حالته
curl -fsS "$ISOGRID_API/applications/$APP_ID/status" \
-H "Authorization: Bearer $ISOGRID_TOKEN"
{
"application_id": "5b0c...",
"deployment_status": "running",
"desired": 1,
"running": 1,
"message": null,
"checked_at": "2026-10-07T09:12:44Z",
"listens": true,
"tasks": [ ... ]
}
desired هو عدد النسخ المطلوبة وrunning عدد النسخ العاملة الآن. وللانتظار في
سكربت:
while :; do
STATUS=$(curl -fsS "$ISOGRID_API/applications/$APP_ID/status" \
-H "Authorization: Bearer $ISOGRID_TOKEN" | jq -r '.deployment_status')
echo "$STATUS"
case "$STATUS" in running|degraded|stopped|failed) break ;; esac
sleep 5
done
النشر من جديد
لتطبيق يشغّل صورة، أعد نشره:
curl -fsS -X POST "$ISOGRID_API/applications/$APP_ID/deploy" \
-H "Authorization: Bearer $ISOGRID_TOKEN"
ولتطبيق مبنيّ من مستودع، ابدأ بناء فرع أو وسم أو إيداع؛ ويُنشر حين ينجح البناء:
curl -fsS -X POST "$ISOGRID_API/applications/$APP_ID/builds" \
-H "Authorization: Bearer $ISOGRID_TOKEN" \
-H "Content-Type: application/json" \
-d '{"git_ref": "main"}'
سرد قواعد بياناتك
curl -fsS "$ISOGRID_API/databases" -H "Authorization: Bearer $ISOGRID_TOKEN" \
| jq '.items[] | {id, name, engine, status}'
هذه هي قواعد البيانات المنشأة على خادم مشترك. أمّا خوادم قواعد البيانات الخاصة
بك فقائمة مستقلّة، GET /database-instances. وقيمة status لقاعدة بيانات هي
إحدى pending أو creating أو importing أو ready أو failed أو
deleting.
تفاصيل الاتصال، ومنها كلمة المرور، طلب مستقلّ
(GET /databases/{id}/connection) بصلاحية مستقلّة: أن ترى أن قاعدة بيانات
موجودة ليس كأن تُسلَّم بيانات اعتمادها.
حالات حدّية يحسن معرفتها قبل أن تصادفها
401 على رمز كان يعمل أمس. انتهت صلاحيته أو أُبطل. أنشئ واحدًا جديدًا؛ لا
شيء آخر يتغيّر. والجواب واحد عمدًا للرمز المجهول والمنتهي والمُبطَل.
403 يسمّي مؤسّسة أخرى. أرسلت X-Organization لمؤسّسة ليست بيانات
الاعتماد مثبّتة عليها. احذف الترويسة، أو أنشئ بيانات اعتماد بينما تعرض وحدة
التحكّم المؤسّسة التي تقصدها.
409 عند الإنشاء يذكر سعرًا. هذا المنتَج لا سعر له بعد في تلك المنطقة،
فهو غير معروض للبيع فيها. اختر منطقة أخرى أو اسأل. انظر
الأسعار والفوترة.
402 على is_public. على مؤسّستك مبلغ مستحقّ عن استخدام سابق، والنشر
للعموم موقوف حتى يُسدَّد. أنشئ التطبيق خاصًّا، أو اشحن رصيدك.
نجح طلب الإنشاء وفشل التطبيق. لم يَعِد الطلب إلا بأن التطبيق موجود. اقرأ
/status، ثم سجلّ البناء أو النشر. وتتناول صفحة
حين تسوء الأمور الأسباب المعتادة.
المبالغ بوحدة nanos. المبالغ المنتهية بـ _nanos أجزاء من مليار من
وحدة العملة: 1500000000 تساوي 1.5. والكائن prices المجاور يحمل الرقم نفسه
منسّقًا للعرض.
ماذا تقرأ بعد ذلك
- مرجع الأوامر للعمليات نفسها من الـ CLI.
- النشر من CI/CD لخطّ نشر لا يحتاج إلى أي شيفرة API.
- الأدوار ومجموعات الصلاحيات والوصول لما يمكن أن يُسمح به لبيانات الاعتماد.
- الأسعار والفوترة.