Pengenalan
API ini memungkinkan aplikasi lain (skrip otomatis, CMS pihak ketiga, automation tool, atau layanan AI) membuat artikel dan mengunggah gambar ke Portal News tanpa membuka panel CMS. Semua permintaan dan respons memakai JSON.
Base URL
https://haitangerang.com/api/v1Mulai cepat
- Minta administrator membuka CMS → User → Edit pada akun Anda, lalu di kartu API Key klik Buat API Key. Salin key-nya, karena hanya tampil sekali.
- Simpan key sebagai variabel lingkungan, misalnya
API_KEY. Jangan menaruhnya di kode front-end atau repositori publik. - Cek key dengan memanggil
GET /me, lalu kirim artikel pertama denganPOST /articles.
curl "https://haitangerang.com/api/v1/me" \
-H "Authorization: Bearer $API_KEY"Autentikasi
Kirim API key pada setiap permintaan lewat header Authorization dengan skema Bearer. Header X-API-Key: <key> juga diterima sebagai alternatif.
Authorization: Bearer pn_live_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx- Key diawali
pn_live_dan terikat pada satu user. Artikel yang dibuat tercatat atas nama user tersebut. - Key memiliki izin yang sama dengan pemiliknya. Contoh: user dengan level Author hanya bisa membuat draft, sedangkan Editor boleh langsung mempublikasikan.
- Key bisa dicabut kapan saja dari halaman edit user. Key juga berhenti berfungsi jika akun pemiliknya dinonaktifkan.
- Di server kami hanya tersimpan hash dari key. Jika key hilang, buat yang baru.
Format & rate limit
- Kirim body JSON dengan header
Content-Type: application/json(kecuali unggah gambar yang memakaimultipart/form-data). - Semua respons berbentuk
{ "success": true | false, ... }. - Waktu memakai ISO 8601 (UTC pada respons). Untuk
scheduled_atsertakan zona waktu, mis.+07:00. - Batas 60 permintaan per menit per API key. Sisa kuota ada di header
X-RateLimit-LimitdanX-RateLimit-Remaining. Jika terlampaui Anda menerima429beserta headerRetry-After(detik).
Kode error
Saat gagal, respons berformat:
{
"success": false,
"message": "Validasi gagal.",
"errors": { "title": "title wajib diisi." }
}| 400 | Body bukan JSON/multipart yang valid. |
| 401 | API key tidak ada, tidak valid, atau sudah dicabut. |
| 403 | Akun pemilik tidak aktif, atau tidak punya izin untuk aksi tersebut (mis. mempublikasikan). |
| 422 | Data tidak lolos validasi. Rinciannya ada di objek errors per field. |
| 429 | Rate limit terlampaui. Tunggu sesuai header Retry-After. |
| 500 | Kesalahan di server. Coba lagi nanti. |
GET /me
/api/v1/meIzin: (key valid)Menampilkan pemilik key dan daftar izinnya. Berguna untuk memverifikasi bahwa key bekerja.
curl "https://haitangerang.com/api/v1/me" \
-H "Authorization: Bearer $API_KEY"{
"success": true,
"data": {
"id": 3,
"name": "Redaksi Bot",
"username": "bot",
"email": "bot@example.com",
"access_level": "Editor",
"permissions": ["articles.view", "articles.create", "articles.publish", "media.upload"]
}
}GET /categories
/api/v1/categoriesIzin: articles.createDaftar kategori aktif. Gunakan id atau slug-nya pada POST /articles.
curl "https://haitangerang.com/api/v1/categories" \
-H "Authorization: Bearer $API_KEY"{
"success": true,
"data": [
{ "id": 1, "name": "Berita", "slug": "berita" },
{ "id": 2, "name": "Ekonomi", "slug": "ekonomi" }
]
}POST /media
/api/v1/mediaIzin: media.uploadMengunggah satu gambar ke Media Library. Hasilnya (url) dipakai sebagai featured_image atau og_image. Format: JPG, PNG, WEBP, SVG; maksimal 5 MB. Gambar raster dikonversi ke WEBP dan ukurannya dibatasi 2400 px.
| Parameter | Tipe | Keterangan |
|---|---|---|
fileWAJIB | file (multipart) | Berkas gambar yang akan diunggah. |
curl -X POST "https://haitangerang.com/api/v1/media" \
-H "Authorization: Bearer $API_KEY" \
-F "file=@./cover.jpg"{
"success": true,
"message": "Gambar berhasil diupload",
"data": {
"id": 12,
"url": "/uploads/2026/10/a1b2c3-taman-kota.webp",
"absolute_url": "https://haitangerang.com/uploads/2026/10/a1b2c3-taman-kota.webp",
"mime_type": "image/webp",
"size": 184320,
"width": 1600,
"height": 900
}
}POST /articles
/api/v1/articlesIzin: articles.createMembuat artikel baru atas nama pemilik key. Konten disanitasi di server (lihat Konten HTML), slug dibuat otomatis dari judul dan dijamin unik.
Body
| Parameter | Tipe | Keterangan |
|---|---|---|
titleWAJIB | string | Judul artikel, maks. 255 karakter. |
content | string (HTML) | Isi artikel. Wajib terisi bila status bukan draft. |
excerpt | string | Ringkasan, maks. 1000 karakter. Jika kosong diambil dari 200 karakter pertama konten. |
slug | string | Slug kustom. Jika kosong dibuat dari judul; bila sudah dipakai ditambah akhiran -2, -3, dst. |
status | draft | published | scheduled | Default draft. published dan scheduled memerlukan izin articles.publish pada pemilik key. |
scheduled_at | string (ISO 8601) | Wajib bila status = scheduled. Harus di masa depan, mis. 2026-11-01T08:00:00+07:00. Artikel terbit otomatis pada waktu itu. |
category_id | integer | ID kategori (lihat GET /categories). |
category | string | Slug kategori. Alternatif dari category_id. |
tags | string[] | Nama tag, maks. 10. Tag yang sudah ada dipakai ulang (tanpa membedakan huruf besar/kecil); tag baru dibuat jika pemilik key punya izin tags.create. |
tag_ids | integer[] | ID tag yang sudah ada, maks. 20. |
featured_image | string | URL gambar utama: /uploads/... dari POST /media atau URL http(s). |
is_featured | boolean | Tampilkan di slider utama halaman depan. Default false. |
meta_title | string | SEO title, maks. 200 karakter. |
meta_description | string | SEO description, maks. 500 karakter. |
meta_keywords | string | Kata kunci dipisah koma. |
canonical_url | string | URL kanonis (http/https). |
og_title / og_description / og_image | string | Override Open Graph untuk artikel ini. |
curl -X POST "https://haitangerang.com/api/v1/articles" \
-H "Authorization: Bearer $API_KEY" \
-H "Content-Type: application/json" \
-d '{
"title": "Pemkot Resmikan Taman Kota Baru",
"content": "<p>Taman seluas dua hektare itu resmi dibuka...</p><h2>Fasilitas</h2><p>Jogging track, area bermain...</p>",
"excerpt": "Taman seluas dua hektare resmi dibuka untuk umum.",
"status": "published",
"category": "berita",
"tags": ["Taman Kota", "Pemkot"],
"featured_image": "/uploads/2026/10/a1b2c3-taman-kota.webp",
"meta_title": "Taman Kota Baru Resmi Dibuka",
"meta_description": "Pemkot meresmikan taman kota baru seluas dua hektare."
}'{
"success": true,
"message": "Artikel berhasil dibuat",
"data": {
"id": 42,
"title": "Pemkot Resmikan Taman Kota Baru",
"slug": "pemkot-resmikan-taman-kota-baru",
"status": "published",
"url": "https://haitangerang.com/news/pemkot-resmikan-taman-kota-baru",
"admin_url": "https://haitangerang.com/marimo/articles?edit=42",
"published_at": "2026-10-29T13:45:10.000Z",
"scheduled_at": null,
"created_at": "2026-10-29T13:45:10.000Z"
}
}url bernilai null untuk draft karena artikel belum tampil publik. Header Location berisi alamat artikel.
{
"success": false,
"message": "Validasi gagal.",
"errors": {
"title": "title wajib diisi.",
"scheduled_at": "scheduled_at harus ISO 8601 dengan zona waktu, mis. 2026-11-01T08:00:00+07:00."
}
}Konten HTML
Field content berisi HTML. Demi keamanan, server membersihkan konten sebelum disimpan: tag, atribut, dan skema URL di luar daftar berikut dibuang (termasuk <script>, atribut on*, dan tautan javascript:).
- Tag:
h2 h3 h4 p br hr strong b em i u s a ul ol li blockquote pre code img figure figcaption div span, sertaiframehanya untuk YouTube dan Vimeo. - Atribut:
href(+target,rel) pada link,src alt width heightpada gambar, dantext-alignpada gaya. - Skema URL:
http,https,mailto,tel. Link eksternal otomatis dibuka di tab baru denganrel="noopener noreferrer". - Gunakan
<h2>dan seterusnya untuk subjudul. Judul utama (h1) berasal dari fieldtitle.
Changelog
- v1: rilis awal dengan
/me,/categories,/tags,/media, dan/articles(POST).
