# Flight Ops Locks and Helicopter Usage Sync Dokumen ini menjelaskan alur data untuk `takeover`, `mission`, `flight_data`, `after_flight_inspection`, `fm_report`, dan `helicopter_usage`. Tujuan utamanya: - mencegah perubahan data pada fase yang sudah final - menjaga `helicopter_usage` sebagai ringkasan yang dihitung dari data sumber - membuat perilaku backend konsisten untuk frontend dan integrasi lain ## Ringkasan Aturan 1. Saat `after_flight_inspection` sudah dibuat: - `mission` untuk flight itu tidak boleh dibuat atau di-update lagi - `flight_data` baru tidak boleh dibuat lagi - `flight_data` yang sudah ada masih boleh diedit 2. Saat `fm_report` di-complete: - `flight_data` untuk flight itu terkunci - `fm_report` menjadi read-only - `helicopter_usage` baru dihitung ulang dari data sumber 3. Saat `GET /api/v1/fm-reports/get/:flight_id`: - backend tetap mengirim `helicopter_usage` - jika row belum ada di database, response tetap mengirim nilai `0` ## Alur Besar Urutan normalnya: 1. `takeover` dibuat 2. `mission` dibuat 3. `flight_data` diisi dan masih bisa diubah 4. `after_flight_inspection` dibuat 5. `fm_report` draft otomatis tersedia 6. user melengkapi `fm_report` 7. `POST /api/v1/fm-reports/complete/:flight_id` 8. backend menghitung ulang `helicopter_usage` ## Detail Per Modul ### 1) Mission Mission bisa dibuat dan di-update selama flight belum masuk fase after flight inspection. Begitu `after_flight_inspection` sudah ada untuk flight tersebut: - create mission ditolak - update mission ditolak Alasan bisnis: - setelah after flight masuk, mission dianggap sudah masuk fase final - mission tidak boleh berubah karena akan mempengaruhi rekonsiliasi data flight Error yang biasanya muncul: - `MISSION_AFTER_FLIGHT_LOCKED` Referensi: - lihat tabel `Mission` di [`docs/error-catalog.md`](./error-catalog.md) ### 2) Flight Data `flight_data` adalah sumber utama untuk hitungan operasional seperti: - landing count - durasi flight - hook release - rotor brake cycle #### Sebelum after flight inspection - create flight data boleh - update flight data boleh - delete flight data boleh #### Setelah after flight inspection dibuat - create flight data baru ditolak - update flight data yang sudah ada masih boleh - delete flight data yang sudah ada ditolak #### Setelah FM report di-complete - update flight data ditolak - delete flight data ditolak - data dianggap final Error yang biasanya muncul: - `FLIGHT_DATA_CREATE_BLOCKED` - `FLIGHT_DATA_AFTER_FLIGHT_LOCKED` - `FLIGHT_DATA_LOCKED` Referensi: - lihat tabel `Flight Data` di [`docs/error-catalog.md`](./error-catalog.md) ### 3) After Flight Inspection `after_flight_inspection` dipakai sebagai penanda bahwa flight sudah masuk fase akhir sebelum FM report di-complete. Catatan penting: - create / upsert after flight inspection tidak lagi memicu kalkulasi `helicopter_usage` - after flight inspection hanya menyimpan hasil inspeksi - kalkulasi usage dipindahkan ke langkah `fm_report complete` ### 4) FM Report FM report dibuat sebagai draft setelah after flight inspection masuk ke flow. #### Sebelum complete - report masih bisa di-update - engine metric masih bisa diisi / diubah - `helicopter_usage` belum dihitung ulang oleh backend #### Setelah complete - report menjadi read-only - update FM report ditolak - `completed_at` dan `completed_by` disimpan - backend memicu refresh `helicopter_usage` Endpoint yang dipakai: - `POST /api/v1/fm-reports/complete/:flight_id` Error yang biasanya muncul: - `FM_REPORT_LOCKED` - `FM_REPORT_COMPLETE_FAILED` Referensi: - lihat tabel `FM Report` di [`docs/error-catalog.md`](./error-catalog.md) ### 5) Helicopter Usage `helicopter_usage` sekarang diperlakukan sebagai summary record. Karakteristiknya: - dihitung dari data sumber - bukan angka yang diisi manual untuk flow normal - tetap bisa di-maintain manual lewat CRUD admin/backfill kalau diperlukan #### Sumber data kalkulasi - `total_landing` = sum `flight_data.landing_count` - `total_airframe_hours` = sum durasi flight - `total_airframe_cycles` = count flight data - `total_hook_release` = sum `flight_data.hook_releases` - `total_rotor_brake_cycle` = sum `flight_data.rotor_brake_cycle` - `total_flight_report` = count report yang punya helicopter terkait - metric engine diambil dari field FM report dan dijumlahkan #### Kapan dihitung Kalkulasi ulang dilakukan saat: - `fm_report` di-complete Kalkulasi tidak dilakukan lagi saat: - create / update after flight inspection - create / update / delete flight data - draft FM report di-upsert ## Response `GET FM Report` Endpoint: - `GET /api/v1/fm-reports/get/:flight_id` Response akan selalu mengirim field `helicopter_usage`. Perilaku response: - jika row `helicopter_usage` ada di database, isi nilainya dari row tersebut - jika row belum ada, backend tetap mengirim object `helicopter_usage` dengan semua angka `0` Contoh bentuk response: ```json { "data": { "type": "fm_report", "id": "report-id", "attributes": { "flight_id": "flight-id", "completed_at": null, "helicopter_usage": { "type": "helicopter_usage", "id": "", "attributes": { "helicopter_id": "helicopter-id", "total_landing": 0, "total_airframe_hours": 0, "total_airframe_cycles": 0, "total_engine_1_hours": 0, "total_engine_1_gpc_ng_n1": 0, "total_engine_1_ptc_nf_n2": 0, "total_engine_1_ccc": 0, "total_engine_2_hours": 0, "total_engine_2_gpc_ng_n1": 0, "total_engine_2_ptc_nf_n2": 0, "total_engine_2_ccc": 0, "total_flight_report": 0, "total_hook_release": 0, "total_rotor_brake_cycle": 0 } } } } } ``` ## Status yang Perlu Diingat ### Masih editable - mission sebelum after flight inspection ada - flight data sebelum FM report di-complete - FM report sebelum complete ### Sudah locked - mission setelah after flight inspection ada - flight data setelah FM report di-complete - FM report setelah complete ## Dampak ke Frontend Frontend sebaiknya mengikuti aturan ini: 1. Jika after flight inspection sudah ada: - sembunyikan atau disable aksi create mission - sembunyikan atau disable aksi create flight data baru 2. Jika FM report sudah complete: - disable semua edit flight data - disable edit FM report 3. Saat menampilkan FM report: - selalu render section helicopter usage - jika angka semua `0`, itu berarti belum ada summary yang terhitung atau belum ada data sumber yang selesai ## Error yang Relevan Lihat katalog lengkap di: - [`docs/error-catalog.md`](./error-catalog.md) Error yang paling sering dipakai di alur ini: - `MISSION_AFTER_FLIGHT_LOCKED` - `FLIGHT_DATA_CREATE_BLOCKED` - `FLIGHT_DATA_AFTER_FLIGHT_LOCKED` - `FLIGHT_DATA_LOCKED` - `FM_REPORT_LOCKED` ## Catatan Implementasi - `after_flight_inspection` tidak lagi memicu refresh `helicopter_usage` - `flight_data` tidak lagi memicu refresh `helicopter_usage` - refresh `helicopter_usage` hanya terjadi saat `fm_report` di-complete - `GET FM Report` tetap aman walau row `helicopter_usage` belum ada ## Referensi Endpoint - `POST /api/v1/mission/create` - `PATCH /api/v1/mission/update/{flight_id}` - `POST /api/v1/flight-data/create` - `PATCH /api/v1/flight-data/update/{id}` - `DELETE /api/v1/flight-data/delete/{id}` - `POST /api/v1/after-flight-inspection/create` - `PATCH /api/v1/after-flight-inspection/update` - `POST /api/v1/fm-reports/complete/{flight_id}` - `GET /api/v1/fm-reports/get/{flight_id}`