ORE's AdvanceCalendar Convention Field
Table of Contents
Summary
AdvanceCalendar is a field on ORE's FXConvention (and, by the
same pattern, on commodity conventions) used specifically to advance
— roll forward — the dates ORE computes for an FX instrument: the
spot date from trade date, and the maturity date from spot. It is
therefore a fundamentally different kind of calendar from
business_day_calendar
and settlement_calendar: those answer "is this day a valid
business/settlement day," while AdvanceCalendar is consumed
directly by date arithmetic (Calendar::advance()), not membership
tests. Like every other ORE calendar field, its XML value is a
comma-joined list of calendar names under JointCalendar union
semantics — in practice almost always the pair's own two legs, but
stored and resolved explicitly rather than derived on the fly.
Detail
What it actually does
ORE resolves the spot and maturity dates of an FX instrument by
advancing directly off the convention's AdvanceCalendar, not off any
generically derived business-day calendar:
// OREAnalytics/orea/engine/parsensitivityinstrumentbuilder.cpp Date spot = conv->advanceCalendar().advance(today, conv->spotDays() * Days); Date maturity = conv->advanceCalendar().advance(spot, term);
The same field backs FX option pricing and FX vol curve construction
(OREData/ored/portfolio/fxoption.cpp,
OREData/ored/marketdata/fxvolcurve.cpp, both assign
spotCalendar_ = fxConv->advanceCalendar()), and yield-curve
bootstrapping for FX-forward-implied points
(OREData/ored/marketdata/yieldcurve.cpp). ORE's own User Guide
documents the fallback behaviour for FX forwards explicitly: "For cash
settlement and if a FXIndex is specified defaults to the fx convention
(field 'AdvanceCalendar') if left blank or omitted, otherwise to
NullCalendar (no holidays)" (Docs/UserGuide/tradedata/fxforward.tex).
XML example
From ORE's own example configuration
(Examples/MinimalSetup/Input/conventions.xml):
<FXConvention> <Id>EUR-GBP-FX</Id> <SpotDays>2</SpotDays> <SourceCurrency>EUR</SourceCurrency> <TargetCurrency>GBP</TargetCurrency> <PointsFactor>1</PointsFactor> <AdvanceCalendar>TARGET,UK</AdvanceCalendar> </FXConvention>
Other examples in the same repository show the same comma-joined
shape: UK,TARGET, US,JP, UK,US — in every case, exactly the
union of the pair's two legs' calendars, joined the same way
currency.holiday_calendar
is joined today.
Why it is stored explicitly rather than derived
Given that AdvanceCalendar almost always equals the union of the
pair's two legs, it might look redundant with a generically computed
business_day_calendar. ORE keeps it as an explicit, named convention
field rather than a derived value for two reasons evident from its
usage:
- It is resolved once at convention-load time and consumed directly
by date-arithmetic methods (
advance()), not membership-tested per-date, so eager resolution avoids recomputing a union on every date calculation. - It is overridable per convention independently of the pair's two
legs — nothing in ORE's schema constrains it to equal exactly
SourceCurrency+TargetCurrency's calendars, even though every example configuration happens to set it that way.
Comma-joined, not a single calendar
Because every observed value is a comma-joined list of two or more
calendar codes, AdvanceCalendar carries the same
many-to-many shape as
currency.holiday_calendar: a currency pair convention can need more
than one calendar, so a reference-data model of this field is a
junction (convention ↔ calendar), not a single nullable foreign key.
See also
- Calendars, Holidays and Events — the hub.
- Currency pair and currency entity fields —
business_day_calendarandsettlement_calendar, the two derived pair-level calendar conceptsAdvanceCalendaris distinct from. - Holiday Calendar Administration — the
JointCalendarunion semanticsAdvanceCalendar's comma-joined values rely on. - Open Source Risk Engine (ORE) — GitHub — source of the code excerpts and XML example above.
- QuantLib: Calendars and holidays — the underlying
Calendar::advance()mechanismAdvanceCalendaris consumed through.