Oninit® UDR — TimeSeries API: Configuration
The YAML mapping that tells oni_ts_read()
which logical metric names map to which physical TimeSeries columns, and
the SQL admin surface that loads, validates, and reloads it without
restarting the instance.
The mapping
One YAML document defines named sources (one per table/TimeSeries pair) and a flat metrics map that assigns each logical metric name to a source and a physical column:
version: 1
timezone: UTC
sources:
host_metrics:
database: sensordb
table: host_metrics
timeseries: ts_data
key_column: host_id
metrics:
cpu.usage:
source: host_metrics
column: col0
cpu.system:
source: host_metrics
column: col1
cpu.wait:
source: host_metrics
column: col3
A source's key_column is the integer primary key column
the Read API's p_key is looked
up against, and timeseries is that table's TimeSeries
column — both live here, in configuration, never as arguments to
oni_ts_read() itself. The mapping is one-to-one within a
source (one logical metric per physical column and vice versa); no
aliases.
database is mandatory on every source — a request
resolves entirely within its source's database, since tables, TimeSeries
objects, and extended type IDs are per-database.
One YAML per database
Each database has its own YAML file, and a session reads the file for the database it is connected to. The path is the first of these that applies:
$ONI_TS_YAML_PATH, if set — one explicit path used by every database;$INFORMIXDIR/etc/oni_ts.<dbname>.yaml, if that file exists (the database name may contain only letters, digits,_and-);$INFORMIXDIR/etc/oni_ts.yaml.
Every source in a database's file must name that same database. A file
that names another database fails validation with
source '<name>': database '<x>' is not the connected
database '<y>' before any catalog check, and nothing is
created. The cache lives in one instance-wide shared-memory block that
holds one slot per database (up to 8). Start, reload, validate, read and
write act only on the connected database's slot, so reloading
analytics never touches the entries for another database.
oni_ts_abort() is the exception: it cancels in-flight reads
in every database. oni_ts_status() reports the connected
database's slot and its YAML path.
Checking a mapping from SQL
Neither the Read API nor
the Write API ever takes a table name, so
debugging a metric that isn't behaving as expected usually means asking
what it actually resolves to. oni_ts_resolve_metrics() is a
read-only admin call that answers that directly, without reading the
deployed YAML file or touching any actual TimeSeries data:
SELECT * FROM TABLE(oni_ts_resolve_metrics('cpu.usage,cpu.wait'));
-- metric source database table_name timeseries key_column column_name datatype
-- cpu.usage host_metrics sensordb host_metrics ts_data host_id col0 float
-- cpu.wait host_metrics sensordb host_metrics ts_data host_id col3 float
It returns a real Informix LIST collection, one row per
requested metric — TABLE() flattens that straight into
ordinary named columns, no JSON parsing or dot-notation required. An
unknown metric name is a hard error, same as
the Read API's own p_metrics.
Unlike oni_ts_read(), a request here isn't restricted to one
source — metrics from different sources can be checked in the same
call, since this only reads the already-loaded configuration cache and
never opens a TimeSeries at all.
Loading and reloading
Loaded once at cold start, and reloadable without a restart:
EXECUTE PROCEDURE oni_ts_start(yaml_text); EXECUTE FUNCTION oni_ts_yaml_validate(); EXECUTE PROCEDURE oni_ts_yaml_reload(mode); -- 'abort' | 'wait' | 'flush' EXECUTE PROCEDURE oni_ts_abort(); EXECUTE FUNCTION oni_ts_abort_status(); EXECUTE FUNCTION oni_ts_status();
oni_ts_start(yaml_text) takes the YAML as an
LVARCHAR argument, which truncates at 2048 bytes. A larger
document loads from the database's YAML file through
oni_ts_yaml_reload(), which reads the file itself.
oni_ts_read() deliberately never builds a cache on its own
from an unspecified YAML source — a cold cache is a clear, hard
error telling the caller to run oni_ts_start() first, not a
guess at what config might have been intended.
The three reload modes trade off how a pending config change interacts with in-flight reads:
abort— cancel in-flight reads on the old generation immediately, cut over now.wait— let in-flight reads finish on the old generation first, then cut over.flush— force an immediate cutover regardless of in-flight work.
Status
oni_ts_status() returns one named ROW, not
formatted text, covering the active/pending config generation, reload
state, and the last validation/reload result — scriptable without
parsing output meant for a human.
Verified against a real instance
The YAML cache and its reload lifecycle — cold start, validation,
all three reload modes, abort — have been built and exercised
against a live, running IBM Informix Dynamic Server instance, end to end.
oni_ts_resolve_metrics() was verified the same way: correct
resolution against a real fixture, a clean rejection for an unknown
metric name, and confirmation that neither the success nor any error
path ever leaves server-side request state stuck.