Lewati ke konten
16/30Bab 16 dari 30

Context Window, Token, dan Tagihan, Terukur

Percakapan 40 giliran menghabiskan input token 22× panjangnya. Caching memangkas 68%; timestamp di tempat salah menambah 20%.

Di halaman ini

Ini percakapan dukungan empat puluh giliran, ditagih giliran demi giliran. Tidak ada yang aneh di dalamnya: seorang developer bertanya tentang API, assistant menjawab dalam satu atau dua paragraf. Seluruh percakapan berisi 5.090 token teks — sekitar delapan halaman.

giliranprompt tokensteks baruoutputbiaya giliran initotal berjalan
121318183$0.002622$0.002622
589214123$0.003260$0.014354
101,65619114$0.004680$0.035530
202,86818103$0.006972$0.094426
303,9412099$0.009070$0.174170
404,94717142$0.011598$0.274386

Baca kolom kedua dan ketiga bersama-sama. Pada giliran 40, pengguna mengetik tujuh belas token dan ditagih untuk 4.947. Pertanyaannya tidak lebih sulit daripada yang pertama; malah lebih pendek. Yang berubah adalah request itu membawa seluruh percakapan bersamanya, lagi, untuk keempat puluh kalinya.

Total input tokens yang ditagih di sepanjang empat puluh call itu: 112.617. Percakapannya sendiri sepanjang 5.090 token. Kamu membayarnya dua puluh dua kali lipat.

Bab ini membahas mengapa itu terjadi, apa namanya di invoice setiap provider, dan dari lima hal yang kamu bayar, mana yang bisa kamu kendalikan.

Tampilkan detail

Yang dibutuhkan bab ini dari Bagian II.

  • Bab 7 membangun tokenizer. token juga menjadi unit di sini — unit yang sama, kini diberi harga.
  • Bab 9 menurunkan self-attention dan biaya O(n2)O(n^2)-nya, di kotak notasi asimtotik. Biaya itulah alasan limit ada sama sekali, dan di sini ia ditautkan alih-alih dijelaskan ulang.
  • Bab 13 mengukur prefill terhadap decode dan menghitung ruang yang ditempati KV cache. Dua fase itulah yang sebenarnya dibeli oleh kolom input dan output di atas.

Selebihnya adalah TypeScript, karena ini akuntansi untuk remote call, bukan matematika tentang model.

Kesalahpahaman paling mahal dalam bisnis ini adalah bahwa model mengingat percakapan.

Tidak, dan mekanisme dari Bab 13 menjelaskan persis alasannya. State transformer selama generation adalah KV cache: keys dan values yang dihitung untuk setiap token dalam sequence. Cache itu hidup selama satu request. Saat request berakhir, proses yang menahannya bebas melayani orang lain, dan cache hilang. Tidak ada penyimpanan per pengguna di sisi lain, dan tidak ada sesi.

Jadi request berikutnya harus datang dengan membawa semua hal yang seharusnya diketahui model, dan model membangun ulang state itu dengan menjalankan forward pass atas seluruh prompt sebelum mengeluarkan satu token baru pun. Bab 15 menyebut prompt sebagai «seluruh state». Inilah alasan fisiknya: prompt adalah state lengkap karena tidak ada hal lain yang bertahan setelah call.

context window adalah panjang maksimum prompt itu ditambah jawabannya. Ia adalah batas atas berapa banyak state yang bisa kamu bangun ulang, bukan wadah yang menyimpan apa pun di antara request. Menyebutnya «memori model» membalik arah kausalitas — kamu tidak sedang mengisi memori, kamu membayar untuk membentuknya kembali.

Dari situlah angka dua puluh dua berasal. Giliran nn membawa semua n1n-1 giliran sebelumnya, jadi total input sepanjang percakapan nn giliran adalah jumlah deret yang terus membesar, yang bersifat kuadratik:

total input  =  i=1n(s+hi)  =  Θ(n2)\text{total input} \;=\; \sum_{i=1}^{n} \big(s + h_i\big) \;=\; \Theta(n^2)

di mana ss adalah system prompt dan hih_i adalah riwayat pada giliran ii. Mencocokkan input kumulatif terukur ke an2+bnan^2 + bn selama empat puluh giliran menghasilkan 60.22n2+432.25n60.22\,n^2 + 432.25\,n, yang memprediksi 113.645 token pada giliran 40 dibanding 112.617 yang terukur. Suku kuadratik mendominasi, dan suku linear adalah yang benar-benar diketik pengguna.

Konsekuensinya adalah kalimat yang perlu dibawa pulang dari bab ini: tagihanmu tumbuh mengikuti kuadrat percakapan, bukan mengikuti pertanyaan terakhir. Empat puluh pertanyaan yang sama, diajukan tanpa riwayat sama sekali, biayanya $0.066036. Menyimpan riwayat biayanya $0.274386. Riwayat melipatgandakan tagihan 4,2 kali, dan akan terus melipatgandakannya, karena pengalinya adalah panjang percakapan.

