# Requirements Document

## Introduction

Fitur ini membangun API endpoint di sisi DOJ (localhost:8001) yang menerima data penjara dari USMS (localhost:8003). Ketika officer USMS menginput data tahanan di halaman /prison, sistem USMS akan mengirim data tersebut ke DOJ untuk dicatat sebagai Criminal Case. API ini menggunakan pola yang sudah ada di DOJ (JSON response dengan format `{success, message, data}`) dan autentikasi via API Key (header `X-API-Key`).

Alur data: USMS /prison → HTTP POST → DOJ /api/criminal-cases (store)

## Glossary

- **DOJ_API**: API endpoint yang disediakan oleh aplikasi DOJ (Department of Justice) di localhost:8001 untuk menerima data dari sistem eksternal
- **USMS_Client**: Service di aplikasi USMS (localhost:8003) yang mengirim HTTP request ke DOJ_API
- **Prison_Record**: Data laporan penjara di USMS yang berisi informasi CID, tanggal, briefing, dan daftar tahanan
- **UserPrison**: Data individual tahanan dalam sebuah Prison_Record, berisi suspect, tipe tahanan, penal code, dan bail
- **Criminal_Case**: Record di tabel `criminal_cases` DOJ yang menyimpan data kasus pidana termasuk accused_name, cid_no, bail_amount, dan status
- **API_Key**: Token autentikasi yang dikirim via header `X-API-Key` untuk mengamankan akses ke DOJ_API
- **Penal_Code**: Array JSON berisi daftar pasal/charge yang dikenakan kepada tahanan, disimpan di field `penal_code` pada UserPrison

## Requirements

### Requirement 1: DOJ Menyediakan API Endpoint untuk Menerima Data Criminal Case dari USMS

**User Story:** Sebagai sistem USMS, saya ingin mengirim data tahanan ke DOJ melalui API, sehingga data kasus pidana tercatat otomatis di sistem DOJ tanpa input manual.

#### Acceptance Criteria

1. WHEN USMS_Client mengirim POST request ke `/api/criminal-cases` dengan header `X-API-Key` yang valid, THE DOJ_API SHALL memvalidasi request body dan menyimpan data sebagai Criminal_Case baru
2. WHEN Criminal_Case baru berhasil disimpan, THE DOJ_API SHALL menghasilkan `application_no` otomatis dengan format `CT-CR-{YEAR}-{XXXX}` di mana `{YEAR}` adalah tahun saat ini (4 digit) dan `{XXXX}` adalah nomor urut 4 digit dimulai dari 0001, di-increment berdasarkan record terakhir pada tahun tersebut
3. WHEN request berhasil diproses dan Criminal_Case tersimpan, THE DOJ_API SHALL mengembalikan response JSON dengan format `{"success": true, "message": "...", "data": {...}}` dan HTTP status 201, di mana `data` berisi seluruh field Criminal_Case yang baru dibuat termasuk `application_no` yang di-generate
4. IF request gagal validasi (field required kosong, format tidak sesuai, atau nilai enum tidak valid), THEN THE DOJ_API SHALL mengembalikan response JSON dengan format `{"success": false, "message": "...", "errors": {...}}` dan HTTP status 422, di mana `errors` berisi key-value pair per field yang gagal validasi
5. IF request tidak menyertakan API Key atau API Key tidak valid, THEN THE DOJ_API SHALL mengembalikan response JSON dengan format `{"success": false, "message": "..."}` dan HTTP status 401 tanpa menyimpan data apapun
6. THE DOJ_API SHALL menerima dan memvalidasi field berikut dalam request body: `cid_no` (required, string, maksimal 100 karakter), `accused_name` (required, string, maksimal 255 karakter), `accused_plea` (required, string, maksimal 100 karakter), `bail_amount` (nullable, numeric, minimum 0), `bail_status` (required, enum: paid/not paid/refund), `decision` (nullable, string, maksimal 1000 karakter), `status` (required, enum: active/closed/arraignment/trial/sentence/search warrant/arrest warrant/withdrawn), `judge_name` (nullable, string, maksimal 255 karakter), `prosecutor_name` (nullable, string, maksimal 255 karakter), `public_defender_name` (nullable, string, maksimal 255 karakter), `date_of_hearing` (nullable, format YYYY-MM-DD)

### Requirement 2: DOJ API Mengamankan Endpoint dengan API Key Authentication

**User Story:** Sebagai administrator DOJ, saya ingin endpoint API diamankan dengan API Key, sehingga hanya sistem yang terotorisasi yang dapat mengirim data.

#### Acceptance Criteria

