{"record":{"id":"c7a84eef71c2fccd","repo":"charmbracelet/crush","slug":"invalid-response-format-missing-data-field","errorCode":null,"errorMessage":"invalid response format: missing data field","messagePattern":"invalid response format: missing data field","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/agent/tools/sourcegraph.go","lineNumber":211,"sourceCode":"\n\tbuffer.WriteString(\"## Sourcegraph API Error\\n\\n\")\n\tfor _, err := range errors {\n\t\terrMap, ok := err.(map[string]any)\n\t\tif !ok {\n\t\t\tcontinue\n\t\t}\n\t\tmessage, ok := errMap[\"message\"].(string)\n\t\tif ok {\n\t\t\tfmt.Fprintf(buffer, \"- %s\\n\", message)\n\t\t}\n\t}\n\treturn true\n}\n\nfunc sourcegraphSearchResults(result map[string]any) (map[string]any, error) {\n\tdata, ok := result[\"data\"].(map[string]any)\n\tif !ok {\n\t\treturn nil, fmt.Errorf(\"invalid response format: missing data field\")\n\t}\n\n\tsearch, ok := data[\"search\"].(map[string]any)\n\tif !ok {\n\t\treturn nil, fmt.Errorf(\"invalid response format: missing search field\")\n\t}\n\n\tsearchResults, ok := search[\"results\"].(map[string]any)\n\tif !ok {\n\t\treturn nil, fmt.Errorf(\"invalid response format: missing results field\")\n\t}\n\treturn searchResults, nil\n}\n\nfunc writeSourcegraphHeader(buffer *strings.Builder, searchResults map[string]any) {\n\tmatchCount, _ := searchResults[\"matchCount\"].(float64)\n\tresultCount, _ := searchResults[\"resultCount\"].(float64)\n\tlimitHit, _ := searchResults[\"limitHit\"].(bool)","sourceCodeStart":193,"sourceCodeEnd":229,"githubUrl":"https://github.com/charmbracelet/crush/blob/7944b8e52225d8805e31eacbf7ef24856b0dfb7a/internal/agent/tools/sourcegraph.go#L193-L229","documentation":"Raised by sourcegraphSearchResults when the parsed GraphQL response map lacks a \"data\" object (internal/agent/tools/sourcegraph.go:209-212). Sourcegraph returns {\"data\": {...}} on success; GraphQL-level failures arrive as a top-level \"errors\" array, which writeSourcegraphErrors handles first — so reaching this error means the 200 response was JSON but shaped unexpectedly (nil data, data as non-object, or an undocumented schema change).","triggerScenarios":"formatSourcegraphResults -> sourcegraphSearchResults sees result[\"data\"] absent or not a map: GraphQL errors payload where only \"errors\" is present and writeSourcegraphErrors returned false (error entries not maps), a nil data field (Sourcegraph returns null data for some internal errors), or a Sourcegraph API schema/shape change.","commonSituations":"Sourcegraph returning {\"data\":null,\"errors\":[...]} with error entries the renderer skipped; partial (non-JSON-error) internal failures; using a modified/self-hosted endpoint with a different response shape; API version drift breaking the expected envelope.","solutions":["Log the full response body to see the actual top-level shape (errors array, null data, etc.).","Check whether the response contained a GraphQL \"errors\" array whose entries were not {message:string} maps — extend writeSourcegraphErrors to surface raw entries.","Verify sourcegraph.com's GraphQL schema is unchanged (introspect data.search) or pin/check a known-good Sourcegraph version for self-hosted endpoints.","Treat this as the tool's 'Failed to format results' text error and retry with a simpler query to rule out query-induced null data."],"exampleFix":"null","handlingStrategy":"type-guard","validationCode":"if data, ok := result[\"data\"].(map[string]any); !ok || data == nil {\n    return fmt.Errorf(\"GraphQL response missing data: %v\", result[\"errors\"])\n}","typeGuard":"func hasGraphQLData(result map[string]any) (map[string]any, bool) {\n    data, ok := result[\"data\"].(map[string]any)\n    return data, ok && data != nil\n}","tryCatchPattern":"formatted, err := formatSourcegraphResults(result, ctxWindow, count)\nif err != nil {\n    return fantasy.NewTextErrorResponse(\"Failed to format results: \" + err.Error()), nil\n}","preventionTips":["Always render top-level GraphQL errors before probing data fields.","Log the raw response when data is absent — null data usually accompanies an errors array.","Pin/monitor the Sourcegraph API version if using a custom endpoint.","Handle data:null explicitly rather than letting the map assertion fail silently."],"tags":["graphql","schema","validation","sourcegraph"],"backgroundTag":"unexpected-api-response-shape","analyzedSha":"7944b8e52225d8805e31eacbf7ef24856b0dfb7a","analyzedAt":"2026-08-29T12:48:59.079Z","schemaVersion":2},"datasetVersion":"2026-08-29T17:17:51.833Z"}