{"record":{"id":"d4807e88e31d4626","repo":"anomalyco/sst","slug":"failed-to-initialize-assets-upload-no-jwt-receive","errorCode":null,"errorMessage":"failed to initialize assets upload: no JWT received","messagePattern":"failed to initialize assets upload: no JWT received","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"pkg/server/resource/cloudflare-worker-assets.go","lineNumber":208,"sourceCode":"\t}\n\tdefer resp.Body.Close()\n\n\t// print out response body as a string\n\tif resp.StatusCode != http.StatusOK {\n\t\tresponseBody, _ := io.ReadAll(resp.Body)\n\t\treturn nil, fmt.Errorf(\"failed to initialize assets upload: HTTP %d %s\", resp.StatusCode, string(responseBody))\n\t}\n\n\tvar result struct {\n\t\tResult InitializeAssetsResponse `json:\"result\"`\n\t}\n\n\tif err := json.NewDecoder(resp.Body).Decode(&result); err != nil {\n\t\treturn nil, err\n\t}\n\n\tif result.Result.Jwt == \"\" {\n\t\treturn nil, fmt.Errorf(\"failed to initialize assets upload: no JWT received\")\n\t}\n\n\treturn &result.Result, nil\n}\n\nfunc (r *WorkerAssets) uploadAssets(manifest AssetManifest, directory, accountId, apiToken string, hashes []string, jwt string) (string, error) {\n\tvar body bytes.Buffer\n\twriter := multipart.NewWriter(&body)\n\n\tfor _, hash := range hashes {\n\t\t// Find the file path for this hash in the manifest\n\t\tvar fileKey string\n\t\tvar contentType string\n\t\tfor path, entry := range manifest {\n\t\t\tif entry.Hash == hash {\n\t\t\t\tfileKey = path\n\t\t\t\tcontentType = entry.ContentType\n\t\t\t\tbreak","sourceCodeStart":190,"sourceCodeEnd":226,"githubUrl":"https://github.com/anomalyco/sst/blob/a0bd20f762883e72a35caccb4896c42ce5b3f707/pkg/server/resource/cloudflare-worker-assets.go#L190-L226","documentation":"Cloudflare returned HTTP 200 for the assets-upload-session request, but the decoded result.jwt field was empty. The JWT is the session token required to authorize subsequent asset uploads, so the library refuses to continue without it. This typically indicates an unexpected API response shape or an API-side anomaly.","triggerScenarios":"Cloudflare responds 200 but with a JSON body whose result.jwt is missing or empty — e.g. an API schema change, an error payload wrapped in a 200, or a response where result.success is false but the HTTP status is still 200.","commonSituations":"Cloudflare API version drift changing the response envelope; the token being valid but the session creation silently failing server-side; proxy/gateway injecting a 200 HTML or partial JSON page that decodes into a zero-value struct.","solutions":["Log the raw response body when jwt is empty to see what Cloudflare actually returned.","Retry the deploy — transient API-side session failures often clear.","Check Cloudflare's API changelog/status for changes to the assets-upload-session response schema.","Ensure no proxy or corporate gateway is rewriting the response (decode errors or empty bodies from HTML pages).","Report/upgrade if the platform's response parsing is out of date with the current Cloudflare API."],"exampleFix":null,"handlingStrategy":"retry","validationCode":"// after a session call, assert the envelope before trusting it\nif (!data.success || !data.result || typeof data.result.jwt !== \"string\" || !data.result.jwt) {\n  throw new Error(`unexpected session response: ${JSON.stringify(data).slice(0, 500)}`);\n}","typeGuard":"function hasJwt(r: unknown): r is { result: { jwt: string; buckets: string[][] } } {\n  const o = r as any;\n  return !!o && typeof o === \"object\" &&\n    typeof o.result?.jwt === \"string\" && o.result.jwt.length > 0 &&\n    Array.isArray(o.result?.buckets);\n}","tryCatchPattern":"try {\n  session = await initAssetSession(manifest);\n} catch (e) {\n  if (String(e).includes(\"no JWT received\")) {\n    console.error(\"Cloudflare returned 200 without a session JWT - check raw response/API version\");\n    session = await retryWithBackoff(() => initAssetSession(manifest), { attempts: 3 });\n  } else throw e;\n}","preventionTips":["Log the raw HTTP body on any empty-jwt response","Retry session creation on empty JWT (transient API behavior)","Watch Cloudflare API changelog for response schema changes","Bypass/inspect corporate proxies that can rewrite API responses"],"tags":["cloudflare","api","jwt","response-parsing"],"backgroundTag":"jwt-token-missing-from-response","analyzedSha":"a0bd20f762883e72a35caccb4896c42ce5b3f707","analyzedAt":"2026-08-30T11:26:00.383Z","schemaVersion":2},"datasetVersion":"2026-08-30T13:17:10.514Z"}