# -*- coding: utf-8 -*- """Test untuk memastikan pembagian tanggung jawab (responsibility bucket) dan laporan tiket berjalan dengan benar. Data expected value diambil dari tiket #9658 yang sudah disetujui. Test ini hanya jalan kalau fixture tiket #9658 sudah di-install. """ from odoo.tests.common import TransactionCase class TestResponsibilityRules(TransactionCase): @classmethod def setUpClass(cls): """Siapkan model Ticket supaya bisa dipakai di semua test.""" super().setUpClass() cls.Ticket = cls.env['freshservice.ticket'] def _ticket_9658(self): """Cari tiket #9658 di database. Return kosong kalau belum ada.""" return self.Ticket.search([('external_ticket_id', '=', '9658')], limit=1) def test_acceptance_1_eight_buckets_sum_to_total(self): """Cek 8 bucket tanggung jawab. Jumlah jam masing-masing bucket harus cocok dengan nilai expected, dan total semua bucket harus sama dengan grand total. """ ticket = self._ticket_9658() if not ticket: self.skipTest('Approved Freshservice fixture for ticket #9658 is not installed.') values = { 'internal': 30.70, 'it_hold': 10.74, 'customer': 31.34, 'user_after_auto_resolve': 29.89, 'needs_verification': 36.72, 'scheduled_meeting': 13.26, 'third_party': 27.22, 'resolved_idle': 0.0, } actual = {key: 0.0 for key in values} for log in ticket.stage_log_ids: key = log.override_responsibility or log.responsibility if key in actual: actual[key] += log.duration_hours or 0.0 for key, expected in values.items(): self.assertAlmostEqual(actual[key], expected, places=2, msg=key) self.assertAlmostEqual(sum(actual.values()), sum(values.values()), places=2) def test_acceptance_2_as_of_and_overrides(self): """Pastikan tiket punya field first_ack_at dan first_meaningful_response_at (waktu respon pertama). """ ticket = self._ticket_9658() if not ticket: self.skipTest('Approved Freshservice fixture for ticket #9658 is not installed.') self.assertTrue(all(hasattr(ticket, field) for field in ( 'first_ack_at', 'first_meaningful_response_at', ))) def test_acceptance_3_bucket_invariant(self): """Cek invariant: total jam dari semua bucket harus sama dengan total jam dari semua stage log. Tidak boleh ada jam yang hilang atau dobel. """ ticket = self._ticket_9658() if not ticket: self.skipTest('Approved Freshservice fixture for ticket #9658 is not installed.') bucket_names = { 'internal', 'it_hold', 'customer', 'user_after_auto_resolve', 'needs_verification', 'scheduled_meeting', 'third_party', 'resolved_idle', } bucket_total = sum( log.duration_hours or 0.0 for log in ticket.stage_log_ids if (log.override_responsibility or log.responsibility) in bucket_names ) self.assertAlmostEqual(bucket_total, sum(log.duration_hours or 0.0 for log in ticket.stage_log_ids), places=2)