Window terbatas karena dua alasan yang menarik ke arah yang sama. Yang pertama adalah alasan Bab 9: attention membandingkan setiap token dengan setiap token lain, sehingga kerja layer itu tumbuh mengikuti kuadrat panjang sequence. Yang kedua adalah memori: KV cache tumbuh linear terhadap panjang sequence, dan Bab 13 sudah melakukan aritmetikanya — pada sequence panjang, ia lebih besar daripada weights.

Kedua limit itu sudah diserang dan belum ada yang dihapus. FlashAttention1 mengatur ulang komputasi agar membaca dan menulis jauh lebih sedikit ke high-bandwidth memory, yang membuat sequence panjang praktis tanpa mengubah biaya asimtotiknya. Position Interpolation2 dan YaRN3 memperluas window yang dapat dipakai dari model terlatih dengan menskalakan ulang positional encodings dari Bab 9, bukan melatih ulang. Bersama-sama, itulah alasan window bergerak dari 2K ke 1M dalam lima tahun.

Yang tidak mereka lakukan adalah membuat context panjang menjadi gratis. Mereka menaikkan batas atas dan membuat kemiringannya lebih landai. Kemiringan itu tetap ada, dan itulah yang diukur oleh price tiers nanti dalam bab ini.

Hampir setiap kalkulator biaya di internet memodelkan API call sebagai input tokens dikali harga input plus output tokens dikali harga output. Itu benar pada 2023. Sekarang itu keliru dengan cara yang bisa membuat tagihan meleset dua kali lipat atau lebih, ke dua arah.

Ada lima kategori token yang dapat ditagih:

bucketapa ituharga tipikal, relatif terhadap input
uncached inputprompt tokens yang harus diproses model dari awal
cache readprompt tokens yang dilayani dari prefix tersimpan0.1×
cache writeprompt tokens yang disimpan ke cache pada call ini1.25× hingga 2×
outputtokens yang dihasilkan model dan dikirim kepadamu5× hingga 6×
reasoningtokens yang dihasilkan model dan tidak dikirim kepadamutarif output

Tiga dari lima itu belum ada sebagai baris terpisah dua tahun lalu, dan dua baris cache adalah yang sering disalahpahami orang, karena cache write biayanya lebih mahal daripada input biasa, bukan lebih murah. Kamu membayar premium untuk menyimpan sesuatu agar nanti bisa membayar diskon untuk membacanya kembali, dan apakah pertukaran itu bagus sepenuhnya bergantung pada berapa kali kamu membacanya.

Bucket reasoning adalah milik Bab 12, kini diberi harga, dan ia membawa detail yang perlu dinyatakan terang-terangan: dokumentasi Google mengatakan pricing «is based on the full thought tokens the model needs to generate, despite only the summary being output from the API.»4 Kamu ditagih untuk tokens yang tidak pernah ditransmisikan kepadamu. Ini satu-satunya bucket yang isinya tidak bisa kamu hitung, inspeksi, atau verifikasi.

Sekarang bagian yang membuat ini menjadi masalah normalisasi, bukan masalah perkalian. Setiap provider melaporkan bucket ini dengan nama berbeda, dan — inilah jebakannya — dua di antaranya memakai kata yang sama untuk dua kuantitas berbeda.

Ambil satu call: 4.837 token dibaca dari cache, 110 fresh, 142 output tokens yang terlihat, 300 reasoning tokens.

three usage payloads, one callJSON
// OpenAI-compatible
{ "usage": { "prompt_tokens": 4947,
             "prompt_tokens_details": { "cached_tokens": 4837 },
             "completion_tokens": 442,
             "completion_tokens_details": { "reasoning_tokens": 300 } } }

// Anthropic
{ "usage": { "input_tokens": 110,
             "cache_read_input_tokens": 4837,
             "cache_creation_input_tokens": 0,
             "output_tokens": 442 } }

// Gemini
{ "usageMetadata": { "promptTokenCount": 4947,
                     "cachedContentTokenCount": 4837,
                     "candidatesTokenCount": 142,
                     "thoughtsTokenCount": 300 } }

Lihat prompt_tokens: 4947 dan input_tokens: 110. Kedua field adalah jumlah input token untuk prompt yang sama. OpenAI menyertakan cached tokens; Anthropic mengecualikannya — dokumentasinya menyatakan identitas itu secara eksplisit, total_input_tokens = cache_read_input_tokens + cache_creation_input_tokens + input_tokens.5 input_tokens milik Anthropic berarti «tokens setelah cache breakpoint terakhir kamu».

Dan lihat output-nya. OpenAI dan Anthropic sama-sama melaporkan 442, yang sudah berisi 300 reasoning tokens. Gemini melaporkan 142 dan menaruh 300 di field tersendiri. Bab 12 menandai ini sebagai inkompatibilitas antara dua cara menghitung pekerjaan yang sama; di sini terlihat biayanya.

Normalizer sepanjang tiga puluh baris dan ia tidak opsional:

normalise.tsTS
export interface Usage {
  promptTokens?: number;        // input, NOT cached
  cachedInputTokens?: number;   // read from cache
  cacheWriteTokens?: number;    // written to cache on this call
  completionTokens?: number;    // output
  reasoningTokens?: number;     // billed apart from output (Gemini only)
}

const num = (v: unknown) => (typeof v === "number" && isFinite(v) ? v : 0);

