JayPocket
Positions
Recent transactions
Alerts
History

Alerts are evaluated every time quotes refresh while the app is open (same as JStock desktop, which alerts while running). iOS does not allow background checks for home-screen web apps without a push server.

Quote provider
Alpha Vantage API key
Primary · free · 25 requests/day (0 used today)
Marketstack API key
Fallback · free · 100 requests/month (each symbol = 1 request)
CORS proxy (Yahoo)
Preferred first — auto-fails over to the others per request
General
Default currency
Portfolio totals are converted into this
Refresh on open
Fetch quotes when the app starts
FX rates
Backup

Everything lives only on this device. Export regularly — JSON includes watchlist, transactions, alerts and settings (keys excluded).

Danger zone

JayPocket v1.5 — inspired by yccheok/JStock · jays cache acorns, you cache ETFs 🐦

📲 Install on your iPhone

  1. Open this page's address in Safari (not Chrome).
  2. Tap the Share button (square with ↑).
  3. Scroll and tap Add to Home Screen, then Add.
  4. Launch it from the home screen — it runs full-screen like a native app.
⚠️ If a red "demo mode" banner is showing, this copy of the app cannot save data on this address. Host your own copy (below) for full persistence — it takes ~3 minutes.

🏠 Host your own copy (free, ~3 min)

  1. Create a GitHub account (you likely have one).
  2. Click New repository → name it jaypocket → Public → Create.
  3. Click uploading an existing file → upload index.html and icon.png → Commit.
  4. Repo Settings → Pages → Branch: main, folder / (root) → Save.
  5. Wait ~1 min; your app is at https://YOURNAME.github.io/jaypocket/.
  6. Open that address in Safari → Add to Home Screen. Done — data now persists on-device.

🔑 Free API keys (recommended)

  • Alpha Vantage (primary): claim key — instant, no card. 25 requests/day = ~2 full refreshes of 9 tickers.
  • Marketstack (fallback): free plan — 100 requests/month, end-of-day prices.
  • Yahoo (zero signup): works with no key via a public CORS proxy — unlimited-ish and live, but the proxy can occasionally be down. It is also used to auto-fill currency and fund names.

Paste keys in Settings. In Auto mode the app uses: Alpha Vantage → Marketstack → Yahoo, skipping providers without keys or budget, falling through per ticker on errors.

📊 Provider comparison

ProviderFree limitFreshnessCoverage
Alpha Vantage25 req/day (1 per ticker)~end of dayLSE (.LON), Xetra (.DEX)
Marketstack100 req/month (1 per ticker)End of day70+ exchanges (MIC suffix, e.g. .XLON)
Yahoo + proxyno keyLive/delayedEverything (suffix .L .AS .DE .MI) — rotates AllOrigins / corsproxy / Jina automatically if one is down

💱 Currencies

  • Each holding quotes in its native currency; each transaction stores its own currency too.
  • Portfolio totals convert everything into your default currency using daily ECB rates (frankfurter.dev).
  • LSE prices in pence (GBp) are auto-converted to GBP (÷100) — e.g. EMIM.

🕰 Change window

The pills above the watchlist switch what the % chip compares against: 1d uses the official previous close from your quote provider; 5d compares to the close five trading days back; 30d / 3m / 6m / 1y look back by calendar date using Yahoo daily closing prices (fetched once per holding, refreshed about daily). The chip always shows the active period label, e.g. 3m +4.2%.

📉 DCA badges

Each watchlist row shows two DCA helpers:

  • ⛰ vs high — distance in % from the all-time high of that listing (computed from Yahoo's full monthly price history, cached for 7 days, nudged up live if a new high prints).
  • 🛒 vs last buy — distance in % from the price of your most recent recorded buy, converted across currencies via ECB rates when needed. It turns green when the price is at or below your last buy — your next tranche would be cheaper than the previous one.

ATH uses the Yahoo symbol's own currency and history; switching a holding to another listing (e.g. IWDA.AS → IWDA.L) refetches it automatically.

🔔 Alerts

Three alert types, all evaluated on every refresh while the app is open (background push needs a server; JStock desktop behaves the same way — it alerts while running). Fired alerts banner + beep, then disarm until you re-arm them.

  • Price level — classic rises-above / falls-below an absolute price.
  • Below high — fires when the price dips ≥ X% under the all-time high (quick presets: 5% and 10%). Re-bases automatically when a new high prints.
  • Below last buy — the DCA alert: fires when the price dips ≥ X% under your most recent buy (0 = any dip below it; cross-currency handled via ECB). Re-bases each time you record a new buy, so it always tracks your next tranche.

🧭 Symbols

Your nine ETFs are pre-mapped per provider (verified working on Yahoo). Tap any watchlist row → Edit to change lines/exchanges — e.g. switch IWDA between Amsterdam IWDA.AS (EUR) and London IWDA.L (USD). The button looks up any new Yahoo symbol and auto-fills name & currency. AGGH has no Alpha Vantage mapping (no Xetra line; the LSE line is a different share class) — it auto-falls back to Yahoo.

🔒 Privacy

No accounts, no server, no analytics. Watchlist, transactions, alerts and API keys are stored only in this device's browser storage. Use Export for backups before iOS cleanups or switching hosting.

🛡 Security & hardening

  • No third-party code — the app loads zero external scripts or fonts, so there's no supply-chain/CDN attack surface (and nothing needing Subresource Integrity).
  • Content-Security-Policy — a strict policy ships in the page itself and (on Cloudflare) in a _headers file: it blocks injected external scripts, framing/clickjacking, and restricts network calls to only the quote/FX hosts. If you set a custom proxy, add its host to both the <meta> CSP and _headers connect-src.
  • All rendered text is HTML-escaped, including fund names pulled from Yahoo — so a crafted name or imported backup can't inject markup.
  • Tamper protection is account-level: nobody can change the hosted file without your host login — turn on 2FA on your Cloudflare account. Optionally put a free Cloudflare Access email-login wall in front of the site.