---
title: "Create a Stripe Checkout session for a new subscription"
method: POST
path: "/subscriptions/checkout"
tags: ["Subscriptions"]
---

# Create a Stripe Checkout session for a new subscription

`POST /subscriptions/checkout`

## Request

- Base URL: `https://api.atako.ai`
- URL: `https://api.atako.ai/subscriptions/checkout`
- Auth: HTTP bearer

Company-admin only. With USE_STRIPE=false, creates the subscription directly and returns `url: null`.

## Request body

- object
  - `planId` string, uuid, required
  - `priceId` string, uuid, required
  - `activeAgentsPurchased` integer
  - `creditsPerPeriod` integer
  - `billingInterval` 'monthly' | 'annual': Required when creditsPerPeriod is set.

## Response `200`

- union
  - object
    - `url` string, uri, required
  - object
    - `url` unknown, required
    - `subscription` CompanySubscription, required
      - `id` string, uuid, required
      - `companyId` string, uuid, required
      - `planId` string, uuid, required
      - `planPriceId` string, uuid, nullable
      - `stripeSubscriptionId` string, nullable: Company admins only — omitted for members.
      - `stripeCustomerId` string, nullable: Company admins only — omitted for members.
      - `stripeScheduleId` string, nullable: Company admins only — omitted for members.
      - `hasStripeSubscription` boolean: Whether a live Stripe subscription backs this row (false for a self-serve trial without card).
      - `hasStripeCustomer` boolean: Whether the company has a Stripe customer.
      - `status` 'trialing' | 'active' | 'past_due' | 'canceled', required
      - `currentPeriodStart` string, date-time
      - `currentPeriodEnd` string, date-time
      - `activeAgentsPurchased` integer, required
      - `pendingActiveAgentsPurchased` integer, nullable: Target seat count of a scheduled reduction (AF-57), null when none is pending.
      - `pendingReductionEffectiveAt` string, date-time, nullable: When the pending reduction lands (= currentPeriodEnd at the time it was scheduled).
      - `cancelAt` string, date-time, nullable: End-of-period cancellation scheduled on Stripe (billing portal): when the service stops. Null when none is scheduled. On a `canceled` subscription: when the service actually stopped.
      - `pendingPaymentActiveAgentsPurchased` integer, nullable: A licence increase whose prorated invoice awaits payment (3DS, declined card): the seat count once paid. Null when nothing is pending.
      - `pendingPaymentInvoiceUrl` string, nullable: The hosted Stripe invoice to pay for `pendingPaymentActiveAgentsPurchased`. Company admins only — omitted for members.
      - `trialSource` 'self_serve' | 'admin_manual', nullable
      - `trialEndAgentCount` integer, nullable
      - `planName` string
      - `planDescription` string
      - `creditsPerAgentPerMonth` integer
      - `billingInterval` 'monthly' | 'annual', nullable
      - `pricePerAgentCents` integer, nullable
      - `createdAt` string, date-time
      - `updatedAt` string, date-time

## Other responses

- `400`: Invalid input, or PLAN_PRICE_NOT_CONFIGURED
- `401`: Missing, malformed, or invalid bearer token / API key, or revoked session (SESSION_REVOKED).
- `403`: The caller does not have the required role/permission.
- `404`: No company / Plan not found / Price not found / Company not found
- `409`: SUBSCRIPTION_EXISTS — the company already has an active/past_due Stripe subscription; use /subscriptions/checkout/add-sessions instead.

---

[API](https://skmtc.dev/atako/apis/atako-api.md) · [All operations](https://skmtc.dev/atako/apis/atako-api/llms.txt) · [OpenAPI document](https://skmtc.dev/atako/apis/atako-api/revisions/aa555c56fbd7?raw)
