Append

Append data to an existing stream, or close it.

bucketpathstringrequired

Bucket ID.

streampathstringrequired

Stream ID within the bucket.

Content-Typeheaderstringrequired

Must match the stream's content type (set at PUT or first POST). Required when the body is non-empty; mismatch returns 400.

Stream-Closedheaderstring

Set to true to close the stream after this append.

If-Matchheaderstring

Conditional write: only succeed if the stream's ETag matches.

Stream-Seqheaderstring

Client-supplied sequence token for conflict detection.

Producer-Idheaderstring

Stable producer identity (UUID, hostname, etc.) for exactly-once writes. Dedup state is per-stream.

Producer-Epochheaderstring

Producer epoch. Bumped on producer restart; must be ≥ the last epoch the server accepted for this Producer-Id. A new epoch resets the seq counter. Max value 2^53 − 1.

Producer-Seqheaderstring

Producer sequence number. Starts at 0 for a new epoch and must increase by exactly 1 per append. Exact (epoch, seq) duplicates are silently deduplicated. Max value 2^53 − 1.

bodybodybinaryrequired

The bytes to append. Must not be empty unless Stream-Closed: true is set (close-only request).

Response

StatusMeaning
200Append successful.
400Empty body without Stream-Closed: true, missing content type, or bad JSON.
404Stream not found.
409Stream is already closed, or sequence/producer conflict.
412If-Match precondition failed.
503Write backpressure. Retry after the duration in Retry-After.

Response headers include Stream-Next-Offset and ETag.

curl -X POST http://127.0.0.1:4437/demo/hello \
  -H 'Content-Type: application/octet-stream' \
  --data-binary 'hello world'
curl -X POST http://127.0.0.1:4437/demo/hello \
  -H 'Content-Type: application/json' \
  --data-binary '{"event": "click", "ts": 1711234567}'
curl -X POST http://127.0.0.1:4437/demo/hello \
  -H 'Stream-Closed: true'

Appends to JSON streams are validated and normalized. The server may coalesce multiple concurrent appends into a single batch for performance.