Sync
One command refreshes the outside data firma depends on: live stock prices from Finnhub and historical FX rates from FRED. Because the scope is derived from the data you've already logged, firma asks each API only for what is missing.
firma sync
By default, this syncs prices for your active holdings and FX history for the
five supported currencies: KRW, JPY, EUR, CNY, and GBP. Both happen in one run.
$firma sync
◇ Updated 4 stocks ◇ Synced 9525 FX rates across 5 currencies
Requires both
finnhub-key (for prices) and fred-key (for FX history).
Run firma config set finnhub-key <key> and
firma config set fred-key <key> first.Scope is Derived from Your Data
firma never asks the APIs for more than it needs. The sync scope is computed from the
local SQLite database:
Prices, based on active holdings
Only tickers with a non-zero net position, computed from your transactions, are fetched from Finnhub. Sell a position down to 0 and it disappears from the next sync. If you hold 4 stocks, sync makes 4 Finnhub calls, not 400.
FX history, based on your earliest entry
On the first run, firma scans transactions, balances, and flow entries to find your earliest date, then backfills FX rates from there through today, usually in about 5 FRED calls and 10 seconds. After that, it only fetches dates beyond your latest cached rate, which is usually sub-second.
This means you should add your data first, then sync. If the database is
empty, sync has nothing to work from and does nothing.
firma sync fx
This refreshes FX history only. It's useful when you import an older transaction
that predates the current FX cache, or when you want updated historical rates
without re-fetching prices.
$firma sync fx
◇ Synced 9525 FX rates across 5 currencies
Same incremental logic. Pulls from
FRED
via the corresponding daily series (
DEXKOUS, DEXJPUS,
DEXCHUS, DEXUSEU, DEXUSUK) and stores
uniform direction (foreign per 1 USD) in ~/.firma/firma.db
fx_rates table.Why Historical FX Matters
Without a historical FX cache, past balances shown in a non-USD currency use
today's exchange rate. That means "what was my net worth in KRW in 2018?" gets
the wrong answer. Firma converts each entry using the FX rate from its own date,
so historical figures reflect what you actually had at that time.
Anything tagged with a date uses the historical rate. Anything that represents
current value, such as portfolio market value, the brief's MACRO TODAY section,
or FX impact since yesterday, stays on live rates from
open.er-api.com.Daily Routine
After the initial setup, the morning ritual is two commands or one Claude prompt:
$firma sync && firma brief
Or, in Claude:
Claude Desktop · firma MCP connected
You
Sync everything and give me today's brief.
Claude
sync_prices ✓ sync_fx_rates ✓ get_brief ✓
Portfolio is up +$1,820 (+1.1%) today. NVDA leads at +4.3%. Macro is risk-on (5/5), stress low (4/100). MSFT earnings hits Apr 29. Anything you want to dig into?