Skip to main content

Asset Allocation (AA) — Local CLI

All commands run from backend/, venv activated (hard rule 1 — never run modules from inside their package folder). Target DB is whatever LOCAL_DB_* in backend/.env points to — tedb on localhost by default.

cd backend
venv\Scripts\activate

1. Apply the migrations

alembic upgrade head

Applies every migration in the chain, including the AA-related ones. Safe to re-run — Alembic tracks the applied revision and no-ops if already at head.

Check current revision:

alembic current

Full chain (oldest to newest), for orientation:

alembic history

2. Seed the data

python -m AA.seed_financial_data_2000_2026

Idempotent — inserts 3 assets (SAVINGS_RATE_SBI, FD_RATE_SBI_1Y, CPI_INFLATION_INDIA) into te_asset and their price rows into te_price, all via ON CONFLICT DO NOTHING. Re-running prints Inserted 0 new ... row(s) once seeded. To revise an already-seeded value, edit the script's data table and issue an UPDATE manually (or a migration) — it never overwrites an existing row.

Source data lives in AA/data/India_Financial_Data_2000-2026.xlsx (a user-supplied workbook, copied into the repo) — see AA/CLAUDE.md rule 6a for how ambiguous rows (ranges, multiple in-year revisions) were resolved into single values.

3. Run the tests

python -m pytest tests/test_aa_models.py tests/test_aa_allocation_engine.py -v

test_aa_models.py asserts te_asset's PK/unique/CHECK constraints (including the economic_data category) and te_price's PK/FK constraints are enforced at the schema level (SAVEPOINT-backed, tests/conftest.py — nothing written lingers in tedb). test_aa_allocation_engine.py is pure unit tests of the CAGR/backtest math against the older wide-table shape it was written for — kept passing (it's self-consistent with its own fixtures) but not exercised by anything live; see AA/CLAUDE.md's Status section.

Quick sanity check — everything at once

cd backend
alembic upgrade head
python -m AA.seed_financial_data_2000_2026
python -m pytest tests/test_aa_models.py tests/test_aa_allocation_engine.py -v

Expect: migrations apply (or no-op if already applied), seed reports 3 assets + 68 price rows inserted the first time / 0 thereafter, all tests PASSED.

Poke the data manually

python -c "
from sqlalchemy import create_engine, text
from app.core.config import settings
engine = create_engine(settings.SYNC_DATABASE_URL)
with engine.connect() as conn:
for row in conn.execute(text('SELECT code, asset_class, value_kind FROM te_asset ORDER BY id')):
print(row)
"