nats-io/nats-server · warning
%w at offset %d
Error message
%w at offset %d
What it means
When a JetStream API request body fails to parse as JSON, the server wraps the underlying error with the byte offset of the syntax error (from json.SyntaxError.Offset) and rate-limit-logs it. With strict JetStream mode enabled, the wrapped error is also returned to the client, pinpointing where the malformed JSON broke.
Source
Thrown at server/jetstream_api.go:1299
if acc == nil {
return nil, nil, nil, nil, ErrMissingAccount
}
return &ci, acc, hdr, msg, nil
}
func (s *Server) unmarshalRequest(c *client, acc *Account, subject string, msg []byte, v any) error {
decoder := json.NewDecoder(bytes.NewReader(msg))
decoder.DisallowUnknownFields()
for {
if err := decoder.Decode(v); err != nil {
if err == io.EOF {
return nil
}
var syntaxErr *json.SyntaxError
if errors.As(err, &syntaxErr) {
err = fmt.Errorf("%w at offset %d", err, syntaxErr.Offset)
}
c.RateLimitWarnf("Invalid JetStream request '%s > %s': %s", acc, subject, err)
if js := s.getJetStream(); js != nil && js.config.Strict {
return err
}
return json.Unmarshal(msg, v)
}
}
}
func (a *Account) trackAPI() {
a.mu.RLock()
jsa := a.js
a.mu.RUnlock()
if jsa != nil {View on GitHub (pinned to 3a66a489d2)
Solutions
- Use the offset in the message to locate the first invalid byte in your request payload and fix the JSON there.
- Serialize the request with a proper JSON encoder (e.g. json.Marshal of the API request struct) instead of manual string building.
- Validate the payload parses (json.Valid) before publishing to $JS.API subjects.
Example fix
// before
nc.Publish("$JS.API.STREAM.CREATE.x", []byte(`{"name":"x"`)) // truncated
// after
cfg, _ := json.Marshal(&JetStreamStreamCreateRequest{Name: "x"})
nc.Publish("$JS.API.STREAM.CREATE.x", cfg) Defensive patterns
Strategy: try-catch
Validate before calling
if !json.Valid(payload) {
return errors.New("request payload is not valid JSON")
} Try / catch
// Go: inspect wrapped json.SyntaxError for offset
var syn *json.SyntaxError
if errors.As(err, &syn) {
log.Printf("bad JetStream request at offset %d", syn.Offset)
} Prevention
- Always marshal API request structs with encoding/json.
- Run json.Valid on hand-built payloads before publishing to $JS.API.
- Watch for message truncation on large requests.
When it happens
Trigger: Publishing to a $JS.API subject with a body that is not valid JSON — truncated message, wrong encoding, concatenation of two JSON docs, or a non-JSON payload sent to an API endpoint.
Common situations: Client sending protobuf/msgpack instead of JSON to JetStream API; string-concatenated payloads with trailing bytes; network truncation of large requests; handcrafted test payloads.
Related errors
- JS_INVALID_JSON
- unknown consumer action: %v
- unknown priority policy: %v
- can not marshal %v
- can not unmarshal %q
AI-assisted analysis of nats-io/nats-server@3a66a489d2 (2026-09-02).
Data as JSON: /api/errors/007f08bc95ec0f72.
Report an issue: GitHub.