Computed Curves and Time Series
Alongside Curve/TimeSeries (which carry their own explicit values), odsl.types has four builders for fields the server computes for you instead:
EventCurve/EventTimeSeriesderive their values from an event group -- the same kind of eventsEvent/events_dataframe()write (see Writing Events) -- reading one property off each event as the value (and, for a curve, another as the tenor/maturity code). Neither carries an explicitdata/contractsfield -- the server rejects one being present at all, even empty ([8003] Invalid update ... Cannot contain data/contracts), since the whole point is that it's derived, not supplied.SmartCurve/SmartTimeSeriesderive their values from a formula expression against another curve/time series asBASE, optionally with a script layered on top. The base curve/time series id and the expression are both required arguments -- the server rejects either being missing the same way.
caution
The base id passed to SmartCurve/SmartTimeSeries has to be the referenced field's full OBJECTID:FIELDNAME reference id -- the same id odsl.get('data', source, id) would read it back with -- not just the field name on its own. 'CURVE' alone resolves to nothing and the smart curve/time series won't compute; it needs to be 'AAA.PYTHON-EXAMPLE:CURVE'.
All four attach to an object as a field exactly like Curve/TimeSeries do:
# EventCurve: built from 'tenor'/'price' properties on events under FORWARDS
event_curve = (
types.EventCurve('AAA.PYTHON-EXAMPLE:FORWARDS', 'price', 'tenor', '#REOMHENG', id='EVENT_CURVE')
.set_currency('EUR')
)
# SmartCurve: the object's own CURVE field, scaled by a formula -- note the
# base id is 'AAA.PYTHON-EXAMPLE:CURVE', not just 'CURVE'
smart_curve = types.SmartCurve('AAA.PYTHON-EXAMPLE:CURVE', 'BASE * 1.1', id='SMART_CURVE')
obj = odsl.get('object', 'private', 'AAA.PYTHON-EXAMPLE')
obj['EVENT_CURVE'] = event_curve.data
obj['SMART_CURVE'] = smart_curve.data
odsl.update('object', 'private', obj)
EventTimeSeries and SmartTimeSeries work the same way:
event_timeseries = (
types.EventTimeSeries('AAA.PYTHON-EXAMPLE:READINGS', 'value', id='EVENT_TIMESERIES', calendar='DAILY', start='2026-08-20')
.set_name('Time series built from READINGS events')
)
smart_timeseries = (
types.SmartTimeSeries('AAA.PYTHON-EXAMPLE:TIMESERIES', 'BASE * 2', id='SMART_TIMESERIES', calendar='DAILY')
.set_name('Smart time series: TIMESERIES doubled')
)
See smart-types-example.py for the full walkthrough, and each class's docstring in odsl/types.py for the rest of their setters.