diff --git a/app/bot_cli.py b/app/bot_cli.py index 8d725a9..4a72c0a 100644 --- a/app/bot_cli.py +++ b/app/bot_cli.py @@ -36,6 +36,24 @@ def cmd_set_pin(args): print(f"OK: f_username={f_username} t_username={t_username}") +def cmd_insert_user(args): + bot = CM_BOT_HAL() + f_password = bot.get_user_pass_from_acc(args.f_username) + if not f_password: + print(f"ERROR: no password for {args.f_username}", file=sys.stderr) + sys.exit(2) + success = bot.insert_user_to_table_user({ + "f_username": args.f_username, + "f_password": f_password, + "t_username": args.t_username, + "t_password": bot.security_pin, + }) + if not success: + print("ERROR: insert failed", file=sys.stderr) + sys.exit(1) + print(f"OK: inserted {args.f_username} → {args.t_username}") + + def build_parser() -> argparse.ArgumentParser: p = argparse.ArgumentParser( prog="bot_cli", @@ -50,6 +68,11 @@ def build_parser() -> argparse.ArgumentParser: sp.add_argument("link") sp.set_defaults(func=cmd_set_pin) + sp = sub.add_parser("insert-user", help="Insert into user table (Telegram /3).") + sp.add_argument("f_username") + sp.add_argument("t_username") + sp.set_defaults(func=cmd_insert_user) + return p diff --git a/tests/test_bot_cli.py b/tests/test_bot_cli.py index 78377dd..048763d 100644 --- a/tests/test_bot_cli.py +++ b/tests/test_bot_cli.py @@ -106,5 +106,50 @@ class CmdSetPinTests(unittest.TestCase): self.assertEqual(args.link, "https://chat.whatsapp.com/abc") +class CmdInsertUserTests(unittest.TestCase): + @mock.patch.object(bot_cli, "CM_BOT_HAL") + def test_inserts_using_password_lookup_and_security_pin(self, mock_hal_class): + mock_hal = mock_hal_class.return_value + mock_hal.get_user_pass_from_acc.return_value = "abc12345" + mock_hal.security_pin = "999111" + mock_hal.insert_user_to_table_user.return_value = True + out = io.StringIO() + with contextlib.redirect_stdout(out): + bot_cli.cmd_insert_user(argparse.Namespace(f_username="13c1234", t_username="player_x")) + self.assertIn("OK: inserted 13c1234 → player_x", out.getvalue()) + mock_hal.insert_user_to_table_user.assert_called_once_with({ + "f_username": "13c1234", + "f_password": "abc12345", + "t_username": "player_x", + "t_password": "999111", + }) + + @mock.patch.object(bot_cli, "CM_BOT_HAL") + def test_no_password_for_f_user_exits_2(self, mock_hal_class): + mock_hal = mock_hal_class.return_value + mock_hal.get_user_pass_from_acc.return_value = None + with self.assertRaises(SystemExit) as cm: + bot_cli.cmd_insert_user(argparse.Namespace(f_username="missing", t_username="player_x")) + self.assertEqual(cm.exception.code, 2) + mock_hal.insert_user_to_table_user.assert_not_called() + + @mock.patch.object(bot_cli, "CM_BOT_HAL") + def test_insert_failure_exits_1(self, mock_hal_class): + mock_hal = mock_hal_class.return_value + mock_hal.get_user_pass_from_acc.return_value = "abc" + mock_hal.security_pin = "000" + mock_hal.insert_user_to_table_user.return_value = False + with self.assertRaises(SystemExit) as cm: + bot_cli.cmd_insert_user(argparse.Namespace(f_username="13c1234", t_username="player_x")) + self.assertEqual(cm.exception.code, 1) + + def test_insert_user_subparser_dispatches(self): + parser = bot_cli.build_parser() + args = parser.parse_args(["insert-user", "13c1234", "player_x"]) + self.assertIs(args.func, bot_cli.cmd_insert_user) + self.assertEqual(args.f_username, "13c1234") + self.assertEqual(args.t_username, "player_x") + + if __name__ == "__main__": unittest.main()