REST API
Baca formulir dan kiriman, pindahkan kiriman ke dan dari spam, dan hapus dengan secret key.
REST API memungkinkan server Anda membaca formulir dan kiriman, memindahkan kiriman ke dan dari spam, serta menghapusnya. API ini berupa JSON lewat HTTPS di https://ikiform.com/api/v1. Dokumen OpenAPI 3.1 ada di /api/v1/openapi.json.
/api/v1. Kirim ke endpoint formulir dengan secret key; lihat Dari server.Kunci API
Buat key di dashboard pada API keys. Satu key milik satu workspace dan hanya bisa melihat workspace itu. Key lengkap hanya ditampilkan sekali; Ikiform hanya menyimpan hash-nya.
| Jenis | Awalan | Gunakan |
|---|---|---|
| Secret | ik_sk_ | Untuk server. Memanggil REST API dengan scope yang Anda pilih, dan bisa membuat kiriman. |
| Publishable | ik_pub_ | Untuk browser. Hanya bisa mengirim formulir, dan hanya dari domain yang Anda cantumkan di key. |
Scope
| Scope | Memberi akses |
|---|---|
forms:read | GET /forms, GET /forms/:formId |
submissions:read | GET /submissions, GET /submissions/:id |
submissions:write | DELETE /submissions/:id, POST /submissions/:id/spam dan /not-spam, serta mengirim ke /f/:formId |
Autentikasi
Kirim secret key sebagai Bearer token. API ini hanya untuk server ke server: tidak mengirim header CORS dan menjawab preflight browser dengan 405, jadi secret key tidak pernah bisa dipakai dari halaman web.
curl https://ikiform.com/api/v1/forms \
-H "Authorization: Bearer $IKIFORM_SECRET_KEY"- Key yang tidak ada, salah format, tidak dikenal, dicabut, atau kedaluwarsa mendapat
401 unauthorizeddenganWWW-Authenticate: Bearer. - Publishable key mendapat
403 forbidden(Publishable keys can only submit forms.). Key tanpa scope yang dibutuhkan mendapat403 forbiddendengan nama scope disebut di pesannya. - Respons dikirim dengan
Cache-Control: no-store.
Contoh SDK di bawah memakai satu client yang sama:
import { createClient } from "@ikiform/sdk";
const ikiform = createClient({ apiKey: process.env.IKIFORM_SECRET_KEY! });Penyusun request
curl "https://ikiform.com/api/v1/submissions?form_id=frm_xxxxxxxxxxxxxxxx&status=received&limit=50" \
-H "Authorization: Bearer $IKIFORM_SECRET_KEY"Jalankan ini dari server Anda. REST API menolak request dari browser, jadi halaman ini tidak pernah mengirimnya.
Endpoint
| Metode | Path | Scope | Mengembalikan |
|---|---|---|---|
GET | /forms | forms:read | Daftar formulir |
GET | /forms/:formId | forms:read | Ambil satu formulir |
GET | /submissions | submissions:read | Daftar kiriman |
GET | /submissions/:id | submissions:read | Ambil satu kiriman |
POST | /submissions/:id/spam | submissions:write | Tandai sebagai spam |
POST | /submissions/:id/not-spam | submissions:write | Tandai sebagai bukan spam |
DELETE | /submissions/:id | submissions:write | Hapus kiriman |
GET | /openapi.json | Tidak ada | Dokumen OpenAPI |
GET | /health | Tidak ada | { "ok": true } |
Daftar formulir
GET /forms dengan scope forms:read.
- Terbaru lebih dulu. Menerima
limit(1 sampai 100, default 25) dancursor.
curl "https://ikiform.com/api/v1/forms?limit=10" \
-H "Authorization: Bearer $IKIFORM_SECRET_KEY"Ambil satu formulir
GET /forms/:formId dengan scope forms:read.
- ID formulir dari workspace lain mengembalikan
404, persis seperti ID yang tidak ada.
curl https://ikiform.com/api/v1/forms/frm_xxxxxxxxxxxxxxxx \
-H "Authorization: Bearer $IKIFORM_SECRET_KEY"Daftar kiriman
GET /submissions dengan scope submissions:read.
| Parameter | Nilai | Default |
|---|---|---|
form_id | ID formulir | Semua formulir di workspace |
status | received atau spam | Keduanya |
limit | 1 sampai 100 | 25 |
cursor | next_cursor dari halaman sebelumnya | Halaman pertama |
- Terbaru lebih dulu.
form_iddari workspace lain mengembalikan daftar kosong alih-alih error, jadi ID tidak bisa ditebak-tebak.
curl "https://ikiform.com/api/v1/submissions?form_id=frm_xxxxxxxxxxxxxxxx&status=received&limit=50" \
-H "Authorization: Bearer $IKIFORM_SECRET_KEY"Ambil satu kiriman
GET /submissions/:id dengan scope submissions:read.
- ID dari workspace lain mengembalikan
404, persis seperti ID yang tidak ada.
curl https://ikiform.com/api/v1/submissions/sub_01k7v2c9t3e8m5q4x6z0a1b2c3 \
-H "Authorization: Bearer $IKIFORM_SECRET_KEY"Tandai sebagai spam
POST /submissions/:id/spam dengan scope submissions:write.
- Memindahkan kiriman yang diterima ke spam, mengurangi
submission_countformulir, dan membatalkan pengiriman webhook-nya yang tertunda. - Memanggilnya pada kiriman yang sudah spam mengembalikannya tanpa perubahan.
curl -X POST https://ikiform.com/api/v1/submissions/sub_01k7v2c9t3e8m5q4x6z0a1b2c3/spam \
-H "Authorization: Bearer $IKIFORM_SECRET_KEY"Tandai sebagai bukan spam
POST /submissions/:id/not-spam dengan scope submissions:write.
- Memindahkannya kembali ke diterima, menghapus skor dan alasan spam-nya, dan mengirim
submission.createdke setiap endpoint webhook yang cocok. - Memanggilnya pada kiriman yang diterima mengembalikannya tanpa perubahan.
curl -X POST https://ikiform.com/api/v1/submissions/sub_01k7v2c9t3e8m5q4x6z0a1b2c3/not-spam \
-H "Authorization: Bearer $IKIFORM_SECRET_KEY"Hapus kiriman
DELETE /submissions/:id dengan scope submissions:write.
- Menghapus kiriman dan pengiriman webhook-nya secara permanen. Tidak bisa dibatalkan. Menghapus lagi mengembalikan
404.
curl -X DELETE https://ikiform.com/api/v1/submissions/sub_01k7v2c9t3e8m5q4x6z0a1b2c3 \
-H "Authorization: Bearer $IKIFORM_SECRET_KEY"Objek
Objek berupa JSON snake_case dengan field object. Timestamp dalam ISO 8601 UTC dengan milidetik. ID kiriman berurutan menurut waktu (sub_ ditambah 26 karakter); ID formulir acak (frm_ ditambah 16 karakter).
| Field formulir | Deskripsi |
|---|---|
status | active, paused, atau disabled |
submission_count | Kiriman yang diterima, bukan spam |
| Field kiriman | Deskripsi |
|---|---|
status | received atau spam |
fields | Nilai yang disimpan |
meta | user_agent, origin, referrer, country, subject, reply_to. Setiap key selalu ada dan nilai apa pun bisa null. Hash IP tidak pernah dikembalikan |
spam.score, spam.reasons | Skor dan alasan spam, seperti honeypot atau origin_mismatch |
Paginasi
Daftar diurutkan dari yang terbaru dan memakai cursor opaque.
- Kirim request tanpa cursor.
- Jika
has_morebernilai true, kirimnext_cursorsebagaicursordengan filter yang sama. - Berhenti saat
next_cursorbernilainull.
Halaman tetap stabil saat kiriman baru masuk: kiriman baru muncul di halaman pertama, tidak pernah sebagai duplikat di halaman berikutnya. Jangan membuat atau mengurai cursor sendiri; cursor yang tidak valid mengembalikan 400 invalid_request.
for await (const submission of ikiform.submissions.iterate({ formId: "frm_xxxxxxxxxxxxxxxx" })) {
console.log(submission.id, submission.fields);
}Error
Error memakai envelope yang sama dengan kiriman formulir. Setiap respons punya header X-Request-Id, yang diulang oleh error sebagai request_id.
{
"ok": false,
"error": { "code": "forbidden", "message": "This API key is missing the forms:read scope." },
"request_id": "req_01k7v2c9t3e8m5q4x6z0a1b2c3"
}| Status | Kode | Kapan |
|---|---|---|
| 400 | invalid_request | limit, status, form_id, atau cursor tidak valid; pesannya menyebut yang mana |
| 401 | unauthorized | Key tidak ada atau tidak valid |
| 403 | forbidden | Publishable key, atau scope tidak ada |
| 404 | not_found | Route atau ID tidak dikenal, atau ID di workspace lain |
| 405 | method_not_allowed | Preflight browser |
| 429 | rate_limited | Melewati rate limit per key |
| 500 | server_error | Ada yang gagal di pihak kami; sertakan request_id |
Rate limit
Setiap key bisa membuat 100 request per 60 detik. Jika melewati batas, API mengembalikan 429 rate_limited dengan header Retry-After dalam detik. SDK mengeksposnya sebagai error.retryAfter.