diff --git a/fusion_plating/fusion_plating_shopfloor/tests/__init__.py b/fusion_plating/fusion_plating_shopfloor/tests/__init__.py index bfabdc1e..3cf4b4ed 100644 --- a/fusion_plating/fusion_plating_shopfloor/tests/__init__.py +++ b/fusion_plating/fusion_plating_shopfloor/tests/__init__.py @@ -6,3 +6,4 @@ from . import test_tablet_lock_payload from . import test_kiosk_user_acl from . import test_tablet_session_event_model from . import test_tablet_pin_auth_manager +from . import test_unlock_lock_session_endpoints diff --git a/fusion_plating/fusion_plating_shopfloor/tests/test_unlock_lock_session_endpoints.py b/fusion_plating/fusion_plating_shopfloor/tests/test_unlock_lock_session_endpoints.py new file mode 100644 index 00000000..f1417e9f --- /dev/null +++ b/fusion_plating/fusion_plating_shopfloor/tests/test_unlock_lock_session_endpoints.py @@ -0,0 +1,96 @@ +import json + +from odoo.tests.common import HttpCase, tagged + + +@tagged('-at_install', 'post_install', 'fp_tablet') +class TestUnlockLockSessionEndpoints(HttpCase): + + def setUp(self): + super().setUp() + Users = self.env['res.users'].with_context(no_reset_password=True) + self.tech = Users.create({ + 'login': 'http_tech@example.com', 'name': 'HTTP Tech', + 'email': 'http_tech@example.com', + 'group_ids': [(6, 0, [ + self.env.ref('fusion_plating.group_fp_technician').id + ])], + }) + self.tech.sudo().set_tablet_pin('1234') + # Make sure the kiosk password is set so lock_session can re-auth. + ICP = self.env['ir.config_parameter'].sudo() + if not ICP.get_param('fp.tablet.kiosk_password'): + ICP.set_param('fp.tablet.kiosk_password', 'test_kiosk_pwd') + kiosk = self.env.ref('fusion_plating_shopfloor.user_fp_tablet_kiosk') + kiosk.sudo().password = 'test_kiosk_pwd' + + def _jsonrpc(self, route, params): + return self.url_open( + route, + data=json.dumps({'jsonrpc': '2.0', 'params': params}), + headers={'Content-Type': 'application/json'}, + ).json() + + def test_unlock_session_with_correct_pin_returns_ok(self): + self.authenticate('fp_tablet_kiosk@enplating.local', 'test_kiosk_pwd') + resp = self._jsonrpc('/fp/tablet/unlock_session', { + 'user_id': self.tech.id, 'pin': '1234', + }) + self.assertTrue(resp['result']['ok']) + self.assertEqual(resp['result']['tech_id'], self.tech.id) + + def test_unlock_session_writes_audit_event(self): + self.authenticate('fp_tablet_kiosk@enplating.local', 'test_kiosk_pwd') + self._jsonrpc('/fp/tablet/unlock_session', { + 'user_id': self.tech.id, 'pin': '1234', + }) + events = self.env['fp.tablet.session.event'].sudo().search([ + ('event_type', '=', 'unlock'), + ('user_id', '=', self.tech.id), + ]) + self.assertGreater(len(events), 0) + e = events[0] + self.assertTrue(e.session_id_hash) + self.assertTrue(e.session_started_at) + + def test_unlock_session_with_wrong_pin_writes_failed_event(self): + self.authenticate('fp_tablet_kiosk@enplating.local', 'test_kiosk_pwd') + resp = self._jsonrpc('/fp/tablet/unlock_session', { + 'user_id': self.tech.id, 'pin': '0000', + }) + self.assertFalse(resp['result']['ok']) + events = self.env['fp.tablet.session.event'].sudo().search([ + ('event_type', '=', 'failed_unlock'), + ('attempted_user_id', '=', self.tech.id), + ('failure_reason', '=', 'wrong_pin'), + ]) + self.assertGreater(len(events), 0) + + def test_lock_session_writes_manual_lock_event(self): + self.authenticate('fp_tablet_kiosk@enplating.local', 'test_kiosk_pwd') + # Unlock first + self._jsonrpc('/fp/tablet/unlock_session', { + 'user_id': self.tech.id, 'pin': '1234', + }) + # Then lock with reason=manual + resp = self._jsonrpc('/fp/tablet/lock_session', {'reason': 'manual'}) + self.assertTrue(resp['result']['ok']) + events = self.env['fp.tablet.session.event'].sudo().search([ + ('event_type', '=', 'manual_lock'), + ('user_id', '=', self.tech.id), + ]) + self.assertGreater(len(events), 0) + self.assertIsNotNone(events[0].session_ended_at) + self.assertGreaterEqual(events[0].duration_seconds, 0) + + def test_lock_session_idle_reason_writes_idle_lock(self): + self.authenticate('fp_tablet_kiosk@enplating.local', 'test_kiosk_pwd') + self._jsonrpc('/fp/tablet/unlock_session', { + 'user_id': self.tech.id, 'pin': '1234', + }) + self._jsonrpc('/fp/tablet/lock_session', {'reason': 'idle'}) + events = self.env['fp.tablet.session.event'].sudo().search([ + ('event_type', '=', 'idle_lock'), + ('user_id', '=', self.tech.id), + ]) + self.assertGreater(len(events), 0)