Currency type - dynamic currency codes
- Dominant language
- Rust
- Stars
- 20.8k
- Forks
- 2.1k
- Avg merge
- 1d 2h
- Merged PRs (30d)
- 181
Description
**Is your feature request related to a problem? Please describe.**
The `currency` parameter on `number` measures/dimensions currently accepts a **fixed ISO-4217 literal only**:
```yaml
measures:
- name: total_amount
sql: amount
type: sum
format: currency
currency: USD # fixed literal - cannot reference a column/dimension
```
This is fine when a column is always one currency. It breaks down for datasets where **each row is denominated in its own currency**, with the currency code stored in a companion column - a very common shape in any situation where you are dealing across currencies.
Today there is no way to tell Cube that a currency field depends on a second dimension to define the actual currency. Note: this is not about formatting the result, that should be a frontend consideration - but about being able to define at teh semantic layer a currency field when its not fixed per cube.
**Describe the solution you'd like**
Allow `currency` (or a new `currency_code`) to accept a field/SQL reference in addition to a literal, e.g.:
```yaml
measures:
- name: total_amount
sql: amount
type: sum
format: currency
currency:
sql: "{CUBE}.order_currency" # resolves per row from another column
```
or referencing a dimension:
```yaml
currency:
dimension: order_currency
```
Behaviour asked for:
- **Per-row resolution.** The currency code is read from the referenced field/expression for each row, so mixed-currency result sets render correctly.
- **Companion inclusion.** When a currency-formatted measure is selected, Cube ensures the referenced currency-code field is available/returned (or at minimum exposes the linkage in the response `annotation`) so clients don't have to hardcode the pairing.
- **Backward compatible.** A literal `currency: USD` keeps working exactly as today; the field-referenced form is opt-in.
- **Numeric type preserved.** Values stay numeric on the wire (like Power BI's dynamic format strings, which keep the measure's data type); the currency is display metadata resolved at the edge, never a pre-formatted string baked into the value.
**Describe alternatives you've considered**
- **`meta` + client glue.** Stash the currency-code field name in `meta` and have the frontend read it, add the field to the query, and format per row. Works, but every consumer re-implements it and Cube does nothing automatically. This is our current plan as a workaround.
- **Views that pair the members.** A view can expose `amount` and `order_currency` together, but selecting one still doesn't pull the other, and the currency is still a fixed literal on the format — so it doesn't achieve per-row labels.
- **Multi-stage `switch` measures** (precomputed `amount_usd`/`amount_eur`/…). Selects a *value* for a chosen currency but the display `currency` attribute stays a fixed literal; doesn't give per-row labels within one result, and doesn't scale to arbitrary currencies.
**Additional context**
## Prior art - other semantic-layer / BI tools that support this
This feature isnt supported as standard, but, does have existing implementations:
- ThoughtSpot - "Set number, date, and currency formats": https://docs.thoughtspot.com/cloud/26.4.0.cl/data-modeling-patterns · dbt tag `ts_currency_type: from_column`: https://docs.thoughtspot.com/cloud/26.5.0.cl/dbt-integration-metadata-tags
- Power BI - Dynamic format strings for measures: https://learn.microsoft.com/en-us/power-bi/create-reports/desktop-dynamic-format-strings · SQLBI write-up (per-cell variation): https://www.sqlbi.com/articles/introducing-dynamic-format-strings-for-dax-measures/
There is a long standing open issue in metabase too (but not implemented AFAIK)
- Metabase - open issue #9879: https://github.com/metabase/metabase/issues/9879 · maintainer confirmation: https://discourse.metabase.com/t/how-to-set-currency-dynamically/16410
Contributor guide
Research direction
Start by tracing the existing `currency` measure parameter and its response `annotation` behavior; no implementation files or tests are named in the issue. Done means literal currencies remain compatible, field or dimension references resolve per row, numeric values stay numeric, and clients can obtain the currency-code linkage without hardcoding it.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- rust
- Domain
- backend-api-design
- Issue type
- Feature
- Difficulty
- 5/5
- Estimated time
- Over a week
- Activity status
- Quiet
- Clarity
- Mostly clear
- Newbie friendliness
- 42/100