export const fromOpenAI = (raw: any): Usage => {
  const u = raw.usage ?? {}, d = u.prompt_tokens_details ?? {};
  const cached = num(d.cached_tokens), write = num(d.cache_write_tokens);
  return {
    promptTokens: Math.max(0, num(u.prompt_tokens) - cached - write), 
    cachedInputTokens: cached,
    cacheWriteTokens: write,
    completionTokens: num(u.completion_tokens),   // reasoning already inside
    reasoningTokens: 0,
  };
};

export const fromAnthropic = (raw: any): Usage => {
  const u = raw.usage ?? {};
  return {
    promptTokens: num(u.input_tokens),            // already excludes cache
    cachedInputTokens: num(u.cache_read_input_tokens),
    cacheWriteTokens: num(u.cache_creation_input_tokens),
    completionTokens: num(u.output_tokens),
    reasoningTokens: 0,
  };
};

export const fromGemini = (raw: any): Usage => {
  const m = raw.usageMetadata ?? {}, cached = num(m.cachedContentTokenCount);
  return {
    promptTokens: Math.max(0, num(m.promptTokenCount) - cached),
    cachedInputTokens: cached,
    cacheWriteTokens: 0,
    completionTokens: num(m.candidatesTokenCount), // EXCLUDES thinking
    reasoningTokens: num(m.thoughtsTokenCount),    // billed at output rate
  };
};

Jalankan tiga payload di atas melalui tiga reader dan ketiganya menghasilkan Usage yang sama, dan karena itu angka yang sama: $0.006491. Kesepakatan itulah seluruh alasan layer ini ditulis.

Jika salah, inilah biayanya, pada call yang sama:

kesalahanditagiherror
memperlakukan cached_tokens sebagai tambahan atas prompt_tokens$0.0161652.49× — kamu menagih prompt dua kali
memperlakukan cache reads sebagai gratis, bukan 0.1×$0.0055240.85× — kamu menanggung 15 %
membaca candidatesTokenCount dan mengabaikan thoughtsTokenCount$0.00289155 % dari call menghilang

Yang ketiga berbahaya, karena gagal diam-diam ke arah kabar baik. Dashboard kamu menunjukkan reasoning model berbiaya kurang dari separuh biaya sebenarnya, dan tidak ada apa pun di mana pun yang memunculkan error.

Setelah bucket dinormalisasi, cost function-nya pendek. Bagian yang tidak langsung jelas hanyalah tier lookup, yang dijelaskan bagian berikutnya:

cost.tsTS
export interface Tier { maxPromptTokens: number | null; price: number }
export interface Pricing {
  input: Tier[]; output: Tier[];
  cachedInput?: Tier[]; cacheWrite?: Tier[]; reasoning?: Tier[];
}

const tierPrice = (tiers: Tier[] | undefined, contextSize: number, fallback?: Tier[]) => {
  const table = tiers ?? fallback;
  if (!table?.length) return 0;
  const sorted = [...table].sort(
    (a, b) => (a.maxPromptTokens ?? Infinity) - (b.maxPromptTokens ?? Infinity));
  for (const t of sorted)
    if (t.maxPromptTokens === null || contextSize <= t.maxPromptTokens) return t.price;
  return sorted[sorted.length - 1].price;
};

export function computeCost(pricing: Pricing, usage: Usage): number {
  const fresh = usage.promptTokens ?? 0;
  const read  = usage.cachedInputTokens ?? 0;
  const write = usage.cacheWriteTokens ?? 0;
  const out   = usage.completionTokens ?? 0;
  const think = usage.reasoningTokens ?? 0;
  const contextSize = fresh + read + write;   // the tier depends on the WHOLE prompt
  return fresh * tierPrice(pricing.input, contextSize)
       + read  * tierPrice(pricing.cachedInput, contextSize, pricing.input)
       + write * tierPrice(pricing.cacheWrite,  contextSize, pricing.input)
       + out   * tierPrice(pricing.output, contextSize)
       + think * tierPrice(pricing.reasoning, contextSize, pricing.output);
}

Ada dua keputusan desain di sana yang layak dipertahankan. Fallback — harga cache yang jatuh kembali ke input, reasoning ke output — mengodekan arti tabel yang hilang: reasoning tokens pada Gemini ditagih dengan tarif output, jadi harga reasoning yang absen bukan nol, melainkan harga output. Dan contextSize menjumlahkan ketiga bucket input, bukan hanya yang fresh, karena tier dipilih berdasarkan seberapa panjang prompt, bukan berdasarkan seberapa banyak bagian prompt yang dikenai harga penuh.

prompt caching menyimpan computed state model untuk sebuah prefix dari prompt kamu, sehingga request berikutnya dengan prefix yang sama melewati recomputation. Empat sifat mengikuti dari kata «prefix», dan keempatnya sering mengejutkan orang.

Cache mencocokkan dari awal rendered prompt ke depan, lalu berhenti pada byte pertama yang berbeda. Tidak ada kredit parsial untuk konten yang muncul belakangan dalam urutan berbeda. OpenAI menyatakannya lugas: «cache reuse requires the entire rendered prefix to match.»6

