chenhg5/cc-connect · info

googlechat: close update response body: %w

Error message

googlechat: close update response body: %w

What it means

This error is returned by Platform.UpdateMessage when resp.Body.Close() fails after a successful update request and drain. Body close failures on HTTP responses are rare and typically indicate the connection was already torn down or a reset occurred while closing. The update itself almost certainly succeeded, since the body was fully read first.

Source

Thrown at platform/googlechat/streaming.go:101

	url, body, err := buildUpdateRequest(h.name, content)
	if err != nil {
		return err
	}
	req, err := http.NewRequestWithContext(ctx, http.MethodPatch, url, bytes.NewReader(body))
	if err != nil {
		return fmt.Errorf("googlechat: build update request: %w", err)
	}
	req.Header.Set("Content-Type", "application/json")
	resp, err := p.doRequest(req)
	if err != nil {
		return err
	}
	if _, err := io.Copy(io.Discard, resp.Body); err != nil {
		_ = resp.Body.Close()
		return fmt.Errorf("googlechat: drain update response body: %w", err)
	}
	if err := resp.Body.Close(); err != nil {
		return fmt.Errorf("googlechat: close update response body: %w", err)
	}
	return nil
}

var (
	_ core.MessageUpdater = (*Platform)(nil)
	_ core.PreviewStarter = (*Platform)(nil)
)

View on GitHub (pinned to 4000b2338a)

Solutions

  1. Treat as non-fatal: the message update already succeeded, so log the error instead of failing the operation.
  2. Disable or shorten HTTP keep-alive if stale connections repeatedly cause this.
  3. Retry only if the caller requires the update call to return nil.
  4. Check for middleware/wrappers around http.RoundTripper that mishandle body closure.

Example fix

// before
if err := resp.Body.Close(); err != nil {
    return fmt.Errorf("googlechat: close update response body: %w", err)
}
// after
if cerr := resp.Body.Close(); cerr != nil {
    // update succeeded; close failure is not fatal
    slog.Warn("googlechat: close update response body", "err", cerr)
}
return nil
Defensive patterns

Strategy: try-catch

Try / catch

// Go: treat close errors as non-fatal
if err := platform.UpdateMessage(ctx, msgID, content); err != nil {
    if strings.Contains(err.Error(), "close update response body") {
        slog.Warn("non-fatal body close error after update", "err", err)
    } else {
        return err
    }
}

Prevention

When it happens

Trigger: Calling UpdateMessage when the HTTP client's response body Close encounters a broken connection (e.g. keep-alive connection reset at close time).

Common situations: Idle keep-alive connections expiring between Google's servers and the client; aggressive connection reaping by NATs, load balancers, or firewalls.

Understand the failure class

Background: "API error: {status}" and "HTTP 401/403/404/429/5xx" errors: non-2xx HTTP responses explained — this error's family across 27 libraries.

Related errors


AI-assisted analysis of chenhg5/cc-connect@4000b2338a (2026-09-06). Data as JSON: /api/errors/daa17418ee48e5a3. Report an issue: GitHub.