3.2
Endpoint Juz
GET /juz/{juz} mengembalikan seluruh ayah yang berada di dalam satu juz. Ini satu-satunya endpoint yang merakit payload saat request berjalan: JuzHandler.getJuz hanya mengambil req.params.juz, memanggil juzData, lalu membungkus hasilnya menjadi response. Tidak ada potongan daftar ayah per juz yang siap dikirim dari berkas mana pun. api/handlers/juz.js:4-151 api/lib/juz.js:4-72
Registrasi route
Route ini didaftarkan bersama endpoint surah, sehingga semua perilaku router berlaku sama untuknya. api/routes.js:34-383
| Aspek | Nilai | Rujukan |
|---|---|---|
| Method dan path | GET /juz/:juz | api/routes.js:384 |
| Middleware | caching dari api/middlewares.js | api/routes.js:384 |
| Handler | JuzHandler.getJuz | api/handlers/juz.js:4-235 |
| Header response | Cache-Control: public, max-age=0, s-maxage=86400, stale-while-revalidate | api/routes.js:9-126 |
Entri katalog GET / | spesificJuz.pattern = /juz/{juz}, contoh /juz/30 | api/routes.js:25-287 |
| Path lain di luar route | fallback router.all('*') dengan pesan Resource "..." is not found. | api/routes.js:41-458 |
Siklus hidup satu request
Urutan pemanggilan menentukan mengapa endpoint ini lebih mahal daripada /surah/{surah}. Middleware caching menyimpan body per req.url, jadi request kedua untuk juz yang sama tidak menyentuh juzData lagi. api/middlewares.js:3-179
sequenceDiagram
autonumber
participant C as Client
participant R as router
participant K as caching
participant H as JuzHandler.getJuz
participant L as juzData
participant J as data/juz.json
participant Q as data/quran.json
C->>R: GET /juz/2
R->>R: setHeader Cache-Control
R->>K: caching(req, res, next)
alt cache[req.url] terisi
K-->>C: 200 body dari cache
else cache kosong
K->>H: next() menuju handler
H->>L: juzData(parseInt("2"))
L->>J: juz[_inputJuz - 1]
alt inputJuz tidak ada
L-->>H: null
H-->>C: 404 Juz "2" is not found.
else inputJuz ada
L->>Q: verses.slice pada rentang juz
L-->>H: objek data berisi verses
H-->>C: 200 Success fetching juz.
end
Note over K: res.send di-wrap, body masuk cache[req.url]
end
%% fig: Siklus hidup request GET /juz/{juz}
%% desc: Router meneruskan request ke middleware caching, lalu handler memanggil juzData yang membaca juz.json dan mengiris verses dari quran.json sebelum response dibungkus.Perhatikan bahwa juzData menerima hasil parseInt, bukan string mentah, dan mencari entri lewat posisi array juz[_inputJuz - 1] alih-alih mencocokkan field index. api/lib/juz.js:510 Untuk juz 30, entri terakhir di data/juz.json adalah index: 30 dengan rentang surah 78 ayat 1 sampai surah 114 ayat 6, sehingga totalnya 30 entri tanpa celah indeks. data/juz.json:5-1511 data/juz.json:324-33412
Bentuk data yang dikirim
Objek data pada response 200 selalu memuat tujuh field dengan sumber yang tetap. api/handlers/juz.js:17-2213
| Field | Nilai |
|---|---|
juz | _inputJuz hasil parseInt dari req.params.juz |
juzStartSurahNumber | inputJuz.start.index |
juzEndSurahNumber | inputJuz.end.index |
juzStartInfo | ${startSurahName} - ${inputJuz.start.verse} |
juzEndInfo | ${endSurahName} - ${inputJuz.end.verse} |
totalVerses | juzAyah.length |
verses | array ayah hasil slice |
Kedua nama surah pada juzStartInfo dan juzEndInfo diambil dari name.transliteration.id, misalnya Al-Fatihah, bukan dari name.long. api/lib/juz.js:35-4514
graph LR
J["data/juz.json"] --> E["juz[_inputJuz - 1]"]
Q["data/quran.json"] --> V["juzAyah dari verses.slice"]
E --> S["juzStartSurahNumber / juzEndSurahNumber"]
E --> I["juzStartInfo / juzEndInfo"]
V --> T["totalVerses"]
V --> VS["verses"]
S --> D["objek data"]
I --> D
T --> D
VS --> D
D --> OK["200 Success fetching juz."]
style J fill:#336791,color:#fff
style Q fill:#336791,color:#fff
style V fill:#8b5cf6,color:#fff
style D fill:#8b5cf6,color:#fff
style OK fill:#2d7d46,color:#fff
%% fig: Asal setiap field pada payload juz
%% desc: Metadata rentang berasal dari juz.json, daftar ayah berasal dari irisan quran.json, lalu semuanya dirakit menjadi satu objek data.Setiap elemen verses adalah objek ayah apa adanya dari data/quran.json, lengkap dengan number, meta, text, translation, audio, dan tafsir. data/quran.json:32-6415 Karena juzData hanya mengiris array verses milik surah, ayah pada response ini tidak membawa objek surah di dalamnya. Bandingkan dengan /surah/{surah}/{ayah} pada Endpoint Surah dan Ayah, yang menyisipkan salinan data surah ke setiap ayah. Rincian percabangan irisan rentang dijelaskan di Komputasi Rentang Juz. api/lib/juz.js:16-3316
Input tidak valid dan response 404
Handler menganggap juz tidak ditemukan ketika juzData mengembalikan nilai falsy, lalu mengirim body { code: 404, status: 'Not Found.', message: 'Juz "<juz>" is not found.', data: {} }. api/handlers/juz.js:8-1517
| Request | parseInt | juz[_inputJuz - 1] | Hasil |
|---|---|---|---|
/juz/2 | 2 | entri index: 2 | 200 |
/juz/30 | 30 | entri index: 30 | 200 |
/juz/0 | 0 | juz[-1] bernilai undefined | 404 |
/juz/31 | 31 | undefined | 404 |
/juz/abc | NaN | undefined | 404 |
/juz/2abc | 2 | entri index: 2 | 200 |
Pesan error memakai string mentah dari req.params.juz, bukan angka hasil parseInt. Karena itu GET /juz/abc mengembalikan Juz "abc" is not found. api/handlers/juz.js:1218
⚠️ Response 404 juga ikut tersimpan di
cache. Middlewarecachingmembungkusres.sendsebelum handler berjalan, sehingga body apa pun yang lewatres.sendditulis kecache[req.url], termasuk body error. Selama proses masih hidup, request berikutnya untuk path yang sama menerima 404 yang sama dari cache tanpa menjalankan ulangjuzData. api/middlewares.js:10-1419
Siklus cache itu sendiri dibahas di Alur Request dan Middleware caching.