Di bawah itu, tidak ada yang di-cache dan tidak ada error yang dikembalikan. Di OpenAI, minimumnya 1.024 token untuk GPT-5.6 dan setelahnya, serta 2.048 untuk model lebih lama. Di Anthropic, rentangnya 512 hingga 4.096 tergantung model — 1.024 untuk Claude Sonnet 4.5, 4.096 untuk Claude Haiku 4.5. Jika kedua field cache kembali nol, biasanya inilah alasannya.

Tautan ke bagian: Menulis lebih mahal daripada membaca, dan lebih mahal daripada tidak caching

Di OpenAI dan Anthropic, cache write adalah 1.25× tarif uncached input untuk cache berumur pendek, dan cache satu jam Anthropic adalah 2×. Read adalah 0.1×. Google tidak mengenakan biaya untuk write, tetapi menyewakan storage: $4.50 per juta token per jam di Gemini 2.5 Pro.

Ia kedaluwarsa, dan hidup di satu mesin

Tautan ke bagian: Ia kedaluwarsa, dan hidup di satu mesin

Entry default Anthropic hidup lima menit, diperbarui gratis pada setiap hit. OpenAI minimal tiga puluh menit setelah write atau reuse terakhir. Dan OpenAI mencatat bahwa cached states hidup di mesin individual, jadi request hanya hit jika di-route ke mesin yang memegang entry itu — inilah yang dipengaruhi prompt_cache_key, tanpa menjamin.

Break-even-nya cukup kecil untuk diingat, dan dokumentasi OpenAI melakukan aritmetikanya: menulis prefix sekali dan memakainya ulang sekali biayanya 1.35× biaya input biasa, dibanding 2× untuk memprosesnya dua kali uncached; sepanjang sepuluh request, satu write dan sembilan read biayanya 2.15× dibanding 10×. Satu reuse membayar write. Anthropic berakhir di tempat yang sama: satu read untuk cache lima menit, dua untuk cache satu jam.

Sekarang percakapan empat puluh giliran lagi, dengan caching aktif dan prefix stabil:

uncached inputcache readscache writestotal
tanpa cache112,617$0.274386
caching2,887104,7834,947$0.088250

Lebih murah enam puluh delapan persen, dan tiga angka dalam tabel itu layak diperhatikan.

Cache belum aktif sampai giliran 6. prompt belum mencapai 1.024 token sampai saat itu, jadi lima giliran pertama ditagih persis seperti sebelumnya — dan giliran keenam ditagih lebih buruk, dengan premium write 1.25×, karena itulah giliran yang mengisi cache. Read pertama datang pada giliran 7. 2.887 uncached tokens dalam tabel adalah aritmetikanya: senilai lima giliran, bukan enam. Caching adalah diskon untuk prompt panjang, dan percakapan pendek tidak mendapat apa-apa darinya.

Premium write adalah $0.002474, yaitu 2,8 % dari tagihan cached. Setiap giliran menulis tail barunya, empat puluh kali, dan seluruh premium write itu hanya kesalahan pembulatan dibanding penghematan read. Biaya write perlu dipahami dengan tepat agar kamu berhenti mengkhawatirkannya.

Hanya 2.887 token yang dikenai harga input penuh dari 112.617. Begitulah bentuk cache yang bekerja: hampir semuanya read.

Urutan prompt menentukan apakah semua ini terjadi

Tautan ke bagian: Urutan prompt menentukan apakah semua ini terjadi

Inilah kegagalan yang benar-benar memakan uang, dan ini bug satu baris.

Taruh sesuatu yang berubah pada setiap call di bagian depan prompt — timestamp, request id, nama pengguna, baris «hari ini adalah», dokumen yang baru di-retrieve — dan prefix berbeda sejak byte pertama. Tidak ada yang cocok. Setiap call miss. Dan karena setiap call menghadirkan prefix baru, setiap call juga menulis.

Percakapan yang sama, empat puluh giliran yang sama, caching aktif, dengan timestamp per call di bagian atas system prompt:

totaldibanding
tanpa caching sama sekali$0.274386
caching, prefix stabil$0.088250−67.8 %
caching, prefix volatile$0.329251+20.0 %

Mengaktifkan prompt caching membuat percakapan dua puluh persen lebih mahal daripada tidak mengaktifkannya. Kamu membayar premium write 1.25× atas 109.730 token dan membaca kembali nol. Tidak ada error, tidak ada warning, dan fiturnya menyala.

Jadi aturannya, dan ini seluruh prompt caching dalam satu baris: konten stabil di depan, konten variabel di belakang. System instructions, tool definitions, dan reference material dulu; timestamps, identitas pengguna, dan pertanyaan saat ini terakhir. Anthropic membuat hierarkinya eksplisit — cache mengikuti toolssystemmessages, dan perubahan di level mana pun membatalkan level itu dan semua setelahnya, jadi mengedit satu tool description membatalkan seluruh cache.5

Dua konsekuensi sering membuat orang tersandung. Mengubah tool mana yang enabled mengubah tool definitions, jadi feature flag yang menambahkan tool untuk sebagian pengguna membelah cache kamu menjadi dua. Dan di Anthropic, menyalakan atau mematikan web search atau citations memodifikasi system prompt, yang membatalkan cache system dan message tanpa kamu menyentuh satu baris pun teksmu sendiri.

