jackwener/OpenCLI · error · CommandExecutionError

Failed to fetch generated Qianwen image ${i + 1}: status=${a

Error message

Failed to fetch generated Qianwen image ${i + 1}: status=${asset?.status || '?'}

What it means

After URLs are collected, clis/qwen/image.js calls fetchImageAsset(page, url) for each one; if the asset is not ok it throws CommandExecutionError('Failed to fetch generated Qianwen image N: status=...') including the HTTP status or '?' when unknown. The generated image exists but downloading it failed.

Source

Thrown at clis/qwen/image.js:166

        const waitResult = await waitForImageUrls(page, targetId, timeout);
        const link = await page.evaluate('window.location.href').catch(() => 'https://www.qianwen.com/');
        if (waitResult.status === 'auth_required') throw authRequired();
        if (waitResult.status === 'timeout') {
            throw new TimeoutError('qianwen image', timeout, 'No generated images observed before timeout.');
        }

        const urls = waitResult.urls;
        if (skipDownload) {
            return [{ Status: '🎨 generated', File: null, Link: link }];
        }

        const stamp = Date.now();
        const results = [];
        for (let i = 0; i < urls.length; i += 1) {
            const url = urls[i];
            const asset = await fetchImageAsset(page, url);
            if (!asset?.ok) {
                throw new CommandExecutionError(`Failed to fetch generated Qianwen image ${i + 1}: status=${asset?.status || '?'}`);
            }
            const suffix = urls.length > 1 ? `_${i + 1}` : '';
            const ext = extFromMime(asset.mime);
            const filePath = path.join(outputDir, `qianwen_${stamp}${suffix}${ext}`);
            await saveBase64ToFile(asset.base64, filePath);
            results.push({ Status: '✅ saved', File: displayPath(filePath), Link: link });
        }
        if (!results.length) {
            throw new EmptyResultError('qwen image', 'No generated images were available to download.');
        }
        return results;
    },
});

View on GitHub (pinned to 49907e53dc)

Solutions

  1. Re-run the command so fresh URLs are generated and downloaded immediately (avoids expired signed links)
  2. Note the status in the message: 403/401 -> re-login to qianwen.com; 404 -> URL expired, regenerate
  3. Reduce delay between generation and download; avoid caching URLs across runs
  4. If '?' and reproducible, check network/proxy access to the image CDN host from the automation browser
Defensive patterns

Strategy: try-catch

Validate before calling

null

Type guard

null

Try / catch

try {
  await downloadGeneratedImages(urls);
} catch (e) {
  const m = e.message.match(/status=(\d+|\?)/);
  const status = m && m[1];
  if (status === '401' || status === '403') {
    await relogin(page);                   // refresh cookies, then regenerate
  } else if (status === '404' || status === '?') {
    await regenerateAndDownload(prompt);   // signed URL expired; get fresh URLs
  } else throw e;
}

Prevention

When it happens

Trigger: The image CDN URL expired (signed URLs with short TTL) by download time; fetch returned 403/404 from the page context; the URL points to a domain blocked by the browser session's cookies/headers; asset?.status is undefined giving '?' on a network-level failure.

Common situations: Waiting too long between generation and download so signed links expire; proxy/firewall stripping the CDN request; multiple images where one of several URLs 404s; rate limiting on the CDN after several downloads.

Related errors


AI-assisted analysis of jackwener/OpenCLI@49907e53dc (2026-08-29). Data as JSON: /api/errors/feb5a5c1620e90aa. Report an issue: GitHub.