Autentikasi
Hampir semua permintaan ke AstroWay API diautentikasi melalui header X-Api-Key. Pengecualian: 14 endpoint /v1/reference/* (signs, planets, houses, aspects, …) berfungsi secara publik tanpa kunci dengan batasan 30 permintaan / jam per IP. Jika permintaan dibuat oleh server kamu, kirimkan header X-AstroWay-Site-URL dan batasnya akan menjadi 300 permintaan / jam per situs: detail.
Untuk semua endpoint komputasi /v1/* (chart, synastry, transits, /reports, /tarot, dll.) - hanya X-Api-Key. Untuk operasi pengguna /v1/me/* (GET /me, DELETE /me/account) - Bearer JWT, yang dikeluarkan melalui /v1/auth/login. OAuth/session-cookies tidak digunakan pada API publik. Kamus referensi /v1/reference/* - tanpa kunci, gratis (tabel lookup kanonis).
Format Kunci
Section titled “Format Kunci”aw_live_aB3xY7pQ9rN2mK4jH8vC5tL6wZ1fD0eRaw_test_aB3xY7pQ9rN2mK4jH8vC5tL6wZ1fD0eRaw_live_: produksi, memotong kredit dari saldoaw_test_: sandbox, permintaan mengembalikan respons stub (atau perhitungan nyata minimal), tidak memotong kredit, ditandai secara terpisah di dashboard- Setelah prefiks: 32 karakter base62, acak secara kriptografis
- Kunci ditampilkan dalam bentuk jelas hanya sekali saat pembuatan. Selanjutnya di dashboard - hanya 4 karakter pertama dan terakhir.
Header Permintaan
Section titled “Header Permintaan”POST /v1/chart HTTP/1.1Host: api.astroway.infoX-Api-Key: aw_live_aB3xY7pQ9rN2mK4jH8vC5tL6wZ1fD0eRContent-Type: application/jsonPostman Collection
Section titled “Postman Collection”Jika kamu lebih nyaman dengan Postman daripada curl/SDK - ada collection siap pakai dengan semua 771 endpoint, dibagi ulang menjadi 55 folder berdasarkan tag OpenAPI, dengan contoh permintaan yang sudah disiapkan. Auth dikonfigurasi pada tingkat collection: kamu memasukkan kunci ke variabel apiKey sekali, semua permintaan akan menggunakannya.
- Published docs: documenter.getpostman.com/view/54689779/2sBXqNmy3n
- Public workspace: postman.com/astroway-info/astroway-api
- Unduh JSON: astroway-api.json (≈ 5 MB) - impor langsung ke Postman atau Insomnia
Collection ini dibuat secara otomatis dari OpenAPI spec - diperbarui dengan setiap deployment.
Membuat dan Mengelola Kunci
Section titled “Membuat dan Mengelola Kunci”Melalui dashboard:
- api.astroway.info/dashboard/keys
- Kamu dapat memiliki hingga 10 kunci aktif per akun secara bersamaan
- Setiap kunci memiliki nama, bidang
name(misalnyaproduction-backend,ci-tests,local-dev)
Melalui API (untuk integrasi self-service):
curl -X POST https://api.astroway.info/v1/keys \ -H "X-Api-Key: aw_live_master_key" \ -H "Content-Type: application/json" \ -d '{"name": "ci-tests", "mode": "test"}'// Equivalent via @astroway/sdk: aw.client.POST('/keys', { body: { name, mode } })const r = await fetch('https://api.astroway.info/v1/keys', { method: 'POST', headers: { 'X-Api-Key': process.env.ASTROWAY_MASTER_KEY!, 'Content-Type': 'application/json', }, body: JSON.stringify({ name: 'ci-tests', mode: 'test' }),});
const { data: created } = await r.json();console.log(created.api_key); // shown once - store it now# Equivalent via `astroway` (PyPI): aw.post('/keys', body={'name': ..., 'mode': ...})import os, requests
r = requests.post( 'https://api.astroway.info/v1/keys', headers={'X-Api-Key': os.environ['ASTROWAY_MASTER_KEY']}, json={'name': 'ci-tests', 'mode': 'test'},)created = r.json()['data']print(created['api_key']) # shown once - store it now<?phpuse GuzzleHttp\Client;
$aw = new Client(['base_uri' => 'https://api.astroway.info/v1/']);$r = $aw->post('keys', [ 'headers' => ['X-Api-Key' => getenv('ASTROWAY_MASTER_KEY')], 'json' => ['name' => 'ci-tests', 'mode' => 'test'],]);
$created = json_decode($r->getBody(), true)['data'];echo $created['api_key']; // shown once - store it nowKunci untuk Browser
Section titled “Kunci untuk Browser”Kunci server-only tipikal: jika permintaan dengannya membawa header Origin atau
Referer, akan muncul 403 ORIGIN_FORBIDDEN. Ini disengaja, dan inilah yang menangkap
kunci yang secara tidak sengaja tertinggal di frontend.
Ketika widget atau halaman perlu mengakses API dari browser, kunci dibuat
langsung dengan kebijakan asal. Bidang origin_restriction di POST /v1/keys:
type | Apa yang diizinkan | Kapan digunakan |
|---|---|---|
server-only (default) | hanya permintaan tanpa Origin dan Referer | backend, cron, CI |
public | hanya host yang terdaftar, dan permintaan wajib membawa asal | widget atau halaman di domain kamu, kunci dalam kode sumber |
allowlist | sama seperti public | penulisan usang: masih diterima, tetapi tidak lagi tercantum di openapi.json |
curl -X POST https://api.astroway.info/v1/keys \ -H "X-Api-Key: aw_live_master_key" \ -H "Content-Type: application/json" \ -d '{ "name": "site-widget", "origin_restriction": { "type": "public", "allowed_origins": ["example.com", "*.example.com"] }, "credits_cap_cycle": 20000, "allowed_endpoints": ["chart", "public/*"] }'Aturan pencocokan, diuji di produksi:
- Hingga 20 host per kunci. Skema (
https://) dan port diabaikan, case-insensitive. www.dihapus dari host yang masuk, jadiexample.commencakupwww.example.com. Tidak perlu menambahkan formulir denganwww.secara terpisah, itu tidak mengubah apa pun.*.example.commencakup subdomain (app.example.com), tetapi bukanexample.comitu sendiri. Apex dicantumkan sebagai baris terpisah, seperti pada contoh di atas.- Host yang tidak ada dalam daftar akan menerima
403 ORIGIN_NOT_ALLOWEDdengan host itu sendiri di bidangincoming_origin, agar terlihat baris mana yang hilang. Refererdihitung setara denganOrigin: browser mengirimkannya di manaOrigintidak ada.
Mengubah Daftar untuk Kunci yang Sudah Dibuat
Section titled “Mengubah Daftar untuk Kunci yang Sudah Dibuat”PATCH /v1/keys/{id} menimpa daftar tanpa menyentuh kunci itu sendiri. Hak akses sama dengan POST /v1/keys di atas; di dashboard, ini adalah item “Ubah asal” di menu kunci.
curl -X PATCH https://api.astroway.info/v1/keys/433 \ -H "X-Api-Key: aw_live_master_key" \ -H "Content-Type: application/json" \ -d '{ "origin_restriction": { "type": "public", "allowed_origins": ["example.com", "*.example.com"] } }'Daftar baru berlaku sejak permintaan berikutnya: cache kunci direset saat penulisan, tidak perlu menunggu satu menit. String kunci itu sendiri tidak berubah, jadi tidak perlu menerbitkan ulang halaman maupun backend. Setelah POST /v1/keys/{id}/rotate, daftar disimpan, dan nilai kunci lama segera berhenti berfungsi.
Kelas kunci tidak dapat diedit, karena sudah tertulis di kunci itu sendiri:
| Upaya | Respons |
|---|---|
pk_ menjadi server-only | 400: kelas adalah bagian dari kunci, perlu dicabut dan dibuat yang baru |
aw_ memberikan daftar domain | 400: kunci browser adalah kelas yang berbeda, dibuat sebagai public |
pk_ dengan daftar kosong | 400: kunci tanpa daftar akan menolak setiap permintaan |
pk_ tanpa anggaran atau cakupan (null) | 400: kunci untuk browser selalu dibatasi oleh keduanya, dapat diubah, tetapi tidak dapat dihapus |
Anggaran Kredit untuk Kunci Terpisah
Section titled “Anggaran Kredit untuk Kunci Terpisah”Kredit bersifat bersama untuk seluruh akun, jadi satu kunci dapat menghabiskan semuanya. Untuk kunci backend, ini normal, tetapi tidak untuk kunci dalam kode sumber halaman: daftar domain memberi tahu dari mana dapat diakses, tetapi tidak memberi tahu berapa biayanya.
credits_cap_cycle di PATCH /v1/keys/{id} yang sama membatasi kunci ini:
curl -X PATCH https://api.astroway.info/v1/keys/433 \ -H "X-Api-Key: aw_live_master_key" \ -H "Content-Type: application/json" \ -d '{"credits_cap_cycle": 5000}'null menghapus batasan (kecuali untuk kunci pk_, anggarannya dapat diubah, tetapi tidak dapat dihapus). 0 berarti kunci yang tidak dapat menghabiskan apa pun: cara untuk memarkir kunci tanpa mencabutnya. Penghitung sama dengan kredit, dan direset bersamaan dengan siklus tarif.
Ketika kunci mencapai batas anggarannya, akan muncul 429 KEY_BUDGET_EXHAUSTED, bahkan jika masih ada kredit di akun, dan bahkan pada tarif dengan overage: anggaran yang dapat dihabiskan lebih dari batas dengan uang, itu bukan anggaran. Selama anggaran ditentukan, setiap respons membawa X-Key-Budget-Limit dan X-Key-Budget-Remaining.
Cakupan Endpoint
Section titled “Cakupan Endpoint”Kunci tanpa cakupan memanggil semua yang termasuk dalam tarif. allowed_endpoints mempersempitnya ke daftar jalur: tepat (chart) atau namespace (embed/*). Ini adalah batasan ketiga yang independen: daftar domain memberi tahu dari mana, anggaran berapa banyak, cakupan apa.
curl -X PATCH https://api.astroway.info/v1/keys/433 \ -H "X-Api-Key: aw_live_master_key" \ -H "Content-Type: application/json" \ -d '{"allowed_endpoints": ["embed/*", "public/moon-phase"]}'null menghapus batasan (kecuali untuk kunci pk_, cakupannya wajib). Daftar kosong tidak diterima: itu akan dibaca sebagai “semua” dan “tidak ada”. Jalur ditulis relatif terhadap /v1, tanpa garis miring awal, case-insensitive.
Panggilan di luar daftar akan menerima 403 ENDPOINT_NOT_IN_SCOPE, dan details akan menyebutkan daftar itu sendiri agar tidak perlu menebak. Cakupan berlaku untuk kedua kelas kunci dan untuk /v1/public/* serta /v1/embed/* sama seperti yang lainnya. Pembacaan layanan di bawahnya tidak dibebaskan, tidak seperti kredit: kunci yang dipersempit ke embed/* tidak akan membaca statistiknya sendiri. Ini disengaja, karena kunci dalam kode sumber halaman tidak boleh memberikan biaya akun kepada pengunjung, dan ini tidak menghalangi pengelolaan kunci: dashboard menggunakan sesi, bukan kunci.
Praktik Terbaik
Section titled “Praktik Terbaik”1. Jangan Letakkan Kunci Server-Only di Frontend
Section titled “1. Jangan Letakkan Kunci Server-Only di Frontend”Kunci tipikal adalah rahasia tingkat backend. Jika masuk ke JS yang dieksekusi di browser pengguna - itu akan terlihat di DevTools dan akan bocor. Itulah mengapa kunci semacam itu merespons 403 ORIGIN_FORBIDDEN untuk setiap permintaan dengan Origin atau Referer.
Jika tetap perlu diakses dari browser, ini dilakukan bukan dengan kunci biasa, melainkan dengan kunci terpisah yang dibuat dengan origin_restriction.type: "public": kunci untuk browser. Kunci semacam itu memiliki prefiks pk_, juga terlihat di DevTools, dan inilah intinya - nilainya dibatasi oleh daftar domain kamu, dan permintaan tanpa asal akan ditolaknya.
Benar: backend kamu menyimpan kunci, frontend memanggil backend kamu, backend kamu - ke AstroWay API.
Salah:
// DO NOT DO THISfetch('https://api.astroway.info/v1/chart', { headers: { 'X-Api-Key': 'aw_live_...' }, // visible in browser});2. Variabel Lingkungan, Bukan Hardcode
Section titled “2. Variabel Lingkungan, Bukan Hardcode”# .env (in .gitignore)ASTROWAY_API_KEY=aw_live_...// in codeconst key = process.env.ASTROWAY_API_KEY;if (!key) throw new Error('ASTROWAY_API_KEY is not set');3. Kunci Terpisah untuk Lingkungan Berbeda
Section titled “3. Kunci Terpisah untuk Lingkungan Berbeda”production-backend: produksistaging-backend: stagingci-tests: pipeline CI/CDlocal-dev-maksym: pengembangan lokal setiap developer
Jika satu kunci dikompromikan - cabut kunci itu, yang lain tetap berfungsi.
4. Rotasi
Section titled “4. Rotasi”Frekuensi yang direkomendasikan - sekali setiap 90 hari. Atau segera, jika ada dugaan kebocoran.
Rotasi tanpa downtime:
- Buat kunci baru dengan
nameyang sama +-v2 - Deploy ke produksi (secara paralel dengan yang lama)
- Pastikan penggunaan mengalir ke kunci baru (dashboard)
- Cabut yang lama
5. Pemantauan Penggunaan
Section titled “5. Pemantauan Penggunaan”Dashboard menampilkan permintaan berdasarkan kunci secara terpisah. Jika tiba-tiba satu kunci mulai membuat 10× lebih banyak permintaan dari biasanya - ini adalah sinyal untuk memeriksa.
Kamu bisa mengatur peringatan: Settings → Notifications → Alert when daily credits > X.
Kesalahan Autentikasi
Section titled “Kesalahan Autentikasi”| Kode | Arti |
|---|---|
401 Unauthorized | Header X-Api-Key tidak ada atau kunci tidak valid |
403 Forbidden | Kunci valid, tetapi tidak memiliki cakupan untuk tindakan ini (misalnya, kunci biasa mencoba mengelola kunci lain) |
403 PUBLISHABLE_KEY_UNBOUNDED | Kunci pk_ tanpa anggaran credits_cap_cycle atau tanpa cakupan allowed_endpoints: tentukan keduanya di pengaturan kunci |
402 Payment Required | Kredit habis (pada Free) atau langganan tidak aktif |
429 Too Many Requests | Batas rate terlampaui (10/60/300 req/min tergantung pada paket) |
Contoh 401:
{ "error": { "code": "invalid_api_key", "message": "The API key provided is invalid or has been revoked.", "request_id": "8aec43e9bc749b37e998a489bbad1757" }}Mode Sandbox
Section titled “Mode Sandbox”Kunci dengan prefiks aw_test_ berfungsi di sandbox:
- Tidak memotong kredit
- Mengembalikan respons stub atau respons nyata minimal
- Tidak memengaruhi statistik produksi
- Endpoint yang tersedia: sama
Berguna untuk CI/CD, tes e2e, dan pengembangan lokal. Dibuat melalui dashboard dengan satu klik.
Selanjutnya
Section titled “Selanjutnya”- Kredit dan Batasan: cara kerja penagihan dan rate limiting
- Kesalahan: daftar lengkap kode kesalahan