# Open Cost Read API

Provider-neutral interoperability proposal, version 0.1 — August 21, 2026

The machine-readable OpenAPI description is published under Apache-2.0 so
providers and other consumers can implement and adapt it.

Canonical technical resources:

- human implementation guide: https://vibecosts.app/cost-api/docs
- raw Markdown specification: https://vibecosts.app/cost-api/spec
- OpenAPI 3.1 description: https://vibecosts.app/cost-api/openapi
- response JSON Schema: https://vibecosts.app/cost-api/schema
- CI-tested conformance cases: https://vibecosts.app/cost-api/conformance
- agent discovery: https://vibecosts.app/llms.txt

## 1. Status and scope

This is an early public proposal, not a certification claim or a replacement for
FOCUS. It defines the smallest secure HTTP profile a SaaS, AI, infrastructure,
or developer-tool provider can expose so a customer-authorized application can
read live incurred costs.

The profile intentionally does not include payment initiation, billing changes,
invoices as a payment instrument, card or bank data, resource mutation, or
end-customer application data.

## 2. Design goals

1. Customers authenticate with the provider, not the consuming application.
2. A grant can read costs and nothing else.
3. Current-period accruals are distinguishable from finalized charges.
4. Cost fields use FOCUS names only where their semantics match.
5. A small SaaS can implement the minimum surface without building a FinOps data
   warehouse.
6. Consumers can normalize many providers behind one connection experience.

## 3. Authorization profiles

### 3.1 Preferred: delegated OAuth

Providers SHOULD implement the OAuth 2.0 authorization code grant with PKCE
using `S256`. They MUST use exact, pre-registered HTTPS redirect URIs in
production. Clients MUST protect the authorization response from CSRF and, when
they support multiple authorization servers, mix-up attacks.

The provider SHOULD publish authorization-server metadata and support:

- scope `costs:read`;
- account or organization selection and informed consent;
- short-lived access tokens;
- rotated refresh tokens or another secure renewal mechanism;
- grant revocation and consent expiry; and
- stable subject and cost-account identifiers that do not expose email
  addresses.

The grant MUST NOT authorize deployments, inference, source/data access, member
management, billing-plan changes, payment initiation, or secret management.
Standard identity and renewal scopes such as `openid` or `offline_access` MAY
accompany `costs:read` when required by the provider; they do not broaden the
resource permissions defined by this profile.

### 3.2 Transitional: restricted token

If delegated OAuth is unavailable, a provider MAY issue a user-created token
whose only permission is `costs:read`. The creation screen SHOULD support a
human-readable name, expiry, revocation, and last-used time.

Consumers MUST NOT request a password, session cookie, full-access token, or a
secret capable of write operations. Restricted tokens are a compatibility path,
not the target user experience.

## 4. Discovery

A provider SHOULD publish its OpenAPI document and OAuth metadata. The canonical
paths below are illustrative; existing provider conventions are valid when the
same semantics are documented.

```text
GET /.well-known/oauth-authorization-server
GET /v1/cost-accounts
GET /v1/costs
```

## 5. Cost accounts

`GET /v1/cost-accounts` returns the organizations, workspaces, or billing
accounts included in the grant. Each object contains:

- `id`: stable opaque identifier;
- `name`: customer-facing name;
- `billing_currency`: ISO 4217 alphabetic currency code; and
- `time_zone`: IANA time-zone identifier used for billing boundaries.

The endpoint MUST return only accounts selected during consent.

## 6. Costs

```http
GET /v1/costs?cost_account_id=acct_123&start=2026-08-01T00:00:00Z&end=2026-08-18T00:00:00Z&granularity=day
Authorization: Bearer <cost-read grant>
Accept: application/json
```

`start` is inclusive and `end` is exclusive. `period_start` and `period_end` in
the response MUST echo that requested interval. A provider MUST support the
current billing period and SHOULD document how much history is available.

### 6.1 Required response fields

- `cost_account_id`
- `billing_currency`
- `period_start` and `period_end`
- `cost_status`: `estimated` or `final`
- `billed_cost`: invoice-basis customer cost after reduced rates and discounts,
  including applicable tax charges
- `updated_at`: when the provider last calculated the result
- `items`: an array, which MAY be empty when only an account total is available

Monetary values and quantities MUST be base-10 JSON strings. Consumers MUST NOT
parse them through binary floating-point arithmetic. Timestamps MUST use RFC 3339
and UTC. Currency MUST NOT be inferred from locale.

### 6.2 Recommended item fields

- `charge_period_start` and `charge_period_end`
- `service_name` and `service_category`
- `resource_id` and `resource_name`
- `region_id`
- `consumed_quantity` and `consumed_unit`
- `list_cost`, `contracted_cost`, `billed_cost`, and `effective_cost`
- `credits`: signed credit total when the provider exposes it separately; a
  negative value reduces billed cost