1. WHEN request ke `/api/criminal-cases` tidak menyertakan header `X-API-Key` dan tidak menyertakan query parameter `api_key`, THE DOJ_API SHALL mengembalikan response JSON dengan field `success` bernilai `false` dan field `message` berisi pesan yang mengindikasikan unauthorized, dengan HTTP status 401
2. WHEN request menyertakan `X-API-Key` yang tidak cocok dengan API key yang dikonfigurasi di server, THE DOJ_API SHALL mengembalikan response JSON dengan field `success` bernilai `false` dan field `message` berisi pesan yang mengindikasikan unauthorized, dengan HTTP status 401
3. WHEN request menyertakan `X-API-Key` yang cocok dengan API key yang dikonfigurasi di server, THE DOJ_API SHALL meneruskan request ke handler endpoint yang dituju dan mengembalikan response sesuai dengan logika endpoint tersebut
4. THE DOJ_API SHALL menerima API Key melalui header `X-API-Key` atau query parameter `api_key`, dengan prioritas header `X-API-Key` digunakan terlebih dahulu apabila keduanya disertakan
5. IF API key belum dikonfigurasi di server (nilai kosong atau tidak ada), THEN THE DOJ_API SHALL menolak semua request ke endpoint yang dilindungi dengan mengembalikan HTTP status 401
6. THE DOJ_API SHALL melakukan perbandingan API key menggunakan metode timing-safe comparison untuk mencegah timing attack

### Requirement 3: USMS Mengirim Data Prison ke DOJ Saat Tahanan Ditambahkan

**User Story:** Sebagai officer USMS, saya ingin data tahanan yang saya input otomatis terkirim ke DOJ, sehingga saya tidak perlu input ulang di sistem DOJ.

#### Acceptance Criteria

1. WHEN officer menambahkan tahanan baru ke Prison_Record melalui fungsi addPrisoner, THE USMS_Client SHALL mengirim HTTP POST request berisi data tahanan ke DOJ_API endpoint `/api/criminal-cases` dalam waktu maksimal 10 detik setelah data lokal berhasil disimpan
2. THE USMS_Client SHALL memetakan data UserPrison ke format Criminal_Case DOJ dengan mapping berikut: `suspect.nama` → `accused_name`, `prison.cid` → `cid_no`, `bail_out` → `bail_amount`, `penal_code` array → `decision` (gabungan field `name` dari setiap elemen penal_code, dipisahkan koma)
3. THE USMS_Client SHALL mengisi field `bail_status` berdasarkan nilai `bail_out`: jika `bail_out` > 0 maka `paid`, jika null atau 0 maka `not paid`
4. THE USMS_Client SHALL mengisi field `accused_plea` dengan nilai default `not guilty` saat mengirim data
5. THE USMS_Client SHALL mengisi field `status` dengan nilai `active` saat mengirim data baru
6. THE USMS_Client SHALL mengisi field `judge_name` dan `prosecutor_name` dengan string kosong ("") saat mengirim data baru, karena informasi tersebut belum tersedia pada tahap input tahanan
7. IF DOJ_API mengembalikan HTTP status code 4xx atau 5xx, THEN THE USMS_Client SHALL tetap menyimpan data tahanan secara lokal dan mencatat error response ke log termasuk HTTP status code dan timestamp
8. IF DOJ_API tidak dapat dihubungi dalam waktu 10 detik (connection timeout), THEN THE USMS_Client SHALL tetap menyimpan data tahanan secara lokal dan mencatat timeout error ke log termasuk timestamp
9. IF field `suspect.nama` bernilai null atau kosong, THEN THE USMS_Client SHALL tidak mengirim data ke DOJ_API dan mencatat validasi error ke log

### Requirement 4: DOJ Menyediakan API Endpoint untuk Mengambil Daftar Criminal Cases

**User Story:** Sebagai sistem USMS, saya ingin dapat mengambil daftar criminal cases dari DOJ, sehingga saya dapat menampilkan status kasus yang sudah dikirim.

#### Acceptance Criteria