Respons yang jelas terhadap tagihan kuadratik adalah berhenti mengirim seluruh riwayat: simpan selusin message terakhir dan buang sisanya. Itu memang menurunkan tagihan, dan biasanya langkah yang salah, dan pengukurannya menunjukkan alasannya.

strategitotaldibanding riwayat penuh + cache
riwayat penuh, tanpa cache$0.274386+211 %
riwayat penuh, caching$0.088250
12 message terakhir, tanpa cache$0.118712+35 %
12 message terakhir, caching aktif$0.122546+39 %

Memotong menjadi window dua belas message 57 % lebih murah daripada mengirim semuanya uncached — perbandingan yang dibuat semua orang, dan alasan teknik ini populer. Tetapi itu 39 % lebih mahal daripada mengirim semuanya dengan cache yang bekerja, dan menyalakan caching bersamaan dengan truncation membuatnya sedikit lebih buruk, bukan lebih baik.

Mekanismenya lagi-lagi prefix. Sliding window membuang message tertua setiap giliran, sehingga prompt tidak lagi dimulai di tempat ia dimulai terakhir kali dan setiap giliran menghadirkan prefix baru. Panduan OpenAI mengatakan persis ini: «summarisation, compaction, or context truncation can change the prefix and reset cache reuse.»6 Pada giliran 40, windowed prompt berisi 813 token, di bawah minimum 1.024-token, jadi tidak bisa di-cache sama sekali.

Dan uang adalah separuh biaya yang murah. Yang kamu buang adalah instruksi yang diberikan pengguna pada giliran 2 yang dibutuhkan model pada giliran 40. Truncation menukar tagihan yang bisa kamu lihat dengan kegagalan yang tidak bisa kamu lihat, dan melakukannya dengan benar — compaction, catatan terstruktur yang disimpan di luar window, retrieving riwayat sesuai kebutuhan — adalah subjek Bab 24.

Melewati tier mengubah harga seluruh request

Tautan ke bagian: Melewati tier mengubah harga seluruh request

Context panjang tidak semata-mata lebih mahal karena lebih panjang. Setelah melewati threshold, ia lebih mahal per token, dan threshold itu berlaku retroaktif pada seluruh prompt.

Halaman model OpenAI untuk gpt-5.6-terra menyatakannya dalam satu kalimat: «Prompts with >272K input tokens are priced at 2x input and 1.5x output for the full request.»7 Bukan untuk kelebihannya. Untuk semuanya.

the most expensive token you will ever sendTEXT
prompt 271,999 + 500 output  ->  $0.5500
prompt 272,000 + 500 output  ->  $0.5500
prompt 272,001 + 500 output  ->  $1.0970

Satu token, lima puluh lima sen. Jika layananmu membangun prompt dari dokumen yang di-retrieve dengan ukuran yang tidak kamu kendalikan, kamu punya tebing dalam cost model di batas yang tidak pernah ditulis siapa pun di timmu.

Pricing Google bekerja dengan cara yang sama dengan threshold 200.000-token: Gemini 2.5 Pro adalah $1.25 per juta input tokens untuk prompt hingga 200K dan $2.50 di atasnya, dengan output naik dari $10.00 ke $15.00.8 Anthropic memilih arah lain — per 6 September 2026, dokumentasinya menyatakan bahwa Claude 4.6 dan setelahnya menyertakan penuh one-million-token window dengan pricing standar, jadi «a 900k-token request is billed at the same per-token rate as a 9k-token request.»9 Model lebih awal masih memakai surcharge.

Inilah alasan harga bukan sebuah angka. Harga adalah tabel tiers yang dikunci oleh panjang prompt, yaitu fungsi Tier[] dalam cost function, dan inilah alasan computeCost memilih tier memakai seluruh prompt, bukan setiap bucket secara terpisah.

Prefill, decode, dan mengapa output enam kali input

Tautan ke bagian: Prefill, decode, dan mengapa output enam kali input

Lima bucket itu memetakan ke dua fase dari Bab 13, dan begitu kamu melihat pemetaannya, rasio harga berhenti terlihat arbitrer.

Input tokens adalah prefill. Seluruh prompt melewati model dalam satu pass, diproses secara paralel — perkalian matriks besar, compute-bound. Biaya per token rendah, dan inilah fase yang menentukan time to first token: prompt 4.947-token memiliki 4.947 token prefill yang harus dilakukan sebelum kata pertama muncul.

Output tokens adalah decode. Mereka diproduksi satu per satu, masing-masing sebuah forward pass penuh yang membaca seluruh KV cache, dengan GPU lebih banyak menunggu memori daripada menghitung. Inilah fase yang menentukan tokens per second, tidak bisa diparalelkan dalam satu response, dan inilah alasan output berbiaya sekitar enam kali input pada model yang dihargai di sini: $12.00 dibanding $2.00 per juta token.

