Step 2: Normalize Currency
Convert all transaction amounts to USD while preserving original values. This replaces DataStage Lookup Stages with inline conversion logic.
The Goal
- Convert
AMOUNTfrom any currency to USD - Preserve
original_amountandoriginal_currencyfor reconciliation - Create
amount_usdas the normalized field
DataStage Equivalent
In DataStage, currency conversion typically requires:
- Lookup Stage reading from a rates table
- Transformer Stage applying the conversion
- Database connection to fetch current rates
- Caching logic to avoid repeated lookups
Expanso simplifies this with inline rate maps or external API calls.
Implementation
The canonical reference owns the currency processor, including the branch result mapping that returns converted fields to the original message. Inspect its input and output in the Explorer.
Understanding the Code
| Expression | What It Does |
|---|---|
let rates = {...} | Define a local variable with rate map |
$rates.get(this.CURRENCY) | Look up rate by currency code |
.or(1.0) | Default to 1.0 if currency not found |
this.AMOUNT * $rates... | Apply the conversion |
Why Use branch?
The branch processor creates an isolated scope:
- Variables defined with
letdon't leak to other processors - Cleaner separation of concerns
- Easier debugging and testing
Expected Output
Use the Explorer checkpoints for the sample input and converted fields.
Production Considerations
Dynamic Rate Fetching
For real-time rates, adapt the branch in the canonical reference to call a reviewed rate API. Preserve the original amount and currency before replacing the branch payload with the API response, and retain the result mapping that returns converted fields to the original message.
Rate Caching
Cache rates to reduce API calls:
- cache:
resource: exchange_rates
operator: get
key: ${! this.CURRENCY }
- mapping: |
root.exchange_rate = content().string().number().catch(1.0)
Handling Unknown Currencies
Log and flag records with unknown currencies:
- mapping: |
let rates = {
"USD": 1.0,
"EUR": 1.08,
"GBP": 1.27,
"JPY": 0.0067,
"CHF": 1.13,
"CAD": 0.74
}
root = this
root._warnings = if $rates.get(this.CURRENCY).or(null) == null {
this._warnings.or([]).append("Unknown currency: " + this.CURRENCY)
} else {
this._warnings.or([])
}
root.amount_usd = this.AMOUNT * $rates.get(this.CURRENCY).or(1.0)