Skip to content

feat: usage report transaction IDs, usage history and exports - #3

Draft
fuzcap wants to merge 1 commit into
mainfrom
feat/billing
Draft

fuzcap wants to merge 1 commit into
mainfrom
feat/billing

Conversation

@fuzcap

@fuzcap fuzcap commented Oct 5, 2026

Copy link
Copy Markdown

What does this PR change?

CLI support for two Kaiten features: idempotent usage reports (transactionId) and the usage history. Server: kaitencloud/kaiten#16. SDK: kaitencloud/sdk-go#1.

  • kaiten instances usage report … --transaction-id <id>. Kaiten applies a keyed report at most once, so the SDK retries it on network errors and 500/502/503/504, and running the command again is safe. A replayed report ("already counted") and dropped metadata (above 4 KiB) are noted on stderr; stdout stays the usage document scripts read. The flag overrides a key given in --file/--payload.
  • Exit codes. A malformed key exits 2 before any request. A key already used for a different report is a 409 and exits 5, like any rejection: a correction is a new report under a new key.
  • kaiten instances usage history <instance> <entitlement>. The accepted reports in order, with the counter before and after each one, the delta, the limit and the key. Flags: --from, --to (last 30 days by default), --transaction-id, --limit.
  • kaiten instances usage export [<instance> <entitlement>]. CSV (default) or NDJSON, streamed to stdout or --output-file:
    • with the two arguments, one pair, up to 366 days per run;
    • without them, the whole organization, up to 31 days per run, narrowed by --instance, --instance-id, --entitlement and --entitlement-id. The ID filters reach deleted instances and entitlements.
    • Exports run on a client with no overall timeout (the server must still start answering within 15 s) and outside the command's 15 s deadline; Ctrl-C still cancels. A file is written as <name>.partial and renamed when complete.
  • github.com/kaitencloud/sdk-go is pinned to a pseudo-version of feat: usage report transaction IDs and the usage history sdk-go#1's branch. Before merging: merge and tag that PR, then bump the pin to the tag.

Why?

A report that timed out could not be retried safely: it might count twice. A key makes the retry safe, and the CLI is how operators and scripts send one-off reports. The history commands let them see, and keep, what was counted.

Testing

task test      # ok, also with -race
task lint      # 0 issues
task deadcode  # nothing unreachable

Against a fake API:

  • Report: the key goes into the body, and no key is sent without the flag. A replay is noted on stderr with stdout still a JSON document. A malformed key exits 2 with no request; a reused key exits 5.
  • History: the request path and from query, and the table's columns (key, limit, negative delta).
  • Export:
    • a pair streams to stdout byte for byte;
    • the organization export goes to a file with its filters in the query, leaving no .partial behind;
    • invocation mistakes exit 2 and send nothing: one argument, three arguments, organization filters with a pair, an unknown format, an unparsable --from;
    • a 422 OutsideRetention exits 5 and creates no file.

Checklist

  • I have read CONTRIBUTING.md.
  • Every commit in this PR includes a valid DCO Signed-off-by line.
  • I have the right to submit all material in this PR.
  • I have not included secrets or confidential data.
  • I have updated tests where appropriate.
  • I have updated documentation where appropriate.
  • I have preserved required third-party licenses and attributions.

Kaiten now makes usage reports idempotent and keeps their history; the
Go SDK models both (kaitencloud/sdk-go#1). The CLI follows.

- instances usage report --transaction-id: Kaiten applies the report at
  most once per key, so the SDK retries it on transient failures and
  running the command again is safe. A replayed report and dropped
  metadata are noted on stderr; stdout stays the usage document. The
  flag wins over a key in --file or --payload.
- A malformed key exits 2 before any request; a key already used for a
  different report is a 409 and exits 5.
- instances usage history <instance> <entitlement>: the accepted
  reports, with the counter before and after each one, the delta, the
  limit and the key; --from, --to, --transaction-id, --limit.
- instances usage export [<instance> <entitlement>]: CSV or NDJSON
  streamed to stdout or --output-file, for one pair (366 days per run)
  or, without arguments, the whole organization (31 days per run) with
  --instance, --instance-id, --entitlement and --entitlement-id. Exports
  run on a client without an overall timeout and outside the command's
  15 s deadline; a file is written as <name>.partial and renamed once
  complete.
- github.com/kaitencloud/sdk-go is pinned to the branch of
  kaitencloud/sdk-go#1 until it is released.

Signed-off-by: Tom Ribuot <[email protected]>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant