Skip to content
This repository was archived by the owner on Feb 25, 2026. It is now read-only.

feat(usage): add feature attribution header to API requests - #407

Merged
pedroheyerdahl merged 2 commits into
devfrom
feat/usage-feature-attribution
Feb 18, 2026
Merged

pedroheyerdahl merged 2 commits into
devfrom
feat/usage-feature-attribution

Conversation

@pedroheyerdahl

Copy link
Copy Markdown
Contributor

Summary

Adds the X-KILOCODE-FEATURE header to all LLM requests going through kilo-gateway, enabling per-feature attribution of token usage in microdollar_usage. This is Step 7 of the Microdollar Feature Tracking plan.

Problem

There's no way to distinguish which feature generates each token usage record in microdollar_usage. All requests from the CLI, VS Code extension, and cloud features look identical at the gateway level.

Solution

Every LLM request now includes an X-KILOCODE-FEATURE header identifying the calling feature. The value is determined by the KILOCODE_FEATURE environment variable, which callers set before spawning the kilo CLI process.

Changes

packages/kilo-gateway/src/api/constants.ts

  • Added HEADER_FEATURE, DEFAULT_FEATURE, ENV_FEATURE constants

packages/kilo-gateway/src/headers.ts

  • Added getFeatureHeader() — reads process.env.KILOCODE_FEATURE, returns undefined when not set
  • buildKiloHeaders() conditionally includes the feature header only when the env var is set
  • No default value in getFeatureHeader() to prevent misattribution — missing env var = no header = NULL in DB

packages/kilo-gateway/src/server/routes.ts

  • FIM route (/kilo/fim) now includes buildKiloHeaders() + hardcoded [HEADER_FEATURE]: "autocomplete" override
  • Previously this route made raw fetch() calls without any kilo headers

packages/kilo-vscode/src/services/cli-backend/server-manager.ts

  • Added KILOCODE_FEATURE: "vscode-extension" to the spawn env when launching the kilo CLI process

packages/opencode/src/index.ts

  • CLI entry point sets process.env.KILOCODE_FEATURE = "cli" if not already set by a caller

packages/kilo-gateway/src/index.ts

  • Exported new constants and getFeatureHeader

packages/kilo-gateway/src/headers.test.ts (new)

  • 7 tests covering getFeatureHeader() and buildKiloHeaders() feature header behavior

Testing

  • 7/7 automated tests pass (bun test src/headers.test.ts)
  • TypeScript typecheck passes

@kilo-code-bot

kilo-code-bot Bot commented Feb 18, 2026 •

Copy link
Copy Markdown
Contributor

Code Review Summary

Status: No New Issues Found | Recommendation: Merge (after addressing existing comments)

Overview

This PR adds feature attribution tracking via a KILOCODE_FEATURE env var and X-KILOCODE-FEATURE header. The implementation is clean and well-structured:

  • Constants & headers (constants.ts, headers.ts): New HEADER_FEATURE and ENV_FEATURE constants with a getFeatureHeader() helper that correctly returns undefined for unset/empty values.
  • Feature tagging by entry point: VS Code extension sets "vscode-extension", direct CLI sets "cli", unattributed serve gets "unknown", and autocomplete FIM overrides to "autocomplete".
  • Header building (routes.ts): The spread + override pattern (...buildKiloHeaders(), [HEADER_FEATURE]: "autocomplete") correctly ensures the autocomplete feature always wins over the env var default.
  • Exports (index.ts): New symbols properly exported with kilocode_change markers.
  • Tests: Good coverage of getFeatureHeader and buildKiloHeaders with proper env var cleanup in afterEach.

The two existing inline comments (about process.argv.includes("serve") substring matching and the hardcoded "KILOCODE_FEATURE" string in server-manager.ts) are the only notable issues. No additional bugs, security vulnerabilities, or logic errors were found.

Files Reviewed (7 files)
  • packages/kilo-gateway/src/api/constants.ts - No new issues
  • packages/kilo-gateway/src/headers.ts - No new issues
  • packages/kilo-gateway/src/index.ts - No new issues
  • packages/kilo-gateway/src/server/routes.ts - No new issues
  • packages/kilo-vscode/src/services/cli-backend/server-manager.ts - No new issues (1 existing comment)
  • packages/opencode/src/index.ts - No new issues (1 existing comment)
  • packages/opencode/test/kilocode/kilo-gateway-headers.test.ts - No new issues

Fix these issues in Kilo Cloud

export const HEADER_FEATURE = "X-KILOCODE-FEATURE"

/** Default feature value (CLI usage) */
export const DEFAULT_FEATURE = "cli"

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I am wondering if we should instead of a default use 'unknown' so that when new products roll out and we forget this change, we see it in the data

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

agreed, and I thought I had changed that. thanks for catching!

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The way I've found to derive cli feature while keeping misattributed new products as unkjonwn is to check if env var is not set and there's no serve command. does that make sense to you?

Comment thread packages/opencode/src/index.ts
Comment thread packages/kilo-vscode/src/services/cli-backend/server-manager.ts
Pedro Heyerdahl added 2 commits February 18, 2026 15:49
Introduce X-KILOCODE-FEATURE header for tracking request origin
across different entry points (CLI, VSCode extension, autocomplete).

- Add HEADER_FEATURE, DEFAULT_FEATURE, and ENV_FEATURE constants
- Add getFeatureHeader() helper reading from KILOCODE_FEATURE env var
- Include feature header in buildKiloHeaders() when env var is set
- Set feature to "autocomplete" for FIM/completion requests
- Set KILOCODE_FEATURE="vscode-extension" when spawning CLI from VSCode
- Default to "cli" feature in opencode entry point
- Add unit tests for feature header logic
…rom command context

Remove the hardcoded DEFAULT_FEATURE ("cli") constant from kilo-gateway
and instead derive the feature value at runtime in opencode. When the
KILOCODE_FEATURE env var is not set, the "serve" command is now tagged
as "unknown" (to surface misconfiguration when a caller forgets to set
the env var), while all other commands default to "cli".
@pedroheyerdahl
pedroheyerdahl force-pushed the feat/usage-feature-attribution branch from 88d9964 to 1be28bb Compare February 18, 2026 18:52
@pedroheyerdahl
pedroheyerdahl merged commit e02debf into dev Feb 18, 2026
7 checks passed
@pedroheyerdahl
pedroheyerdahl deleted the feat/usage-feature-attribution branch February 18, 2026 20:31
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants