Fix category budget overlaps and document the uv run test workflow.
Tests / test (push) Successful in 11s
Tests / lint (push) Successful in 12s

This commit is contained in:
2026-10-18 09:40:31 +02:00
parent ea7854473f
commit d4ebab96d6
5 changed files with 207 additions and 95 deletions
+162
View File
@@ -414,6 +414,168 @@ class TestSetCategoryBudgetDateEdgeCases:
)
assert len(budgets) == 2
def test_shared_endpoint_is_replaced(self, db_session: Session):
"""Inclusive ranges that share a date must not overlap after replacement."""
cat = CategoryFactory.build()
cat_db = upsert_category(db_session, cat, do_commit=False)
db_session.commit()
set_category_budget(
db_session,
CategoryBudget(
category=cat,
amount_eur=100.00,
valid_from=date(2026, 10, 1),
valid_to=date(2026, 10, 15),
),
)
set_category_budget(
db_session,
CategoryBudget(
category=cat,
amount_eur=200.00,
valid_from=date(2026, 10, 15),
valid_to=date(2026, 10, 31),
),
)
budgets = (
db_session.query(CategoryBudgetDb)
.filter_by(category_id=cat_db.id)
.order_by(CategoryBudgetDb.valid_from)
.all()
)
assert [(b.amount_eur, b.valid_from, b.valid_to) for b in budgets] == [
(100.00, date(2026, 10, 1), date(2026, 10, 14)),
(200.00, date(2026, 10, 15), date(2026, 10, 31)),
]
class TestSetCategoryBudgetRegressionCases:
def test_new_range_overlapping_multiple_budgets_is_added_once(
self, db_session: Session
):
cat = CategoryFactory.build()
cat_db = upsert_category(db_session, cat, do_commit=False)
db_session.commit()
for start, end, amount in (
(date(2026, 10, 1), date(2026, 10, 31), 100.00),
(date(2026, 12, 1), date(2026, 12, 31), 200.00),
):
set_category_budget(
db_session,
CategoryBudget(
category=cat,
amount_eur=amount,
valid_from=start,
valid_to=end,
),
)
set_category_budget(
db_session,
CategoryBudget(
category=cat,
amount_eur=300.00,
valid_from=date(2026, 10, 1),
valid_to=date(2026, 12, 31),
),
)
budgets = (
db_session.query(CategoryBudgetDb).filter_by(category_id=cat_db.id).all()
)
assert len(budgets) == 1
assert budgets[0].amount_eur == 300.00
assert budgets[0].valid_from == date(2026, 10, 1)
assert budgets[0].valid_to == date(2026, 12, 31)
@pytest.mark.parametrize(
("existing_start", "existing_end", "new_start", "new_end", "expected"),
[
(
date(2026, 10, 1),
date(2026, 12, 31),
None,
date(2026, 11, 15),
[
(100.00, date(2026, 11, 16), date(2026, 12, 31)),
(200.00, None, date(2026, 11, 15)),
],
),
(
date(2026, 10, 1),
date(2026, 12, 31),
date(2026, 11, 15),
None,
[
(100.00, date(2026, 10, 1), date(2026, 11, 14)),
(200.00, date(2026, 11, 15), None),
],
),
(
None,
date(2026, 12, 31),
date(2026, 10, 1),
date(2026, 10, 31),
[
(100.00, None, date(2026, 9, 30)),
(200.00, date(2026, 10, 1), date(2026, 10, 31)),
(100.00, date(2026, 11, 1), date(2026, 12, 31)),
],
),
(
date(2026, 10, 1),
None,
date(2026, 11, 1),
date(2026, 11, 30),
[
(100.00, date(2026, 10, 1), date(2026, 10, 31)),
(200.00, date(2026, 11, 1), date(2026, 11, 30)),
(100.00, date(2026, 12, 1), None),
],
),
],
)
def test_partially_unbounded_ranges_are_split_correctly(
self,
db_session: Session,
existing_start: date | None,
existing_end: date | None,
new_start: date | None,
new_end: date | None,
expected: list[tuple[float, date | None, date | None]],
):
cat = CategoryFactory.build()
cat_db = upsert_category(db_session, cat, do_commit=False)
db_session.commit()
set_category_budget(
db_session,
CategoryBudget(
category=cat,
amount_eur=100.00,
valid_from=existing_start,
valid_to=existing_end,
),
)
set_category_budget(
db_session,
CategoryBudget(
category=cat,
amount_eur=200.00,
valid_from=new_start,
valid_to=new_end,
),
)
budgets = (
db_session.query(CategoryBudgetDb).filter_by(category_id=cat_db.id).all()
)
actual = {(float(b.amount_eur), b.valid_from, b.valid_to) for b in budgets}
assert actual == set(expected)
class TestFindCategoryDb:
"""Test find_category_db function."""