Qwen-Image-2.1 هو نموذج الصور مفتوح الأوزان الذي أصدرته علي بابا في 20 سبتمبر 2026: مولد بمعاملات 7B يتعامل مع تحويل النص إلى صورة، والتحرير باستخدام ما يصل إلى 10 صور مرجعية، وإخراج شفاف أصلي (RGBA). يرشدك هذا الدليل من pip install إلى نقطة نهاية HTTP عاملة. ويغطي مسارات التعليمات البرمجية المرجعية الأربعة من ملف GitHub README، والإعدادات المهمة، وغلاف FastAPI صغير بحيث يمكن استدعاء النموذج مثل أي واجهة برمجة تطبيقات صور أخرى، وكيفية اختبار نقطة النهاية هذه في Apidog بحيث لا تؤدي تغييرات المطالبات وتحديثات النموذج إلى تعطل تطبيقك.
إذا كنت تريد الخلفية أولاً، فإن مقالة ما هو Qwen-Image-2.1 تغطي البنية والترخيص. النسخة القصيرة من الترخيص: للاستخدام البحثي وغير التجاري فقط ما لم تحصل على اتفاقية تجارية منفصلة من Qwen. كل ما يلي مناسب للتقييم.
قبل أن تبدأ
| المتطلب | التفاصيل |
|---|---|
| حزم Python | torch>=2.4.0, transformers>=5.17, diffusers من GitHub main, accelerate, pillow |
| فئة خط الأنابيب | QwenImage21Pipeline (فئة واحدة للتوليد والتحرير) |
| الأوزان | Qwen/Qwen-Image-2.1, bf16 safetensors |
| وحدة معالجة الرسوميات (GPU) | لم تحددها Qwen؛ يستهدف الكود المرجعي جهاز CUDA واحدًا بصيغة bfloat16، مع enable_model_cpu_offload() كبديل |
| الإخراج الافتراضي | 2048 × 2048؛ 40 خطوة استدلال |
| اختياري | نماذج إعادة كتابة المطالبات Qwen-Image-2.1-PE-T2I / PE-I2I |
التثبيت:
pip install "torch>=2.4.0" "transformers>=5.17" accelerate pillow
pip install git+https://github.com/huggingface/diffusers
تم دمج `diffusers` في PR مخصص في يوم الإطلاق، لذا فإن إصدار PyPI الأقدم من 20 سبتمبر لن يحتوي على فئة خط الأنابيب.
الخطوة 1: تحويل النص إلى صورة
import torch
from diffusers import QwenImage21Pipeline
pipe = QwenImage21Pipeline.from_pretrained(
"Qwen/Qwen-Image-2.1", torch_dtype=torch.bfloat16
).to("cuda")
image = pipe(
prompt='A neon shop sign that reads "QWEN IMAGE 2.1", rainy night, reflections on wet pavement',
num_inference_steps=40,
generator=torch.Generator("cuda").manual_seed(42),
).images[0]
image.save("t2i_example.png")
شيئان يجب ملاحظتهما. المطالبة تضع نص اللافتة بين علامتي اقتباس؛ يعد عرض نص Qwen هو السبب الذي يجعل الناس يختارون هذا الخط من النماذج، واقتباس السلسلة الحرفية هو الاتفاقية من الإصدارات السابقة. والبذرة واضحة. حافظ عليها بهذه الطريقة في كل طلب تنوي اختباره، لأن البذرة الثابتة هي التي تجعل نقطة نهاية الصورة قابلة للتكرار بما يكفي للتأكيد عليها.
مرر width و height من الجدول المدعوم عندما تحتاج إلى إخراج غير مربع:
| النسبة | الحجم |
|---|---|
| 1:1 | 2048 × 2048 |
| 4:3 / 3:4 | 2400 × 1792 / 1792 × 2400 |
| 3:2 / 2:3 | 2528 × 1696 / 1696 × 2528 |
| 16:9 / 9:16 | 2752 × 1536 / 1536 × 2752 |
الخطوة 2: إخراج شفاف
الشفافية تعتمد على المطالبة. الصياغة الموصى بها في ملف README حرفية، لذا استخدمها:
image = pipe(
prompt=(
"This is an RGBA image with transparency. A cute cartoon dragon sticker. "
"The image has alpha channel and the background is transparent."
),
num_inference_steps=40,
generator=torch.Generator("cuda").manual_seed(42),
).images[0]
image.save("transparent_example.png")
تحقق من النتيجة بدلاً من الوثوق بها:
assert image.mode == "RGBA", image.mode
alpha = image.getchannel("A")
print("transparent pixels:", sum(1 for p in alpha.getdata() if p == 0))
هذا التأكيد هو الاختبار الأول الذي ستقوم بنقله إلى Apidog لاحقًا. النموذج الذي يعيد صامتًا RGB عندما طلبت RGBA هو خطأ سيجده المستخدمون قبل أن تجده أنت.
الخطوة 3: التحرير، بصورة واحدة أو حتى عشر صور
نفس خط الأنابيب يقوم بالتحرير عندما تمرر image:
from PIL import Image
input_image = Image.open("input.png")
edited = pipe(
prompt="Change the background to a sunset beach",
image=input_image,
num_inference_steps=40,
generator=torch.Generator("cuda").manual_seed(42),
).images[0]
edited.save("edit_example.png")
للحصول على مراجع متعددة، مرر قائمة (الحد الأقصى في منشور الإطلاق هو 10):
refs = [Image.open(f"ref_{i}.png") for i in range(3)]
result = pipe(
prompt="These three characters are sitting around a campfire in a forest",
image=refs,
num_inference_steps=40,
generator=torch.Generator("cuda").manual_seed(42),
).images[0]
result.save("multi_ref_example.png")
يعمل التحرير المحلي بثلاث طرق في منشور الإطلاق: دوائر ملونة تشير إليها باللون في المطالبة، تعليقات توضيحية مرسومة، أو الصورة الأصلية غير المعدلة بالإضافة إلى صورة قناع منفصلة يتم تمريرها كمدخلين. لا يقدم ملف README مثالًا مخصصًا للقناع، لذا فإن الشكل ذو المدخلين هو الذي يجب تجربته أولاً: image=[original, mask] مع مطالبة تصف ما يظهر في المنطقة المقنعة [تحقق من ذلك مقابل README بمجرد توفر مثال للقناع].
التحرير هو أيضًا المكان الذي يظهر فيه عمل سرعة 2.1. الصور المرجعية والتعليمات ثابتة عبر خطوات إزالة الضوضاء، لذا يقوم النموذج بحساب ذاكرة التخزين المؤقت للقيم الرئيسية مرة واحدة ويعيد استخدامها. تكلفة عشرة مراجع أقل بكثير من عشرة أضعاف تكلفة مرجع واحد.
الخطوة 4: اجعله يتناسب مع وحدة معالجة الرسوميات (GPU) الخاصة بك
لم تنشر Qwen أرقام VRAM. إذا لم يتناسب خط أنابيب bf16، يقدم ملف README ما يلي:
pipe = QwenImage21Pipeline.from_pretrained("Qwen/Qwen-Image-2.1", torch_dtype=torch.bfloat16)
pipe.enable_model_cpu_offload()
بالنسبة للتشغيل، يشير ملف README إلى vLLM-Omni (مع FP8) و SGLang و LightX2V. يدعم ComfyUI دعمًا أصليًا مع سير عمل نموذجي إذا كنت لا ترغب في كتابة أي بايثون على الإطلاق. وإذا لم يكن لديك وحدة معالجة رسوميات (GPU)، فإن الخيارات المجانية تغطي العرض التجريبي المستضاف و Qwen Chat.
الخطوة 5: تغليفه كواجهة برمجة تطبيقات HTTP
يجب ألا تستورد تعليمات التطبيق البرمجية مكتبة diffusers. ضع خط الأنابيب خلف خدمة صغيرة بحيث يكون لديها عقد يمكنك إصدار إصدارات منه، ومحاكاته، واختباره. هذا الغلاف الخاص بـ FastAPI يتكون من حوالي 40 سطرًا ويعيد بايتات PNG:
# server.py
import io, torch
from fastapi import FastAPI, UploadFile, File, Form
from fastapi.responses import Response
from PIL import Image
from diffusers import QwenImage21Pipeline
app = FastAPI()
pipe = QwenImage21Pipeline.from_pretrained(
"Qwen/Qwen-Image-2.1", torch_dtype=torch.bfloat16
).to("cuda")
SIZES = {"1:1": (2048, 2048), "16:9": (2752, 1536), "9:16": (1536, 2752)}
@app.post("/v1/images")
async def generate(
prompt: str = Form(...),
aspect: str = Form("1:1"),
transparent: bool = Form(False),
seed: int = Form(42),
steps: int = Form(40),
references: list[UploadFile] = File(default=[]),
):
if transparent and not prompt.startswith("This is an RGBA image"):
prompt = ("This is an RGBA image with transparency. " + prompt +
" The image has alpha channel and the background is transparent.")
refs = [Image.open(io.BytesIO(await f.read())) for f in references[:10]]
w, h = SIZES.get(aspect, SIZES["1:1"])
kwargs = dict(prompt=prompt, num_inference_steps=steps,
generator=torch.Generator("cuda").manual_seed(seed))
if refs:
kwargs["image"] = refs if len(refs) > 1 else refs[0]
else:
kwargs.update(width=w, height=h)
image = pipe(**kwargs).images[0]
buf = io.BytesIO()
image.save(buf, format="PNG")
return Response(buf.getvalue(), media_type="image/png",
headers={"X-Image-Mode": image.mode, "X-Seed": str(seed)})
شغّله باستخدام uvicorn server:app --port 8000. رأسا الاستجابة X-Image-Mode و X-Seed موجودان بحيث يمكن للاختبار التحقق من الشفافية وقابلية التكرار دون فك ترميز PNG. هذا هو الخيار الوحيد الخاص بالمنتج في الغلاف؛ والباقي هو نقطة نهاية multipart عادية.
الخطوة 6: اختبار نقطة النهاية في Apidog
الآن أصبحت واجهة برمجة تطبيقات (API)، وتنطبق هنا نفس الانضباط الذي تطبقه على واجهة برمجة تطبيقات gpt-image-2.5 أو واجهة برمجة تطبيقات Nano Banana 2. في Apidog:
- أنشئ نقطة النهاية كـ
POST {{base_url}}/v1/imagesمع جسم متعدد الأجزاء:prompt،aspect،transparent،seed،steps، وحقل ملفreferencesقابل للتكرار. ضعbase_urlفي بيئة بحيث تشير نفس المجموعة إلى جهاز الكمبيوتر المحمول الخاص بك، أو صندوق GPU، أو محاكاة. - أرسل طلبًا لتحويل النص إلى صورة باستخدام
seed=42ومطالبة لافتة النيون. تأكد من200،Content-Type: image/png، وX-Image-Mode: RGB. - أضف تأكيدات في المعالج اللاحق: الحالة هي 200،
X-Image-ModeتساويRGBAعندما يكونtransparent=true، حجم جسم الاستجابة فوق حد أدنى (صورة PNG بحجم 2K تعود بحجم 2 كيلوبايت هي صورة فارغة)، وX-Seedتعكس ما أرسلته. - أرسل حالة الشفافية وتعديلًا بثلاثة مراجع بنفس الطريقة، مع إرفاق الصور في حقل الملف. احفظ كل حالة كحالة اختبار.
- شغلها كسيناريو اختبار وفق جدول زمني أو في CI. عندما تقوم بتبديل بنية كمية أو إصدار 2.2 مستقبلي، تخبرك المجموعة في دقائق ما إذا كانت الشفافية لا تزال تعمل وما إذا كانت البذرة لا تزال قابلة للتكرار.
- احاكيها بينما تكون وحدة معالجة الرسوميات مشغولة. يعيد الموك الذكي الخاص بـ Apidog صورة PNG معلبة لنفس العقد، بحيث يواصل الواجهة الأمامية البناء.
بما أن Apidog يقوم أيضًا بإنشاء مواصفات ووثائق OpenAPI من نقطة النهاية التي حددتها، يصبح عقد الغلاف قابلاً للمشاركة بمجرد أن يعمل. قم بتنزيل Apidog واستورد نقطة النهاية أعلاه للبدء.
اختياري: إعادة كتابة المطالبة باستخدام PE-T2I
يحول Space التجريبي الطلبات المكونة من سطر واحد إلى مطالبات منظمة طويلة باستخدام Qwen-Image-2.1-PE-T2I، وهو نموذج Qwen3.5-VL 9B معدّل خصيصًا يعيد JSON مع مطالبة إنجليزية موسعة ونسبة أبعاد موصى بها. قم بتشغيله كخدمة ثانية أمام /v1/images، أو تخطيه واكتب المطالبات الكاملة بنفسك. إذا أضفته، اختبره بشكل منفصل: إنه واجهة برمجة تطبيقات نصية بعقد JSON، وينتج عن إعادة كتابة معطلة صورًا سيئة تبدو وكأنها خطأ في المولد.
الأسئلة الشائعة
هل يعمل خط أنابيب واحد على التوليد والتحرير؟ نعم. يقوم QwenImage21Pipeline بالتوليد عند استدعائه بمطالبة فقط ويقوم بالتحرير عندما تمرر image (صورة PIL واحدة أو قائمة تصل إلى 10 صور).
كيف أحصل على صورة PNG شفافة؟ ابدأ المطالبة بـ "هذه صورة RGBA بشفافية" وقل إن الخلفية شفافة. تحقق من image.mode == "RGBA" على النتيجة.
ما هي الإعدادات الموصى بها؟ 40 خطوة استدلال و bfloat16، وفقًا لملف README. قيم الإرشاد غير مدرجة لـ 2.1؛ استخدمت إصدارات Qwen-Image السابقة true_cfg_scale=4.0، لذا جرب ذلك إذا بدت المخرجات غير موجهة بشكل كافٍ [تحقق].
هل يمكنني استخدام هذا في منتج تجاري؟ ليس بموجب الترخيص الافتراضي. يتم شحن Qwen-Image-2.1 بموجب ترخيص Qwen Research؛ يتطلب الاستخدام التجاري ترخيصًا منفصلاً من Qwen. التفاصيل في ما هو Qwen-Image-2.1.
هل توجد واجهة برمجة تطبيقات مستضافة بدلاً من ذلك؟ Qwen Image 3.0 و 3.0 Pro هما نماذج صور مستضافة من علي بابا بأسعار لكل صورة. تغطي مقارنة 2.1 مقابل 3.0 متى يتم الاستضافة الذاتية ومتى يتم الاستئجار.
إلى أين تذهب بعد ذلك
لديك الآن أربع مكالمات عاملة، وغلاف بعقد ثابت، ومجموعة اختبار تتحقق من أهم خاصيتين لهذا النموذج، الشفافية وقابلية التكرار. بعد ذلك، قرر ما إذا كان ترخيص البحث يناسب استخدامك، أو ما إذا كانت واجهة برمجة تطبيقات 3.0 المستضافة هي الأنسب، واحتفظ بكلا الاثنين خلف نفس مجموعة Apidog بحيث يكون التبديل مجرد تغيير لعنوان URL الأساسي، وليس إعادة كتابة.