Tiga konsekuensi langsung mengikuti. cache read menggantikan kerja prefill, jadi ia membeli latency dan uang sekaligus — diskon yang sama muncul sebagai tagihan lebih rendah dan penantian lebih pendek untuk token pertama. Reasoning tokens adalah decode yang tidak pernah kamu lihat, itulah alasan reasoning model tidak streaming apa pun selama beberapa detik lalu menjawab cepat: Bab 12 memperingatkan konsekuensi interface, dan ini konsekuensi invoice. Dan membatalkan stream tidak menghentikan generationBab 14 membangun cancellation dan menyisakan harganya untuk bab ini, dan harganya adalah jumlah output penuh, karena tokens diproduksi dan ditagih apakah ada yang mendengarkan atau tidak. Hal yang sama berlaku untuk jawaban yang tidak disimpan siapa pun: meregenerasi jawaban giliran 40 lima kali biayanya $0.057990 untuk satu yang tersisa di layar.

Menghitung token sebelum kamu mengirimnya

Tautan ke bagian: Menghitung token sebelum kamu mengirimnya

Tokenizer Bab 7 adalah Python dan tetap di sana. Budgeting terjadi di server yang membangun request, jadi harus terjadi di sini, dan hanya ada tiga tingkat akurasi yang tersedia.

Level satu: hitung lokal. js-tiktoken mengirimkan BPE merge tables yang sama dengan tiktoken Python, jadi hitungan byte-for-byte identik untuk encoding OpenAI, tanpa network call:

count.tsTS
import { getEncoding } from "js-tiktoken";

const enc = getEncoding("o200k_base");
const PER_MESSAGE = 4;   // role and delimiters added by the chat template
const PER_REPLY = 3;     // priming for the assistant turn

export function promptTokens(messages: { role: string; content: string }[]) {
  return messages.reduce(
    (sum, m) => sum + enc.encode(m.content).length + PER_MESSAGE, PER_REPLY);
}

Dua konstanta itu penting dan di situlah hitungan lokal mulai meleset. Teksmu bukan yang di-tokenize — chat template dari Bab 11 membungkus setiap message dalam role markers lebih dulu, dan itu tokens yang kamu bayar. Empat per message dan tiga untuk reply priming adalah pendekatan konvensional untuk model chat OpenAI; di sepanjang delapan puluh satu message percakapan di atas, jumlahnya 324 token, 6,4 % dari panjangnya. Hitungan di sini diperiksa silang terhadap tiktoken Python dari Bab 7 pada semua delapan puluh satu string dan identik.

Level dua: tanya provider. Anthropic mengekspos /v1/messages/count_tokens dan Google mengekspos count_tokens, keduanya menerima bentuk request yang sama dengan call nyata dan mengembalikan jumlah input token secara gratis. Gunakan saat kamu tidak bisa menghitung lokal — dan kamu tidak bisa menghitung lokal untuk Anthropic, yang tokenizer-nya tidak dipublikasikan. Dokumentasi Anthropic berhati-hati tentang apa yang diberikannya: count itu «is an estimate», dan «may include tokens added automatically by Anthropic for system optimizations», yang «you are not billed».10

Level tiga: baca usage di response. Itulah kebenarannya, dan ia datang setelah uang dibelanjakan. Persis itulah alasan dua level pertama ada — untuk memutuskan apakah request dikirim, bukan untuk menagihnya.

Hal-hal yang kamu bayar tetapi tidak ditunjukkan siapa pun

Tautan ke bagian: Hal-hal yang kamu bayar tetapi tidak ditunjukkan siapa pun

Empat line item yang tidak muncul sebagai line item.

System prompt, dibayar pada setiap call. Yang di atas adalah 192 token dengan template overhead-nya. Sepanjang empat puluh call, itu 7.680 token — 5,6 % dari seluruh tagihan percakapan ini, untuk delapan baris yang ditulis sekali. Ia juga kandidat cache terbaik, karena stabil sekaligus berada paling depan.

Tool definitions. Nama, deskripsi, dan JSON schema setiap tool dikirim pada setiap request, dan provider menambahkan scaffolding di atasnya. Anthropic mempublikasikan angkanya: mengaktifkan tools saja menambahkan hidden system prompt 496 token di Claude Sonnet 4.5 dengan tool_choice disetel ke auto, atau 588 dengan any atau named tool.9 Itu sebelum schema kamu sendiri. Bab 18 membangun katalognya; Bab 24 mengukur apa yang dimakannya.

Setiap generation, termasuk yang kamu buang. Lima regeneration biayanya lima kali. Chat menampilkan satu.

Thoughts yang tidak ditunjukkan kepadamu. Billing didasarkan pada full thought tokens meskipun hanya summary yang dikembalikan, dan tidak ada akuntansi milikmu yang bisa mengaudit angka itu.

Memiliki 200K token bukan berarti menggunakannya

Tautan ke bagian: Memiliki 200K token bukan berarti menggunakannya

Satu peringatan penutup, karena ini pikiran berikutnya yang alami dan jawabannya bukan yang paling jelas.

Window satu juta token bukan berarti satu juta token yang berguna. Akurasi retrieval menurun tergantung posisi: Liu dkk. menemukan bahwa model menemukan informasi dengan andal di awal dan akhir input panjang, dan jauh kurang andal di tengah.11 Window yang lebih besar membeli kemampuan untuk mengirim lebih banyak, bukan kepastian untuk dibaca.

