Qwen 图像编辑快速入门:使用文本指令编辑图像

Qwen 图像编辑快速入门:使用文本指令编辑图像

Novita AI 上的 Qwen 图像编辑 API 使用自然语言指令修改现有图像,由 20B 参数的 Qwen-Image 模型驱动。本快速入门涵盖了完整的异步工作流:提交包含源图像和提示词的编辑请求,接收任务 ID,轮询直至编辑完成,并获取编辑后的图像 URL。端点为 POST https://api.novita.ai/v3/async/qwen-image-edit

目录

何时使用本快速入门

当你需要以下功能时,请使用本指南:

  • 通过文本指令修改现有图像 — 更改背景、切换风格、移除元素、旋转物体或调整衣物,而无需从头重建图像。
  • 保持未修改区域不变,同时进行针对性编辑。模型的双路径架构(Qwen2.5-VL 用于语义理解 + VAE 编码器用于外观保留)专门设计用于防止编辑渗透到你未描述的区域。
  • 精确编辑图像中的文字。Qwen 图像编辑可处理标志、海报和品牌资产中双语英文字母与中文字符的替换 — 保留字体、大小和周围视觉风格,这是大多数图像生成器难以做到的。

如果你仅根据提示词生成新图像(无需输入图像),请改用 Qwen 图像 txt2img 快速入门。有关模型能力、基准测试和架构的完整概述,请参阅 Qwen-Image on Novita AI 发布文章

第一步:获取 Novita API 密钥

创建一个 Novita AI 账户,并导航至 API 密钥管理 页面。生成一个密钥,并在运行以下任何代码示例前将其存储为环境变量:

export NOVITA_API_KEY="your_api_key_here"

请确保密钥不暴露在客户端代码、前端打包文件或版本控制中。如果密钥泄露,请从同一设置页面轮换它。

第二步:确认端点与模型

项目
编辑端点 POST https://api.novita.ai/v3/async/qwen-image-edit
结果轮询端点 GET https://api.novita.ai/v3/async/task-result?task_id=<id>
模型 Qwen Image Edit(20B MMDiT,双路径架构)
API 文档 Novita AI Qwen Image Edit 参考

API 是异步的。编辑调用立即返回一个 task_id;你轮询结果端点,直到状态变为 TASK_STATUS_SUCCEED。这是所有 Novita AI 图像生成端点(包括 txt2img 端点)使用的相同两步模式。

价格为每张图像 $0.02。在构建成本模型之前,请查看 Novita AI 定价页面 确认当前费率。

第三步:发送你的第一个编辑请求

向编辑端点 POST 请求,包含源图像和编辑指令:

curl -s -X POST https://api.novita.ai/v3/async/qwen-image-edit \
  -H "Authorization: Bearer $NOVITA_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "prompt": "将背景更改为雪山景观",
    "image": "https://example.com/my-portrait.jpg"
  }'

成功的 200 响应返回:

{
  "task_id": "abc123..."
}

保存 task_id — 你需要它来检索编辑后的图像。

第四步:轮询获取结果

使用 task_id 作为查询参数,GET 任务结果端点:

curl -s "https://api.novita.ai/v3/async/task-result?task_id=abc123..." \
  -H "Authorization: Bearer $NOVITA_API_KEY"

持续轮询,直到 task_status 字段变为 TASK_STATUS_SUCCEED

{
  "task_status": "TASK_STATUS_SUCCEED",
  "images": [
    {
      "image_url": "https://...",
      "image_url_ttl": "86400",
      "image_type": "JPEG"
    }
  ]
}

image_url 在 TTL 窗口(通常为 24 小时)后过期。如果需要长期访问,请下载并将结果存储到你自己的对象存储中。

需要处理的状态值:

状态 含义
TASK_STATUS_QUEUED 请求正在排队等待;继续轮询
TASK_STATUS_PROCESSING 编辑正在进行中;继续轮询
TASK_STATUS_SUCCEED 完成;从 images[0].image_url 读取编辑后的图像
TASK_STATUS_FAILED 生成失败;检查 error 字段了解原因

