ADR-009: Insights and data visualisation approach¶
| Status | Accepted |
| Date | 2026-04-10 |
| Deciders | CTO, Head of Product, CRO |
| Affects repos | bank-app, bank-risk-platform |
Status¶
Accepted — 2026-04-10
Context¶
The bank has two distinct visualisation needs:
Customer-facing insights: Spending breakdowns, balance trends, savings progress, FX rate movements, pre-approval offers, anomaly alerts. These must feel native to the app — fast, beautiful, intuitive. Not a BI tool embedded in a banking app.
Internal / operational intelligence: Capital and liquidity dashboards for Treasury, AML typology analysis for Compliance, credit portfolio views for Risk, management MI for the executive team, operational exception queues for back office. These range from real-time operational dashboards to analytical deep-dives.
The question is whether to serve both — or either — from a traditional BI platform (Tableau, Power BI, Looker), from embedded charts in the front end, from Snowflake's native tooling, or from an AI-augmented approach that combines visualisation with natural language interaction.
Options evaluated¶
Option A — Traditional BI platform (Tableau, Power BI, Looker)¶
A standalone BI tool connected to Snowflake. Users access dashboards via the BI platform's own interface.
Strengths: Pre-built visualisation library; self-service for non-technical users; strong regulatory reporting presentation; handles complex cross-dimensional analysis.
Weaknesses: Separate tool from the bank's front end — creates a disjointed experience; licensing cost (Tableau/Looker are expensive); most BI platforms feel old compared to modern app UX; customer-facing use is not appropriate; not suitable for real-time operational views; requires BI developer skills separate from the engineering team.
Option B — Embedded charts in the front end (Recharts, Tremor, Chart.js, Nivo)¶
Charts and data tables built directly into the React/Next.js front end using open-source charting libraries. Data served via a dedicated Snowflake read API — a thin Lambda layer that queries Snowflake dynamic tables and caches results at the API layer (Redis / ElastiCache, TTL matched to signal cadence). No reporting or visualisation data passes through Postgres.
Strengths: Native app experience — charts feel like part of the product, not an embedded tool; full control over design and UX; no additional licensing; fast for pre-computed data; works for both customer-facing and back office surfaces from the same codebase (ADR-004); Snowflake is the single source of truth for all analytical data — no duplication into Postgres; aligned with KISS and cost-effective principles.
Weaknesses: Ad-hoc analysis (slice-and-dice, custom date ranges, dimension pivoting) is harder to build than in a BI tool; more engineering effort to build each visualisation; complex analytical queries need to be pre-computed in Snowflake dynamic tables.
Option C — Snowflake-native (Streamlit in Snowflake, Snowsight)¶
Snowflake has two native visualisation options: Snowsight (the Snowflake web UI with dashboards) and Streamlit in Snowflake (Python-based data apps running inside Snowflake).
Strengths: Zero data movement — visualisations run directly on the data; Streamlit provides rich interactive data apps with Python; no additional platform; good for internal analytical users.
Weaknesses: Not suitable for customer-facing use; Snowsight is a BI tool, not a product interface; Streamlit apps are Python-based and separate from the bank's main front end; limited design control.
Option D — AI-augmented approach (embedded charts + natural language interaction)¶
Embedded charts in the front end (Option B) augmented with an AI layer that allows natural language interaction. Customer-facing: "Why did my spending go up last month?" generates an AI explanation drawing on the customer's categorised transaction data in Snowflake. Internal: "Show me customers with a credit score above 650 who haven't been offered a loan" generates a Snowflake query and returns results in a table.
Strengths: Transforms static dashboards into interactive intelligence; the AI layer works directly with data in Snowflake — no duplication required; customer-facing AI explanations use the categorisation and insight models already built in Snowflake; internal AI-assisted analysis reduces the need for a self-service BI tool; aligns strongly with AP-007 (Evolution) and BG-003 (Intelligent financial assistant).
Weaknesses: AI layer adds complexity; requires careful prompt engineering to avoid hallucinated financial data; natural language to SQL requires guardrails; customer-facing AI responses must be governed (could generate inappropriate financial advice).
Perspective evaluation¶
| Perspective | Traditional BI | Embedded charts | Snowflake-native | AI-augmented |
|---|---|---|---|---|
| Usability | ~ Separate tool | ✓ Native experience | ~ Internal only | ✓ Most intuitive |
| Strategy | ~ Backward-looking | ✓ | ✓ | ✓ Differentiating |
| Evolution | ~ BI vendor dependent | ✓ Full control | ✓ Snowflake grows | ✓ AI improves over time |
| Cost | ✗ High licensing | ✓ Open source | ✓ Included in Snowflake | ✓ API cost marginal |
| Integration | ~ Separate platform | ✓ Same codebase | ✓ On the data | ✓ Both layers |
| Support & Maintenance | ~ Separate tool to maintain | ✓ Same team | ✓ | ~ AI governance overhead |
| Resource | ~ BI developer skills | ✓ Frontend team | ✓ Data team | ~ AI/prompt engineering |
| Capability | ✓ Rich ad-hoc analysis | ~ Pre-built views only | ✓ | ✓ |
| Regulatory | ~ Separate evidence trail | ✓ Auditable via API | ✓ | ✓ with guardrails |
See perspectives.md for how to use these evaluation lenses.
Principles alignment¶
| Principle | Assessment |
|---|---|
| AP-001 KISS | Embedded charts is simplest; Snowflake is the single analytical source — no duplication into Postgres for display purposes |
| AP-005 Customer driven | Customer-facing AI explanations directly serve BG-003 (intelligent financial assistant) |
| AP-006 Cost effective | Open-source charting + Snowflake Cortex; no BI licensing |
| AP-007 Evolution | AI layer improves as models improve and more data accumulates |
| AP-008 Real time | Real-time operational views need pre-computed data; batch analytics do not |
Recommendation (pending decision)¶
Option D — AI-augmented embedded approach, implemented in two layers:
Layer 1 — Embedded charts (launch): - Recharts or Tremor for customer-facing visualisations in the app - Back office dashboards built in the same front end (ADR-004) - Data served via a dedicated Snowflake read API (thin Lambda → Snowflake presentation tables → response). No external cache layer — freshness is managed by Dynamic Table refresh cadence (ADR-038) - Reporting and insight data does not pass through Postgres — Snowflake is the single source and Postgres is not used as a reporting cache - The Snowflake presentation layer pre-shapes data to the API response payload — roll-ups, pivots, and aggregations happen at Dynamic Table refresh time, not at query time. This is equivalent to a traditional BI semantic/presentation layer - Design system consistent with the app — charts are product, not BI
Layer 2 — AI interaction (phase 2, 3–6 months post-launch): - Customer-facing: natural language explanations of spending, savings, and balance trends using Claude API + categorised transaction data from Snowflake - Internal: natural language to Snowflake query for back office power users (compliance, risk, credit analysts) - Guardrails: customer AI responses restricted to informational — no financial advice; all queries logged
Traditional BI tools are not recommended. They create a separate platform to maintain, cost significant licensing fees, and produce a disjointed experience. If an executive or analyst needs ad-hoc analysis capability beyond the embedded charts, Streamlit in Snowflake provides that without adding a BI platform.
Data layer constraint (see ADR-038)¶
ADR-038 establishes the formal three-tier rule. For this ADR, the operative constraint is:
Visualisation and reporting data is Tier 3. It is read directly from Snowflake via the API layer. It is never written into Postgres for display purposes.
The Snowflake read API queries purpose-built presentation tables (pre-shaped Dynamic Tables, one row per customer per signal) — not the raw analytical tables. Heavy computation happens at refresh time. The API layer owns the circuit breaker (graceful degraded response if Snowflake is slow); Snowflake owns the data and the freshness guarantee via Dynamic Table refresh cadence. No Redis or external cache is used — the presentation layer is the cache.
Relevant viewpoints¶
- Functional viewpoint — Customer insight cards; back office dashboards; AI interaction capability
- System viewpoint — Chart components ← API layer (cache) ← Snowflake dynamic tables; AI layer ← Claude API ← Snowflake
- Information viewpoint — Which metrics are in which Snowflake dynamic tables; cache TTL per signal type
- Security viewpoint — AI query guardrails; financial advice boundary; audit trail for AI responses; Snowflake read API row-level security
See viewpoints.md for guidance on producing these viewpoints.
Signoff record¶
| Date | Name | Role | Status |
|---|---|---|---|
| 2026-04-10 | Ross Millen | CTO | Approved |
| 2026-04-10 | Ross Millen | Head of Architecture | Approved |
| 2026-04-10 | Ross Millen | Head of Data | Approved |
Capabilities¶
| Capability | Description | Relationship |
|---|---|---|
| CAP-019 | Monthly spending summary & trends | enabled — embedded charts driven by Snowflake read API |
| CAP-020 | Predicted upcoming payments | enabled — payment prediction signals from Snowflake presented via read API |
| CAP-021 | Low balance alert | enabled — balance threshold signals from Snowflake served to insight cards |
| CAP-022 | Unusual transaction alert | enabled — anomaly signals from Snowflake presented in app |
| CAP-023 | Net worth dashboard (linked external accounts) | enabled — net worth visualisation via embedded Recharts/Tremor |
| CAP-063 | Proactive financial insight engine | enabled — embedded charts and read API pattern is the delivery mechanism |
| CAP-070 | Real-time capital ratio engine (CET1/RWA) | governed — capital dashboards served from Snowflake via read API |
| CAP-071 | LCR/NSFR continuous calculation | governed — liquidity dashboards served from Snowflake via read API |
Related decisions¶
| ADR | Title | Relationship |
|---|---|---|
| ADR-002 | Snowflake as the analytics and risk compute platform | data source for all visualisations |
| ADR-004 | Single frontend codebase for customer and back office | back office dashboards use the same codebase |
| ADR-019 | Intelligent customer home screen and financial intelligence layer | home screen is the primary insight delivery surface |
| ADR-038 | Data access tier policy — Snowflake as the reporting and insight layer | defines Tier 3 — all insight and reporting data comes from Snowflake |
All ADRs
Compiled 2026-05-22 from source/entities/adrs/ADR-009.yaml