{"record":{"id":"558b4e0ee51cca06","repo":"micro/go-micro","slug":"failed-to-parse-poll-response-w","errorCode":null,"errorMessage":"failed to parse poll response: %w","messagePattern":"failed to parse poll response: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"ai/atlascloud/atlascloud.go","lineNumber":1027,"sourceCode":"\thttpReq.Header.Set(\"Authorization\", \"Bearer \"+p.opts.APIKey)\n\n\thttpResp, err := http.DefaultClient.Do(httpReq)\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"poll request failed: %w\", err)\n\t}\n\tdefer httpResp.Body.Close()\n\n\tbody, _ := io.ReadAll(httpResp.Body)\n\n\tvar pollResp struct {\n\t\tData struct {\n\t\t\tStatus  string   `json:\"status\"`\n\t\t\tOutputs []string `json:\"outputs\"`\n\t\t\tError   string   `json:\"error\"`\n\t\t} `json:\"data\"`\n\t}\n\tif err := json.Unmarshal(body, &pollResp); err != nil {\n\t\treturn nil, fmt.Errorf(\"failed to parse poll response: %w\", err)\n\t}\n\n\tswitch pollResp.Data.Status {\n\tcase \"completed\":\n\t\tresp := &ai.ImageResponse{}\n\t\tfor _, output := range pollResp.Data.Outputs {\n\t\t\tresp.Images = append(resp.Images, ai.Image{URL: output})\n\t\t}\n\t\treturn resp, nil\n\tcase \"failed\":\n\t\treturn nil, fmt.Errorf(\"image generation failed: %s\", pollResp.Data.Error)\n\tdefault:\n\t\treturn nil, nil\n\t}\n}\n\nconst defaultVideoModel = \"google/gemini-omni-flash/image-to-video-developer\"\n","sourceCodeStart":1009,"sourceCodeEnd":1045,"githubUrl":"https://github.com/micro/go-micro/blob/24529f140421a11a33b6999ab7944f2021cfd69c/ai/atlascloud/atlascloud.go#L1009-L1045","documentation":"This error is wrapped by pollPrediction (image path) when the JSON body returned by the Atlas Cloud prediction/status endpoint cannot be unmarshaled into the expected {data:{status,outputs,error}} shape. The library throws it because it cannot determine the job status without a parseable response. The underlying json.Unmarshal error is preserved via %w.","triggerScenarios":"GET <BaseURL>/api/v1/model/prediction/<id> (called from GenerateImage polling loop) returns a 200 response whose body is not valid JSON or does not match the expected struct — e.g. an HTML error/login page from a wrong BaseURL, a proxy gateway JSON envelope with a different schema, an empty body, or a truncated response.","commonSituations":"Misconfigured ATLAS BaseURL pointing at a different service or a UI route; corporate proxy or API gateway returning an HTML 200 page; Atlas Cloud changing the poll response schema (version drift); rate-limit or auth-redirect pages served with 200 status.","solutions":["Verify p.opts.BaseURL points to the correct Atlas Cloud API host (e.g. https://api.atlascloud.ai) with no trailing UI path","Log the raw body returned by the poll endpoint and compare it against the expected {\"data\":{\"status\":...}} schema","Confirm your API key is valid — some gateways return HTML login/redirect pages with 200 for unauthenticated requests","Check whether an HTTP proxy/CDN in front of the API is rewriting or truncating responses","Check Atlas Cloud API changelog for a poll-response schema change and update the library"],"exampleFix":"// before: silent truncation hides the real body\nbody, _ := io.ReadAll(httpResp.Body)\nif err := json.Unmarshal(body, &pollResp); err != nil {\n\treturn nil, fmt.Errorf(\"failed to parse poll response: %w\", err)\n}\n// after: log body on failure to diagnose\ntlogging.Logf(\"poll status=%d body=%q\", httpResp.StatusCode, string(body))","handlingStrategy":"try-catch","validationCode":"// before calling GenerateImage\nif u, err := url.Parse(strings.TrimSpace(baseURL)); err != nil || u.Scheme == \"\" || u.Host == \"\" {\n\treturn fmt.Errorf(\"invalid base URL %q\", baseURL)\n}","typeGuard":"func isValidPollResponse(body []byte) bool {\n\tvar probe struct { Data struct { Status string `json:\"status\"` } `json:\"data\"` }\n\treturn json.Unmarshal(body, &probe) == nil && probe.Data.Status != \"\"\n}","tryCatchPattern":"resp, err := provider.GenerateImage(ctx, req)\nif err != nil {\n\tif strings.Contains(err.Error(), \"failed to parse poll response\") {\n\t\tlog.Printf(\"non-JSON poll body; check BaseURL/proxy: %v\", err)\n\t}\n\treturn fmt.Errorf(\"image job status unavailable: %w\", err)\n}","preventionTips":["Validate BaseURL at startup with url.Parse","Log raw HTTP bodies on parse failures for diagnostics","Ensure API keys are valid so gateways don't return HTML pages","Pin/monitor the provider API version for schema changes"],"tags":["json","http","image-generation","polling"],"backgroundTag":"json-parse-failed","analyzedSha":"24529f140421a11a33b6999ab7944f2021cfd69c","analyzedAt":"2026-09-01T02:52:24.923Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T05:18:18.240Z"}