第五步:检查定价、限制和常见错误

定价:每张图像 $0.02(请查看 定价页面 确认)。

速率限制:请查看 API 参考 了解当前速率限制。如果遇到 429 错误,请降低请求速率并在重试时实现指数退避。

常见 HTTP 错误

状态码 可能的原因
400 请求体格式错误 — 缺少 promptimage,无效的图像格式,或不支持的输入尺寸
401 缺少或无效的 API 密钥 — 确认 Authorization: Bearer <key> 格式
429 超出速率限制 — 添加退避和重试逻辑
500 服务器端错误 — 短暂延迟后重试

如果任务状态为 TASK_STATUS_FAILED,响应通常包含错误消息。常见原因包括不支持的图像格式、超出大小限制的图像,或触发内容安全过滤器的提示词。

Python 示例

此脚本提交编辑请求,轮询直到完成,并打印输出图像 URL:

import os
import time
import requests

API_KEY = os.environ["NOVITA_API_KEY"]
BASE_URL = "https://api.novita.ai/v3/async"


def submit_edit(image: str, prompt: str, seed: int | None = None) -> str:
    payload: dict = {"prompt": prompt, "image": image}
    if seed is not None:
        payload["seed"] = seed
    response = requests.post(
        f"{BASE_URL}/qwen-image-edit",
        headers={
            "Authorization": f"Bearer {API_KEY}",
            "Content-Type": "application/json",
        },
        json=payload,
    )
    response.raise_for_status()
    return response.json()["task_id"]


def poll_result(task_id: str, interval: float = 2.0, timeout: float = 120.0) -> dict:
    deadline = time.time() + timeout
    while time.time() < deadline:
        response = requests.get(
            f"{BASE_URL}/task-result",
            headers={"Authorization": f"Bearer {API_KEY}"},
            params={"task_id": task_id},
        )
        response.raise_for_status()
        data = response.json()
        status = data.get("task_status", "")
        if status == "TASK_STATUS_SUCCEED":
            return data
        if status == "TASK_STATUS_FAILED":
            raise RuntimeError(f"编辑任务失败: {data}")
        time.sleep(interval)
    raise TimeoutError(f"任务 {task_id} 在 {timeout} 秒内未完成")


if __name__ == "__main__":
    task_id = submit_edit(
        image="https://example.com/product-photo.jpg",
        prompt="将夹克换成红色皮夹克,保留背景",
    )
    print(f"任务 ID: {task_id}")

    result = poll_result(task_id)
    for img in result["images"]:
        print(img["image_url"])

cURL 示例

使用 jq 解析 JSON 的两步命令工作流:

#!/bin/bash
# 步骤 1:提交编辑请求
TASK_ID=$(curl -s -X POST https://api.novita.ai/v3/async/qwen-image-edit \
  -H "Authorization: Bearer $NOVITA_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "prompt": "转换为水彩画风格,保留主体和构图",
    "image": "https://example.com/landscape.jpg"
  }' | jq -r '.task_id')

echo "任务 ID: $TASK_ID"

# 步骤 2:轮询直到完成
while true; do
  RESULT=$(curl -s "https://api.novita.ai/v3/async/task-result?task_id=$TASK_ID" \
    -H "Authorization: Bearer $NOVITA_API_KEY")
  STATUS=$(echo "$RESULT" | jq -r '.task_status')
  echo "状态: $STATUS"
  if [ "$STATUS" = "TASK_STATUS_SUCCEED" ]; then
    echo "$RESULT" | jq -r '.images[].image_url'
    break
  elif [ "$STATUS" = "TASK_STATUS_FAILED" ]; then
    echo "任务失败:"
    echo "$RESULT" | jq .
    exit 1
  fi
  sleep 2
done

如果系统中没有 jq,请使用 apt install jq(Debian/Ubuntu)或 brew install jq(macOS)安装。

关键参数

