aboutsummaryrefslogtreecommitdiffstats
path: root/tests
diff options
context:
space:
mode:
authorDanilo M. <danix@danix.xyz>2026-06-30 11:06:44 +0200
committerDanilo M. <danix@danix.xyz>2026-06-30 11:06:44 +0200
commita9b7872fd85cbde483bc65fc1540a9d7f0c5d193 (patch)
tree6632adfe62bb8d05ea2802e5c4f11a3541cb6f75 /tests
parent28bde5b10abf904212dfc3cae937112134293053 (diff)
downloadfirefly-cli-a9b7872fd85cbde483bc65fc1540a9d7f0c5d193.tar.gz
firefly-cli-a9b7872fd85cbde483bc65fc1540a9d7f0c5d193.zip
feat: transaction add/list/get/search with type inference
Diffstat (limited to 'tests')
-rw-r--r--tests/unit/test_commands_transaction.py68
1 files changed, 68 insertions, 0 deletions
diff --git a/tests/unit/test_commands_transaction.py b/tests/unit/test_commands_transaction.py
new file mode 100644
index 0000000..db187b7
--- /dev/null
+++ b/tests/unit/test_commands_transaction.py
@@ -0,0 +1,68 @@
+import unittest
+from unittest.mock import MagicMock
+from firefly_cli.commands import transaction as tx
+from firefly_cli.context import Context
+
+def make_ctx():
+ client = MagicMock()
+ resolver = MagicMock()
+ return Context(client=client, resolver=resolver, human=False), client, resolver
+
+class TestTxAdd(unittest.TestCase):
+ def test_infers_withdrawal_from_asset_to_expense(self):
+ ctx, client, resolver = make_ctx()
+ resolver.account.side_effect = lambda n: {
+ "Checking": {"id": "1", "name": "Checking", "type": "asset"},
+ "Groceries": {"id": "2", "name": "Groceries", "type": "expense"},
+ }[n]
+ client.request.return_value = {"data": {"id": "55", "type": "transactions",
+ "attributes": {}}}
+ args = MagicMock(amount="42.50", source="Checking", dest="Groceries",
+ desc="food", date="2026-06-30", category=None,
+ tags=None, type=None)
+ rc = tx.cmd_add(args, ctx)
+ self.assertEqual(rc, 0)
+ method, path = client.request.call_args[0][:2]
+ body = client.request.call_args[1]["body"]
+ split = body["transactions"][0]
+ self.assertEqual((method, path), ("POST", "/api/v1/transactions"))
+ self.assertEqual(split["type"], "withdrawal")
+ self.assertEqual(split["source_id"], "1")
+ self.assertEqual(split["destination_id"], "2")
+ self.assertEqual(split["amount"], "42.50")
+
+ def test_infers_deposit_revenue_to_asset(self):
+ ctx, client, resolver = make_ctx()
+ resolver.account.side_effect = lambda n: {
+ "Salary": {"id": "7", "name": "Salary", "type": "revenue"},
+ "Checking": {"id": "1", "name": "Checking", "type": "asset"},
+ }[n]
+ client.request.return_value = {"data": {"id": "1", "attributes": {}}}
+ args = MagicMock(amount="1000", source="Salary", dest="Checking",
+ desc="pay", date=None, category=None, tags=None, type=None)
+ tx.cmd_add(args, ctx)
+ self.assertEqual(client.request.call_args[1]["body"]["transactions"][0]["type"],
+ "deposit")
+
+ def test_explicit_type_overrides_inference(self):
+ ctx, client, resolver = make_ctx()
+ resolver.account.side_effect = lambda n: {"id": "1", "type": "asset", "name": n}
+ client.request.return_value = {"data": {"id": "1", "attributes": {}}}
+ args = MagicMock(amount="5", source="A", dest="B", desc=None, date=None,
+ category=None, tags="food,fun", type="transfer")
+ tx.cmd_add(args, ctx)
+ split = client.request.call_args[1]["body"]["transactions"][0]
+ self.assertEqual(split["type"], "transfer")
+ self.assertEqual(split["tags"], ["food", "fun"])
+
+class TestTxList(unittest.TestCase):
+ def test_list_passes_date_params(self):
+ ctx, client, _ = make_ctx()
+ client.request.return_value = {"data": []}
+ args = MagicMock(since="2026-06-01", until="2026-06-30",
+ account=None, limit=10)
+ tx.cmd_list(args, ctx)
+ params = client.request.call_args[1]["params"]
+ self.assertEqual(params["start"], "2026-06-01")
+ self.assertEqual(params["end"], "2026-06-30")
+ self.assertEqual(params["limit"], 10)