Wind Wind / Docs
Dashboard

Getting Started

Quickstart

Add Wind billing to your AI app in about 15 minutes.

1

Create your app and get an API key

In the Dashboard, create a new app. Go to the General tab to generate a key — it starts with sk_live_.

Then go to the Features tab and create a feature with an ID (e.g. chat) and a pricing mode:

per_call Fixed price per request — e.g. $0.10 every time.
per_token Cost-based markup — e.g. 1.3× provider cost.
The feature_id in every request must exactly match a feature you've created, or calls fail with NO_PRICING_RULE.
2

Connect a user's Wind wallet

Users connect their Wind wallet once using trywind. After that, all AI requests bill their wallet automatically.

shell
npm install trywind wind-ai
typescript
const wind = new WindManager({ appId: 'YOUR_APP_ID', appName: 'Your App' })

// When the user clicks "Connect Wind wallet"
wind.connect({ externalUserId: currentUser.id })

After the redirect back, call parseReturnUrl() on page load:

typescript
const result = wind.parseReturnUrl()
if (result?.connected) {
  await fetch('/api/me/wind-connect', {
    method: 'POST',
    body: JSON.stringify({ windUserId: result.windUserId }),
  })
}

Store windUserId on the user row in your DB.

3

Make a billable AI request

On your server, initialize the wind-ai client and call client.chat(). Wind handles billing automatically.

typescript
import { createClient } from 'wind-ai'

const client = createClient({
  apiKey: process.env.WIND_API_KEY,
  baseUrl: 'https://wind-production-3225.up.railway.app',
})

const response = await client.chat({
  userId: user.windUserId,
  featureId: 'chat',
  model: 'google/gemini-2.5-flash',
  messages: [{ role: 'user', content: userMessage }],
})
Wind debits the user's wallet, takes a small platform cut, and credits your developer earnings — all in one request.
4

Parse the response

The response follows the OpenAI chat completion shape with a receipt field added by Wind.

typescript
// The AI reply
const text = response.choices[0].message.content

// Billing receipt
const {
  user_charge_cents,   // credits deducted from the user's wallet
  provider_cost_cents, // what Wind paid the model provider
  dev_share_cents,     // your earnings on this request
  input_tokens,
  output_tokens,
} = response.receipt
5

Show the user their wallet balance

typescript
const res = await fetch(`https://wind-production-3225.up.railway.app/v1/user/status?userId=${user.windUserId}`, {
  headers: { 'Authorization': 'Bearer YOUR_API_KEY' },
})
const { wallet } = await res.json()
// wallet.availableCents — spendable balance in cents
// wallet.balanceCents   — total (before holds)
6

Handle low balance gracefully

When a request fails with INSUFFICIENT_FUNDS, send the user to Wind to top up:

typescript
try {
  const result = await callYourBackend(message)
  displayResult(result)
} catch (err) {
  if (err.message === 'low_balance') {
    window.open('https://user.usewind.app/wallet', '_blank')
    showToast('Top up your Wind wallet to continue.')
  }
}
To let users switch their linked Wind account, redirect to Wind Connect again with force_auth=true.