1. WHEN USMS_Client mengirim GET request ke `/api/criminal-cases`, THE DOJ_API SHALL mengembalikan daftar Criminal_Case dalam format JSON dengan hasil diurutkan berdasarkan data terbaru (created_at descending)
2. WHEN filter `cid_no` disertakan sebagai query parameter, THE DOJ_API SHALL mengembalikan hanya Criminal_Case yang field `cid_no`-nya mengandung nilai filter tersebut (partial match, case-insensitive)
3. WHEN filter `accused_name` disertakan sebagai query parameter, THE DOJ_API SHALL mengembalikan hanya Criminal_Case yang field `accused_name`-nya mengandung nilai filter tersebut (partial match, case-insensitive)
4. WHEN filter `status` disertakan sebagai query parameter, THE DOJ_API SHALL mengembalikan hanya Criminal_Case yang field `status`-nya sama persis dengan nilai filter tersebut, dengan nilai valid: `active`, `closed`, `arraignment`, `trial`, `sentence`, `search warrant`, `arrest warrant`, `withdrawn`
5. THE DOJ_API SHALL mengembalikan response dengan format `{"success": true, "message": "...", "data": [...]}` dimana array `data` berisi objek Criminal_Case dengan field: `id`, `application_no`, `cid_no`, `accused_name`, `judge_name`, `prosecutor_name`, `public_defender_name`, `date_of_hearing`, `accused_plea`, `bail_amount`, `bail_status`, `decision`, `status`, `created_at`, `updated_at`
6. IF tidak ada Criminal_Case yang cocok dengan filter yang diberikan, THEN THE DOJ_API SHALL mengembalikan response dengan format `{"success": true, "message": "...", "data": []}` dengan HTTP status 200 dan array `data` kosong
7. IF nilai query parameter `status` tidak termasuk dalam daftar nilai valid, THEN THE DOJ_API SHALL mengabaikan filter tersebut dan mengembalikan semua Criminal_Case tanpa filter status

### Requirement 5: USMS Menggunakan Service Class untuk Komunikasi dengan DOJ API

**User Story:** Sebagai developer, saya ingin komunikasi ke DOJ API dienkapsulasi dalam service class, sehingga kode mudah di-maintain dan di-test.

#### Acceptance Criteria

1. THE USMS_Client SHALL menggunakan service class `DojCriminalCaseService` untuk semua komunikasi ke DOJ_API endpoint criminal-cases, dengan minimal public method `store(array $data)` untuk membuat Criminal_Case dan `index(array $filters)` untuk mengambil daftar Criminal_Case
2. THE USMS_Client SHALL membaca base URL DOJ dari environment variable `DOJ_API_URL` dan IF environment variable `DOJ_API_URL` tidak tersedia atau bernilai kosong, THEN THE USMS_Client SHALL melempar exception saat service di-instantiate
3. THE USMS_Client SHALL membaca API Key dari environment variable `DOJ_API_KEY` dan IF environment variable `DOJ_API_KEY` tidak tersedia atau bernilai kosong, THEN THE USMS_Client SHALL melempar exception saat service di-instantiate
4. THE USMS_Client SHALL mengatur timeout HTTP request maksimal 10 detik, dan IF request melebihi batas waktu 10 detik, THEN THE USMS_Client SHALL melempar exception yang berisi informasi bahwa request timeout
5. IF response dari DOJ_API memiliki HTTP status selain 2xx, THEN THE USMS_Client SHALL melempar exception yang berisi HTTP status code dan response body dari DOJ_API sehingga caller dapat menentukan penanganan error yang sesuai
6. THE USMS_Client SHALL menyertakan header `Content-Type: application/json` dan `X-API-Key` dengan nilai dari environment variable `DOJ_API_KEY` pada setiap request ke DOJ_API

### Requirement 6: DOJ Menyediakan API Endpoint untuk Mengambil Detail Single Criminal Case

**User Story:** Sebagai sistem USMS, saya ingin dapat mengambil detail satu criminal case berdasarkan ID atau CID, sehingga saya dapat menampilkan informasi lengkap kasus.

#### Acceptance Criteria

1. WHEN USMS_Client mengirim GET request ke `/api/criminal-cases/{id}` dengan parameter `id` berupa numeric ID, THE DOJ_API SHALL mengembalikan response dengan format `{"success": true, "message": "success", "data": {...}}` berisi detail Criminal_Case yang sesuai
2. WHEN USMS_Client mengirim GET request ke `/api/criminal-cases/{id}` dengan parameter `id` berupa `cid_no`, THE DOJ_API SHALL mengembalikan response dengan format `{"success": true, "message": "success", "data": {...}}` berisi detail Criminal_Case yang memiliki `cid_no` tersebut
3. IF Criminal_Case dengan ID atau `cid_no` yang diminta tidak ditemukan, THEN THE DOJ_API SHALL mengembalikan response `{"success": false, "message": "Data tidak ditemukan.", "data": null}` dengan HTTP status 404
4. WHEN Criminal_Case berhasil ditemukan, THE DOJ_API SHALL menyertakan field berikut dalam objek `data`: `id`, `application_no`, `cid_no`, `accused_name`, `judge_name`, `prosecutor_name`, `public_defender_name`, `date_of_hearing`, `accused_plea`, `bail_amount`, `bail_status`, `decision`, `status`, `created_at`, dan `updated_at`
5. IF request tidak menyertakan header autentikasi yang valid, THEN THE DOJ_API SHALL mengembalikan response `{"success": false, "message": "Unauthorized"}` dengan HTTP status 401
