bytebase/bytebase · error

%.100s

Error message

%.100s

What it means

Slack responded 200 OK but with a body other than the literal 'ok'. Classic Slack incoming webhooks return 'ok' on success; any other 200 body (often JSON with an error like 'channel_not_found' or 'user_not_found', or an HTML interstitial) is treated as failure and reported truncated to 100 chars via the %.100s verb.

Source

Thrown at backend/plugin/webhook/slack/slack.go:247

		Timeout: webhook.Timeout,
	}
	resp, err := client.Do(req)
	if err != nil {
		return errors.Wrapf(err, "failed to POST webhook to %s", context.URL)
	}

	b, err := io.ReadAll(resp.Body)
	if err != nil {
		return errors.Wrapf(err, "failed to read POST webhook response from %s", context.URL)
	}
	defer resp.Body.Close()

	if resp.StatusCode != http.StatusOK {
		return errors.Errorf("failed to POST webhook to %s, status code: %d, response body: %s", context.URL, resp.StatusCode, b)
	}

	if string(b) != "ok" {
		return errors.Errorf("%.100s", string(b))
	}

	return nil
}

func postDirectMessage(webhookCtx webhook.Context) bool {
	ctx := context.Background()
	t := getSlackToken(webhookCtx.IMSetting)
	if t == "" {
		slog.Warn("failed to found valid slack im token", slog.String("event", webhookCtx.EventType))
		return false
	}
	p := newProvider(t)
	sent := map[string]bool{}
	if err := common.Retry(ctx, func() error {
		var errs error
		for _, u := range webhookCtx.MentionEndUsers {
			if sent[u.Email] {

View on GitHub (pinned to 1870550677)

Solutions

  1. Look at the truncated body in the error — it contains Slack's actual complaint (e.g. channel_not_found)
  2. Recreate the incoming webhook and re-select a valid channel; update the configured URL
  3. Confirm the URL is a genuine https://hooks.slack.com/services/... incoming webhook, not an API or SSO page
  4. Check for proxies that rewrite responses (body would be HTML rather than JSON)

Example fix

// before
// webhook channel deleted in Slack
// after
// edit the incoming webhook, choose an existing channel, save the new URL into settings
Defensive patterns

Strategy: try-catch

Validate before calling

// preflight: post a test ping once at config time and require body == "ok"
body, code := tryPost(testURL, minimalPayload); if code != 200 || body != "ok" { return errors.New("webhook did not return ok: " + body) }

Try / catch

if err := webhook.Post(ctx); err != nil { body := err.Error() // <=100 chars of Slack's response
  if strings.Contains(body, "channel_not_found") { /* reselect channel */ } }

Prevention

When it happens

Trigger: Calling Post where Slack returns 200 with an error payload — e.g. the webhook posts to a missing channel, or the URL is not an incoming-webhook endpoint and returns HTML/JSON instead of 'ok'.

Common situations: Channel configured for the webhook was deleted; URL points at a non-webhook Slack endpoint; Slack changes response format for newer webhook types; proxy returns a 200 HTML page (captive portal, SSO).

Understand the failure class

Background: "invalid response format", "malformed payload", "missing data field": when an API returns 200 but the response shape is wrong — this error's family across 23 libraries.

Related errors


AI-assisted analysis of bytebase/bytebase@1870550677 (2026-09-06). Data as JSON: /api/errors/0202101ef2c5766e. Report an issue: GitHub.