micro/go-micro · error

anthropic stream error: %s

Error message

anthropic stream error: %s

What it means

Returned by streamReader.Recv when Anthropic sends a terminal "error" event in the SSE stream. The raw JSON payload of the error event is embedded in the message so the developer can see Anthropic's error type (overloaded_error, api_error, etc.) that aborted the stream mid-generation.

Source

Thrown at ai/anthropic/anthropic.go:330

			if chunk.Delta.Type == "text_delta" && chunk.Delta.Text != "" {
				return &ai.Response{Reply: chunk.Delta.Text}, nil
			}
		case "message_start":
			if chunk.Message.Usage.InputTokens > 0 || chunk.Message.Usage.OutputTokens > 0 {
				return &ai.Response{Usage: usage(chunk.Message.Usage.InputTokens, chunk.Message.Usage.OutputTokens)}, nil
			}
		case "message_delta":
			if chunk.Delta.StopReason != "" || chunk.Usage != nil {
				response := &ai.Response{StopReason: chunk.Delta.StopReason}
				if chunk.Usage != nil {
					response.Usage = usage(chunk.Usage.InputTokens, chunk.Usage.OutputTokens)
				}
				return response, nil
			}
		case "message_stop":
			return nil, io.EOF
		case "error":
			return nil, fmt.Errorf("anthropic stream error: %s", data)
		}
	}
	if err := s.scanner.Err(); err != nil {
		return nil, err
	}
	return nil, io.EOF
}

func (s *streamReader) Close() error {
	if s.closed {
		return nil
	}
	s.closed = true
	return s.body.Close()
}

func usage(input, output int) ai.Usage {
	return ai.Usage{InputTokens: input, OutputTokens: output, TotalTokens: input + output}

View on GitHub (pinned to 24529f1404)

Solutions

  1. Parse the embedded JSON payload to read error.type; retry the whole stream (with backoff) for overloaded_error or api_error since partial output may exist before the error.
  2. Check Anthropic's status page (status.anthropic.com) if overloaded_error repeats.
  3. Implement resumable handling: keep already-received chunks and restart the request if the stream errors.
  4. Reduce max_tokens/request size if overloaded errors correlate with large requests.

Example fix

// before
resp, err := stream.Recv()
if err != nil { return err }
// after
resp, err := stream.Recv()
if err != nil {
	if strings.Contains(err.Error(), "overloaded_error") {
		time.Sleep(backoff); return retryStream(ctx, req)
	}
	return err
}
Defensive patterns

Strategy: retry

Type guard

func isOverloadedStreamErr(err error) bool {
	return err != nil && strings.Contains(err.Error(), "overloaded_error")
}

Try / catch

for attempt := 0; attempt < 3; attempt++ {
	stream, err := provider.Stream(ctx, req)
	if err != nil { return err }
	for {
		resp, err := stream.Recv()
		if errors.Is(err, io.EOF) { return nil }
		if err != nil {
			if isOverloadedStreamErr(err) { time.Sleep(backoff(attempt)); break } // restart stream
			return err
		}
		// accumulate resp.Reply
	}
}

Prevention

When it happens

Trigger: Anthropic emits an SSE event with type "error" during streaming — typically overloaded_error (server capacity), api_error, or a mid-stream invalid_request_error after the stream already started with 200 OK.

Common situations: Long generations interrupted by Anthropic 529/overloaded conditions, transient infra failures mid-stream, or requests hitting degraded regions.

Related errors


AI-assisted analysis of micro/go-micro@24529f1404 (2026-09-01). Data as JSON: /api/errors/dfac1581e66d5fc1. Report an issue: GitHub.