{"record":{"id":"dd6ce590b9ee2915","repo":"charmbracelet/crush","slug":"failed-to-set-config-field-w","errorCode":null,"errorMessage":"failed to set config field: %w","messagePattern":"failed to set config field: %w","errorType":"error_code","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/client/config.go","lineNumber":22,"sourceCode":"\t\"context\"\n\t\"encoding/json\"\n\t\"fmt\"\n\t\"net/http\"\n\n\t\"github.com/charmbracelet/crush/internal/config\"\n\t\"github.com/charmbracelet/crush/internal/oauth\"\n\t\"github.com/charmbracelet/crush/internal/proto\"\n)\n\n// SetConfigField sets a config key/value pair on the server.\nfunc (c *Client) SetConfigField(ctx context.Context, id string, scope config.Scope, key string, value any) error {\n\trsp, err := c.post(ctx, fmt.Sprintf(\"/workspaces/%s/config/set\", id), nil, jsonBody(struct {\n\t\tScope config.Scope `json:\"scope\"`\n\t\tKey   string       `json:\"key\"`\n\t\tValue any          `json:\"value\"`\n\t}{Scope: scope, Key: key, Value: value}), http.Header{\"Content-Type\": []string{\"application/json\"}})\n\tif err != nil {\n\t\treturn fmt.Errorf(\"failed to set config field: %w\", err)\n\t}\n\tdefer rsp.Body.Close()\n\tif rsp.StatusCode != http.StatusOK {\n\t\treturn fmt.Errorf(\"failed to set config field: status code %d\", rsp.StatusCode)\n\t}\n\treturn nil\n}\n\n// RemoveConfigField removes a config key on the server.\nfunc (c *Client) RemoveConfigField(ctx context.Context, id string, scope config.Scope, key string) error {\n\trsp, err := c.post(ctx, fmt.Sprintf(\"/workspaces/%s/config/remove\", id), nil, jsonBody(struct {\n\t\tScope config.Scope `json:\"scope\"`\n\t\tKey   string       `json:\"key\"`\n\t}{Scope: scope, Key: key}), http.Header{\"Content-Type\": []string{\"application/json\"}})\n\tif err != nil {\n\t\treturn fmt.Errorf(\"failed to remove config field: %w\", err)\n\t}\n\tdefer rsp.Body.Close()","sourceCodeStart":4,"sourceCodeEnd":40,"githubUrl":"https://github.com/charmbracelet/crush/blob/7944b8e52225d8805e31eacbf7ef24856b0dfb7a/internal/client/config.go#L4-L40","documentation":"SetConfigField wraps a transport-level failure of the POST to /workspaces/{id}/config/set. The config change never reached the server.","triggerScenarios":"c.post returns an error: connection refused, context canceled/expired, or request encoding failure when setting a config field.","commonSituations":"Server not running or socket path wrong; context deadline exceeded during a slow request; workspace id invalid causing an earlier failure.","solutions":["Check the wrapped error for connectivity issues and verify the server is reachable","Verify the workspace id and that the context has adequate deadline","Retry the call once the connection is restored"],"exampleFix":null,"handlingStrategy":"retry","validationCode":"// Ensure the context is alive and server reachable before the call\nif err := ctx.Err(); err != nil {\n    return err\n}\nreq, _ := http.NewRequestWithContext(ctx, http.MethodGet, healthURL, nil)\nif _, err := http.DefaultClient.Do(req); err != nil {\n    return fmt.Errorf(\"server unreachable: %w\", err)\n}","typeGuard":null,"tryCatchPattern":"if err := c.SetConfigField(ctx, id, scope, key, value); err != nil {\n    if errors.Is(err, context.DeadlineExceeded) || isConnRefused(err) {\n        // retry with backoff\n    }\n    return err\n}","preventionTips":["Pass contexts with adequate deadlines","Confirm server connectivity before config mutations","Retry idempotent config sets on transport failure"],"tags":["http","network","config"],"backgroundTag":"http-request-failed","analyzedSha":"7944b8e52225d8805e31eacbf7ef24856b0dfb7a","analyzedAt":"2026-08-29T12:48:59.079Z","schemaVersion":2},"datasetVersion":"2026-08-29T17:17:51.833Z"}