- `invoice_id` for finalized items
- `tags` containing customer-defined allocation metadata

`billed_cost` maps to FOCUS BilledCost. Optional `effective_cost` maps to FOCUS
EffectiveCost and therefore means amortized cost, including the applicable
portion of relevant prepaid purchases. It MUST NOT be used as a synonym for the
amount expected on an invoice. Profile-specific control fields such as
`cost_status` and `updated_at` are not represented as FOCUS columns. A full FOCUS
dataset remains the preferred export for providers with complex cost and usage
records.

### 6.3 Billing semantics

- Report the customer's provider-calculated billed cost, not a reconstruction
  from public list prices.
- Report cost as it accrues in the represented service period, before payment
  settlement.
- Identify open-period data as `estimated` until it is finalized. A final value
  changes only through an explicit correction or adjustment.
- Preserve refunds, credits, and negative adjustments as signed values.
- Include applicable tax charges in `billed_cost`. Providers MAY also identify
  tax as signed item records for reconciliation, but consumers MUST NOT add
  those records to the already inclusive top-level total.
- Document reporting latency, billing boundaries, and finalization behavior.
- Do not silently convert currencies.

## 7. Pagination and caching

Large item sets use an opaque `page_token`. The token MUST bind the original
query and a consistent provider snapshot. Ordering and `updated_at` MUST remain
stable for that pagination session. Top-level totals describe the entire query
window and repeat unchanged on every page; only `items` is page-scoped.
Responses SHOULD provide `ETag` or `Last-Modified` and honor conditional reads.
Providers SHOULD document their rate limit rather than conforming to an
arbitrary minimum.

Use conventional status codes: `401` for an invalid or expired grant, `403` for
insufficient scope/account consent, `429` for rate limiting, and `5xx` for
provider failure. `429` and retryable `5xx` responses SHOULD include
`Retry-After` where known.

## 8. Future events

Events are intentionally outside the v0.1 OpenAPI and response conformance
artifacts. A future profile may define:

- `cost.updated`;
- `cost.finalized`;
- `consent.expiring`;
- `consent.revoked`; and
- `connection.action_required`.

That future profile will require stable event IDs, creation timestamps, account
IDs, schema versions, signed delivery, idempotency, duplicate and out-of-order
tolerance, and an authoritative fetch after notification.

## 9. Consumer security requirements

A conforming consumer:

- never collects provider passwords;
- asks only for cost-read access;
- keeps all credentials server-side and out of URLs, analytics, logs, and client
  storage;
- encrypts reusable credentials using managed envelope encryption or an
  equivalent design with rotation and access controls;
- stores only normalized data required for the user-facing product;
- supports disconnection, revocation, deletion, and export;
- records security-relevant connector activity in an audit log; and
- publishes security contact, retention, incident-response, and vulnerability
  disclosure information.

## 10. Conformance levels

- **Core response:** the published JSON Schema plus cost-account selection and
  the positive and negative response cases.
- **Delegated authorization:** Core response plus OAuth, consent selection,
  renewal, and revocation. Authorization is reviewed manually in v0.1.
- **Detailed response:** Core response plus itemized
  daily/service/resource attribution.
- **FOCUS export:** the provider separately supplies a currently conforming
  FOCUS dataset.

Conformance describes interface capability; it does not certify a provider's or
consumer's overall security.

## 11. Evolution

Version 0.x changes may be incompatible. Feedback should focus on cost-read use
cases that are not already represented by FOCUS. Vibe Costs is the intended
reference consumer, but the format and scope names are intentionally neutral so
other cost-management applications can implement them without depending on
Vibe Costs.

## 12. Provider implementation checklist

Before pilot access, a provider SHOULD verify all of the following:

1. The endpoint reads the provider's authoritative billing ledger rather than
   reconstructing price from infrastructure inventory or public list prices.
2. The authorization grant cannot mutate resources, members, plans, payment
   methods, secrets, or customer application data.
3. Consent limits the response to explicitly selected cost accounts.
4. Monetary values are base-10 strings and currency is explicit.
5. Open periods are `estimated`; provider calculation time is returned in
   `updated_at`; finalization behavior is documented.
6. Credits, refunds, discounts, and negative adjustments remain visible.
7. Pagination is stable, retry behavior is documented, and rate limiting uses
   conventional status and `Retry-After` headers.
8. The published response schema accepts every positive case and rejects every
   negative case before the connector is identified as verified. Authorization,
   freshness, and revocation behavior are separately reviewed during the pilot.

Implementation questions and pilot access can be sent to
hello@vibecosts.app. Vibe Costs will build and maintain the reference consumer
connector.