Fenomena itu diukur sekali dalam course ini — retrieval rate pada sembilan posisi dalam prompt 853-token yang sama — dan tempatnya di Bab 24, di mana ia mengubah apa yang dilakukan agent. Ia dikutip di sini karena mengubah apa yang sebaiknya kamu beli: token termurah adalah token yang tidak kamu kirim.

Sekarang kamu bisa memprediksi berapa biaya sebuah call sebelum membuatnya, membaca berapa biayanya sesudahnya, dan membedakan keduanya. Itu mencakup semua hal tentang request kecuali bagian yang belum kamu sentuh: knob.

Bab 17 adalah sampling — temperature, top-p, top-k, penalties, dan determinisme yang tidak kamu miliki. Ia dimulai dengan membongkar error paling luas di bidang ini, bahwa temperature adalah kenop kreativitas. Bukan: temperature membagi logits dari Bab 4 sebelum softmax, dan menaikkannya tidak membuat model imajinatif, melainkan menaikkan probabilitas tokens yang oleh model sendiri diberi skor lebih buruk. Dari sana, mengapa greedy decoding menghasilkan teks yang secara terukur lebih buruk daripada sampling, mengapa top-k dan top-p gagal pada bentuk distribusi yang berlawanan, dan eksperimen yang menutup bab: dua puluh forward pass identik pada temperature 0 kembali bit-for-bit identik saat model berjalan sendirian, dan menaruh prompt yang sama dalam batch bersama request orang lain menggeser 97 % logits-nya.

Tidak semuanya cocok. Alasannya dimulai dari kotak floating-point di Bab 2.


Semua harga, threshold, dan multiplier dalam bab ini dibaca dari halaman provider masing-masing pada 6 September 2026 dan dinyatakan dengan tanggal itu karena semuanya akan berubah. Metode lebih penting daripada angkanya: bucket, aturan prefix, dan aritmetika tier telah stabil selama dua tahun sementara setiap angka di dalamnya bergerak.

