[BUG] webhooks.yml failedContinue has had no effect since v3.7.0 — parsed but never read

Author: johnhengaCreated Sep 17, 2026Updated Sep 17, 2026

OpenIM Server Version

main (175a7bb06, 2026-08-31); same on v3.7.x and v3.8.x

Operating System and CPU Architecture

Linux (AMD)

Deployment Method

Source Code Deployment

Bug Description and Steps to Reproduce

failedContinue in config/webhooks.yml is parsed into config.BeforeConfig.FailedContinue (pkg/common/config/config.go) and then never read. A search of the repository for FailedContinue returns only pkg/common/config/config.go, config/webhooks.yml and deployments/deploy/openim-config.yml — no Go code uses the value.

pkg/common/webhook.WithCondition checks only Enable and returns the callback's error unchanged:

go
func WithCondition(ctx context.Context, before *config.BeforeConfig, callback func(context.Context) error) error {
	if !before.Enable {
		return nil
	}
	return callback(ctx)
}

and Client.post returns the network and unmarshal errors unconditionally:

go
b, err := c.client.Post(ctx, fullURL, ..., timeout)
if err != nil {
	return servererrs.ErrNetwork.WrapMsg(err.Error(), "post url", fullURL)
}
if err = json.Unmarshal(b, output); err != nil {
	return servererrs.ErrData.WithDetail(err.Error() + " response format error")
}

It did work up to v3.6.x, in pkg/common/http/http_client.go:

go
b, err := Post(ctx, url, nil, input, callbackConfig.CallbackTimeOut)
if err != nil {
	if callbackConfig.CallbackFailedContinue != nil && *callbackConfig.CallbackFailedContinue {
		log.ZInfo(ctx, "callback failed but continue", err, "url", url)
		return nil
	}
	...
}

The handling was dropped in b76816bc142d0a43eaf2525725f9b72959d6e0a4 ("refactor: 3.7.0 code conventions." #2148), where pkg/common/webhook.Client replaced that helper. The config field was kept.

Steps to reproduce:

  1. In config/webhooks.yml, set url to an address where nothing is listening, and set:
    yaml
    beforeSendSingleMsg:
      enable: true
      timeout: 5
      failedContinue: true
  2. Send a one-to-one message.
  3. Expected, per the documentation: the send continues, because failedContinue is true. Actual: the send fails with the webhook's network error.

This is a different axis from actionCode / nextCode (#3049). Those still work, and let a receiver that answers abort the operation. What has no switch today is a receiver that is unreachable, times out, or returns malformed JSON: the before-event operation then always fails.

The documentation still describes the flag as working — https://github.com/openimsdk/docs/blob/main/content/docs/chat/platform-api/webhooks/overview.mdx : "failedContinue | Whether a before-event operation continues after receiver failure or timeout."

Question for the maintainers: was the removal intended?

  • If yes, the field should be removed from config/webhooks.yml, deployments/deploy/openim-config.yml and the docs, so that operators do not configure something that has no effect.
  • If no, restoring it in Client.post (return nil on the post and unmarshal errors when before.FailedContinue is set, leaving the actionCode / nextCode path unchanged) would match the documented behaviour.

Happy to send a PR for either outcome.

Screenshots Link

No response

Source: openimsdk/open-im-server