参数 类型 必填 默认值 描述
prompt string 描述所需编辑的自然语言指令
image string 源图像,可为 URL 或 base64 编码的字符串
seed integer 随机 固定种子,用于跨多次运行获得可重复的输出
output_format string jpeg 输出格式 — 请参考 API 文档了解可接受的值

编写有效的提示词:具体性很重要。“将广告牌上的文字改为‘夏季促销’”给模型一个清晰、有限的任务。“改善图像”则不行。当你只想更改一个元素而保持其他所有内容不变时,请明确你希望保留的内容:“将夹克颜色改为红色,保持背景和脸部不变。”这有助于 VAE 编码器路径发挥其锁定未修改区域的作用。

使用 seed 进行迭代:在调整提示词时,固定种子可以让你直接比较编辑结果 — 输出变化来自提示词的更改,而非随机采样。一旦找到有效的提示词,如果你希望多次编辑的输出有多样性,可以移除种子约束。

典型用例

背景替换:“将背景替换为极简白色工作室” — Qwen 图像编辑在更换环境的同时保留主体的边缘和光照。当主体与原始背景有清晰边界时,效果可靠。

图像中的文字:替换商店招牌、海报标题或产品标签上的文字 — 包括中文和英文。该模型在保留字体样式和周围视觉上下文方面优于生成式内绘方法,后者往往会重新生成整个区域。

风格转换:“转换为油画风格”或“使其看起来像铅笔素描”应用于源图像,而非从头描述。VAE 编码器路径保留原始构图和物体位置,而提示词驱动风格转换。

物体级别更改:更换衣物、更改特定物品的颜色、添加或移除配饰。指令应指明要更改的具体元素,以防止编辑影响相邻区域。

IP 转换与物体旋转:模型支持视图合成更改(例如旋转物体以显示不同角度),以及角色或产品图像的视觉风格转换 — 相关用例记录在 Qwen-Image-Edit on Novita AI 概述 中。

故障排除

输出看起来未更改:指令可能不够具体。请更明确地指定要针对哪个元素:“将汽车颜色从蓝色改为红色”,而不是“把它变成红色”。

不当编辑扩散到未预想区域:对于高度特定的局部编辑,请在提示词中包含明确的保留语言:“仅更改 X,保持 Y 不变。”过于开放的提示词会赋予模型重新解释整个构图的空间。

任务完成但图像 URL 返回 403 或 404image_url_ttl 字段(以秒为单位)告诉你 URL 的有效期。如果你在 TTL 之后才轮询该 URL,则 URL 已过期。成功轮询后请立即下载图像。

401 未授权:确认 Authorization 头的格式为 Bearer <key>,且 Bearer 后有一个空格。确认密钥处于活动状态且未被撤销,可在 Novita AI 控制台 中查看。

任务始终超时:图像编辑比文本生成耗时更长 — 正常负载下通常为 15–60 秒。如果任务总是超过你的超时时间,请增加轮询窗口,然后再将其视为失败。

常见问题

源图像会保留在 Novita 的服务器上吗?

你的图像通过 HTTPS 上传到 Novita AI 的 API,并在其基础设施上处理。在发送包含敏感个人信息、私人健康数据或机密内容的图像之前,请查看 Novita AI 的数据处理政策。

我可以使用 base64 编码的图像而不是 URL 吗?

可以。在 image 字段中传递原始的 base64 字符串。有关 base64 负载的大小限制,请参考 API 参考

是否有用于一致性的 seed 参数?

有 — 可选的 seed 参数固定随机状态,使相同的提示词和图像产生一致的结果。在迭代提示词措辞时非常有用,可以避免重新采样带来的输出噪音。

我可以使用此端点进行批量任务吗?

可以。并行提交多个编辑请求并收集 task_id 值,然后并发轮询它们。每个请求都是独立的。

此端点与 Qwen 图像 txt2img 端点有何区别?

编辑端点需要一张源图像,并生成它的修改版本。txt2img 端点 完全根据文本提示生成图像 — 无需输入图像。当你已有要修改的内容时使用编辑端点;当你要从头创建时使用 txt2img。

推荐文章