Kuliah Stanford CS336 2, Resource accounting, adalah perlakuan akademik paling dekat untuk materi ini dan bacaan lanjutan yang tepat: ia melakukan aritmetika yang sama di sisi training seperti yang dilakukan bab ini di sisi inference. Hitungan token di sini dibuat dengan js-tiktoken 1.0.21 memakai encoding o200k_base dan cl100k_base, atas percakapan empat puluh giliran sepanjang 5.090 token; per-message template overhead adalah pendekatan konvensional empat-plus-tiga dan dinyatakan di mana pun ia disertakan. Angka cache, tier, dan truncation adalah aturan pricing terdokumentasi yang diterapkan pada jumlah token terukur tersebut, bukan observasi response API live — tidak ada paid call yang dibuat untuk menghasilkan bab ini, yang juga merupakan alasan jujur mengapa klaim latency bersifat kualitatif dan klaim biaya tidak.

  1. Dao, T., Fu, D. Y., Ermon, S., Rudra, A. dan Ré, C. FlashAttention: Fast and Memory-Efficient Exact Attention with IO-Awareness. arXiv:2205.14135 (2022). Mengapa batas atas bergerak tanpa biaya asimtotik berubah.

  2. Chen, S., Wong, S., Chen, L. dan Tian, Y. Extending Context Window of Large Language Models via Positional Interpolation. arXiv:2306.15595 (2023).

  3. Peng, B., Quesnelle, J., Fan, H. dan Shippole, E. YaRN: Efficient Context Window Extension of Large Language Models. arXiv:2309.00071 (2023).

  4. Google, Thinking, ai.google.dev/gemini-api/docs/thinking, dan Token counting, ai.google.dev/gemini-api/docs/tokens, keduanya diakses 2026-09-06. «Pricing is based on the full thought tokens the model needs to generate, despite only the summary being output from the API.» Usage object melaporkan total_input_tokens, total_output_tokens, total_thought_tokens, total_cached_tokens, total_tool_use_tokens, dan total_tokens — enam bucket, dengan thoughts dan tool use di luar output count. Nama field lebih awal untuk kuantitas yang sama, masih dikembalikan oleh surface generateContent, adalah thoughtsTokenCount, didokumentasikan di halaman ketiga, ai.google.dev/gemini-api/docs/generate-content/thinking.

  5. Anthropic, Prompt caching, docs.anthropic.com/en/docs/build-with-claude/prompt-caching, diakses 2026-09-06. Sumber hierarki invalidation toolssystemmessages dan tabelnya; panjang minimum cacheable per model; identitas total_input_tokens = cache_read_input_tokens + cache_creation_input_tokens + input_tokens; serta masa hidup default lima menit yang diperbarui tanpa biaya pada setiap hit. 2

  6. OpenAI, Prompt caching, platform.openai.com/docs/guides/prompt-caching, diakses 2026-09-06. Sumber untuk: aturan entire-rendered-prefix; minimum cacheable prefix (1.024 visible input tokens pada GPT-5.6 dan setelahnya, 2.048 sebelumnya); multiplier write 1.25× dan read 0.1×, serta ketiadaan biaya write pada GPT-5.5 dan sebelumnya; masa hidup 30 menit; batas four-writes-per-request dan fifty-breakpoint; catatan machine-affinity dan prompt_cache_key; contoh kerja break-even 1.35×, 2.15×, dan 10×; serta pernyataan bahwa summarisation, compaction, atau truncation me-reset cache reuse. 2

  7. OpenAI, Pricing (platform.openai.com/docs/pricing) dan halaman model untuk gpt-5.6-terra, keduanya diakses 2026-09-06. gpt-5.6-terra, standard service tier, per juta tokens: input $2.00, cached input $0.20, cache writes $2.50, output $12.00; long context input $4.00, cached $0.40, writes $5.00, output $18.00; «prompts with >272K input tokens are priced at 2x input and 1.5x output for the full request»; context window 1.050.000 token dengan maksimum 922.000 input tokens. Tabel yang sama mencantumkan gpt-6-astra pada $10.00/$1.00/$12.50/$50.00 dan gpt-5.6-luna pada $0.20/$0.02/$0.25/$1.20. Setiap biaya terhitung dalam bab ini memakai tarif standard short-context gpt-5.6-terra.

  8. Google, Gemini Developer API pricing, ai.google.dev/gemini-api/docs/pricing, diakses 2026-09-06. Gemini 2.5 Pro, per juta tokens: input $1.25 untuk prompt hingga 200K dan $2.50 di atasnya; output $10.00 dan $15.00, dalam kedua kasus diberi label «including thinking tokens»; context caching $0.125 dan $0.25, plus biaya storage $4.50 per juta token per jam. Gemini 3.1 Pro Preview memakai threshold 200K yang sama pada input $2.00/$4.00 dan output $12.00/$18.00.

  9. Anthropic, Pricing, docs.anthropic.com/en/docs/about-claude/pricing, diakses 2026-09-06. Per juta tokens, base input / 5-minute cache write / 1-hour cache write / cache read / output: Claude Sonnet 4.5 $3 / $3.75 / $6 / $0.30 / $15; Claude Haiku 4.5 $1 / $1.25 / $2 / $0.10 / $5; Claude Opus 5 $5 / $6.25 / $10 / $0.50 / $25. Multiplier: 1.25× untuk write lima menit, 2× untuk write satu jam, 0.1× untuk read. Juga sumber pernyataan long-context («Claude 4.6 and later models... include the full 1M token context window at standard pricing»), jumlah token tool-use system prompt (496 token pada Claude Sonnet 4.5 dengan tool_choice berupa auto atau none, 588 dengan any atau named tool), dan catatan bahwa Claude 4.7 dan setelahnya memakai tokenizer lebih baru yang menghasilkan «approximately 30 % more tokens for the same text». 2 3

  10. Anthropic, Token counting, docs.anthropic.com/en/docs/build-with-claude/token-counting, diakses 2026-09-06. Endpoint /v1/messages/count_tokens menerima input yang sama dengan message dan mengembalikan jumlah input token; dokumentasi menyatakan bahwa count itu estimasi, bahwa ia mungkin menyertakan tokens yang ditambahkan Anthropic untuk optimisasi system, dan bahwa tokens itu tidak ditagih.

  11. Liu, N. F., Lin, K., Hewitt, J., Paranjape, A., Bevilacqua, M., Petroni, F. dan Liang, P. Lost in the Middle: How Language Models Use Long Contexts. arXiv:2307.03172 (2023). Dikutip di sini, diukur di Bab 24.


Dibuat oleh

David Vicente Campos

Pendiri NeuraLIA Labs & salah satu pendiri MyRealFood

Saya seorang insinyur komputer lulusan Universitas León. Saya ikut mendirikan MyRealFood, tempat saya sebagai CTO membangun aplikasi yang telah digunakan jutaan orang untuk makan lebih sehat, dan saya mendirikan NeuraLIA Labs, tempat saya membangun produk AI. Di sini saya menulis tentang hal-hal yang harus saya pahami sepanjang perjalanan, sebagaimana dulu saya berharap ada yang menjelaskannya kepada saya.

Selengkapnya tentang penulis

Diterbitkan oleh NeuraLIA Labs.

Dapatkan postingan baru di inbox kamu

Berita AI, panduan, dan update produk — email singkat saat kami menerbitkan sesuatu yang layak kamu baca.

Indeks kursus

Abstract software decision engine with branching paths, probability nodes, and glowing gates.
jev11 menit baca

Model AI Jev dibuat untuk keputusan, bukan prosa

Jev dari TypeSafe AI menarik perhatian karena memperlakukan kecerdasan software sebagai persoalan probabilitas: pilih cabang yang tepat, sertakan keyakinan, dan hindari membayar LLM untuk menulis teks saat kode membutuhkan keputusan.

Abstract agent runtime sorting documents, memory blocks and pointer nodes inside a bounded context frame.
context-engineering11 menit baca

Rekayasa konteks untuk agen AI jangka panjang

Agen yang berjalan lama tidak gagal hanya karena window-nya kecil. Mereka gagal ketika file, output tool, dan riwayat lama menggeser tugas yang seharusnya diselesaikan agen.

Siap membiarkan LIA yang memilih?

Berkarya dengan semua model AI dalam satu tempat — mulai gratis hari ini.