محادثة متعددة الخطوات
واجهة برمجة تطبيقات CloudZIR عديمة الحالة : لا تحتفظ بأي ذاكرة بين طلبين. لإجراء محادثة، أنتم من يعيد إرسال التاريخ في كل استدعاء.
المبدأ#
يحتوي كل استدعاء على القائمة الكاملة للرسائل المتبادلة حتى الآن. يقرأ النموذج هذه القائمة وينتج الرسالة التالية :
Tour 1 → [system, user₁] → assistant₁
Tour 2 → [system, user₁, assistant₁, user₂] → assistant₂
Tour 3 → [system, user₁, assistant₁, user₂, ...] → assistant₃
مثال كامل#
from openai import OpenAI
client = OpenAI(api_key="zir_ai_...", base_url="https://api.cloudzir.com/v1")
messages = [{"role": "system", "content": "Tu es un assistant concis, en français."}]
def demander(texte: str) -> str:
messages.append({"role": "user", "content": texte})
reponse = client.chat.completions.create(model="mina-low", messages=messages)
contenu = reponse.choices[0].message.content
# ÉTAPE CLÉ : on remet la réponse dans l'historique
messages.append({"role": "assistant", "content": contenu})
return contenu
print(demander("Quelle est la capitale de l'Algérie ?"))
print(demander("Et sa population ?")) # « sa » = celle d'Alger : le contexte est conservéimport OpenAI from "openai";
const client = new OpenAI({
apiKey: process.env.CLOUDZIR_API_KEY,
baseURL: "https://api.cloudzir.com/v1",
});
const messages = [
{ role: "system", content: "Tu es un assistant concis, en français." },
];
async function demander(texte) {
messages.push({ role: "user", content: texte });
const r = await client.chat.completions.create({ model: "mina-low", messages });
const contenu = r.choices[0].message.content;
messages.push({ role: "assistant", content: contenu });
return contenu;
}
console.log(await demander("Quelle est la capitale de l'Algérie ?"));
console.log(await demander("Et sa population ?"));curl https://api.cloudzir.com/v1/chat/completions \
-H "Authorization: Bearer $CLOUDZIR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "mina-low",
"messages": [
{"role": "system", "content": "Tu es un assistant concis, en français."},
{"role": "user", "content": "Quelle est la capitale de l Algérie ?"},
{"role": "assistant", "content": "Alger."},
{"role": "user", "content": "Et sa population ?"}
]
}'عدم إعادة إدراج رد المساعد في messages. يفقد النموذج حينها
الخيط ويكرر نفسه : كل جولة تبدو له وكأنها الأولى.
الأدوار#
| الدور | الاستخدام |
|---|---|
system | تعليمات دائمة : النبرة، اللغة، النطاق، القواعد. توضع أولًا. |
user | ما يقوله المستخدم النهائي. |
assistant | ما ردّ به النموذج (يُعاد إرساله كما هو). |
tool | نتيجة أداة نفّذتموها (استدعاء الأدوات). |
يُقبَل developer كمرادف لـsystem.
التحكم في الطول (والتكلفة)#
يُعاد فوترة التاريخ في كل جولة. ثلاث استراتيجيات، من الأبسط إلى الأدق :
1. نافذة متحركة#
MAX_TOURS = 12
def tronquer(messages: list[dict]) -> list[dict]:
"""Garde le message système + les N derniers messages."""
systeme = [m for m in messages[:1] if m["role"] == "system"]
reste = messages[len(systeme):]
return systeme + reste[-MAX_TOURS * 2:]
2. ملخص الجولات القديمة#
def compacter(client, messages: list[dict]) -> list[dict]:
"""Remplace les vieux échanges par un résumé - moins cher que de tout garder."""
systeme, anciens, recents = messages[:1], messages[1:-8], messages[-8:]
if len(anciens) < 6:
return messages
resume = client.chat.completions.create(
model="mina-flash", # le résumé n'a pas besoin du gros modèle
messages=[
{"role": "system", "content": "Résume ces échanges en 5 points factuels."},
{"role": "user", "content": str(anciens)},
],
max_tokens=300,
).choices[0].message.content
return systeme + [{"role": "system", "content": f"Résumé des échanges précédents : {resume}"}] + recents
3. التحقق قبل الإرسال#
إذا تجاوز السياق المُقدَّر نافذة النموذج، تجيب واجهة API بالرمز 400
مع رسالة صريحة. توقعوا ذلك بتقريب «الأحرف ÷ 4» الموصوف في
الرمز واستخدامه، واختاروا نموذجًا بنافذة
أوسع عند الحاجة (mina-full يصل إلى 256 000 رمز ؛ انظروا
النماذج والأسعار).
حفظ محادثة#
خزّنوا قائمة messages في قاعدتكم (سطر لكل رسالة، مع معرّف
المحادثة) وأعيدوا تحميلها في الجولة التالية. لا تخزّنوا أبدًا مفتاح API في
المتصفح : يجب أن ينطلق الاستدعاء من خادمكم.
لا تستخدم CloudZIR محتوى إدخالاتكم لتدريب النماذج. في استدعاءات المحادثة المتزامنة، تمرّر
مسارات واجهة API الرسائل والصور إلى المحرك دون تسجيلها في قاعدة بيانات الواجهة؛ وتُسجّل بيانات
الاستخدام اللازمة للفوترة والدعم. تُخزَّن الملفات المرفوعة عبر
API الملفات بشكل منفصل، وتحذفها
DELETE /v1/files/{file_id}؛ ولا تُطبّق عليها مدة انتهاء تلقائية. انظروا أيضًا التخزين المؤقت للسياق و
الأسئلة الشائعة.