Stream Data Access
Stream data provides access to time-series data stored in CrateDB. While runtime queries retrieve the current state of entities from MongoDB, stream data queries retrieve historical measurements and events recorded over time — such as sensor readings, machine metrics, or energy production values.
Stream Data vs Runtime Queries
| Stream Data | Runtime | |
|---|---|---|
| Purpose | Historical time-series data | Current entity state |
| Storage | CrateDB | MongoDB |
| Key field | timestamp | rtId |
| Typical data | Sensor readings, measurements, events | Entities, configurations, relationships |
| Query root | streamData | runtime |
API Approaches
OctoMesh provides three ways to query stream data:
| Approach | Endpoint | Use Case |
|---|---|---|
| Typed | streamData.[typeName] | Strongly typed queries for a known CK type. Returns typed fields directly. |
| Transient | streamData.transientStreamDataQuery | Ad-hoc queries where columns and filters are specified at request time. |
| Persisted | streamData.streamDataQuery | Execute a saved query definition by its rtId. |
Query Types
| Query Type | Description | Detail Page |
|---|---|---|
| Simple Query | Retrieve raw time-series rows with column selection, filtering, and sorting | Simple Query |
| Aggregation Query | Compute aggregated values (AVG, MIN, MAX, COUNT, SUM) across data points | Aggregation Queries |
| Grouped Aggregation Query | Aggregate values grouped by one or more columns | Aggregation Queries |
| Downsampling Query | Reduce data density by bucketing time ranges with aggregation | Downsampling Query |
All query types are available as both transient (ad-hoc) and persisted (saved) variants.
Typed Query
The streamData query root exposes typed fields for each CK type that has stream data enabled. Field names are derived from the CK type's full name (with dots and slashes removed) in camelCase. For example, the CK type Industry.Energy/EnergyMeter becomes industryEnergyEnergyMeter.
query {
streamData {
industryEnergyEnergyMeter {
items {
rtId
ckTypeId
timeStamp
voltage
}
}
}
}
A response to this query can look like the following:
{
"data": {
"streamData": {
"industryEnergyEnergyMeter": {
"items": [
{
"rtId": "65dc6d24cc529cdc46c84fcc",
"ckTypeId": "Industry.Energy/EnergyMeter",
"timeStamp": "2024-03-21T16:22:47.676Z",
"voltage": 4.04196210149963
},
{
"rtId": "65dc6d24cc529cdc46c84fcc",
"ckTypeId": "Industry.Energy/EnergyMeter",
"timeStamp": "2024-03-21T16:23:50.675Z",
"voltage": -9.00808094383129
}
]
}
}
}
}
Typed queries return attribute values as named fields (e.g., voltage). For more flexible queries where you choose columns at request time, use the transient query approach instead.
Pagination
Stream data queries support cursor-based pagination using the first and after parameters. The first parameter specifies the number of items to return, while after indicates the cursor position to start fetching from.
query {
streamData {
industryEnergyEnergyMeter(first: 2, after: "YXJyYXljb25uZWN0aW9uOjE=") {
pageInfo {
endCursor
hasNextPage
}
items {
rtId
ckTypeId
timeStamp
voltage
}
}
}
}
The response includes pageInfo with endCursor (use as the after value for the next page) and hasNextPage (indicates whether more data is available). The totalCount field is also available on all stream data connections.
Common Parameters
StreamDataArguments
The StreamDataArguments input type is used to specify time filtering and limits when executing queries:
| Field | Type | Required | Description |
|---|---|---|---|
| from | DateTime | No | Start of the time range to query |
| to | DateTime | No | End of the time range to query |
| limit | Int | No | Maximum number of data points to return |
| queryMode | QueryMode | Yes | Query execution mode (use DEFAULT) |
| interval | Seconds | No | Time interval for downsampling |
FieldFilter
Field-level filters allow you to restrict results based on attribute values:
| Field | Type | Required | Description |
|---|---|---|---|
| attributePath | String | Yes | The attribute to filter on |
| operator | FieldFilterOperators | Yes | Comparison operator |
| comparisonValue | SimpleScalar | No | Value to compare against |
Available operators: EQUALS, NOT_EQUALS, GREATER_THAN, GREATER_EQUAL_THAN, LESS_THAN, LESS_EQUAL_THAN, LIKE, NOT_IN, IN, ANY_EQ, ANY_LIKE, MATCH_REG_EX
Sort
| Field | Type | Required | Description |
|---|---|---|---|
| attributePath | String | Yes | The attribute to sort by |
| sortOrder | SortOrders | No | ASCENDING, DESCENDING, or DEFAULT |
Result Structure
All stream data queries return a StreamDataQueryRowDtoConnection with the following structure:
| Field | Type | Description |
|---|---|---|
| totalCount | Int | Total number of matching rows |
| pageInfo | PageInfo | Pagination cursor information |
| items | [StreamDataQueryRow] | The result rows |
Each StreamDataQueryRow contains:
| Field | Type | Description |
|---|---|---|
| rtId | OctoObjectId | The runtime entity this data point belongs to |
| ckTypeId | RtCkTypeId | The CK type identifier |
| timestamp | DateTime | The timestamp of the data point |
| rtWellKnownName | String | Optional well-known name of the entity |
| cells | RtQueryCellDtoConnection | Data values as attributePath / value pairs |
The cells connection is used by transient and persisted queries. Each cell contains an attributePath (the column name) and a value (the data point value). Typed queries return values as named fields directly instead.
Typed queries use timeStamp (capital S) as the field name, while transient and persisted queries use timestamp (lowercase). This difference reflects the underlying data types used by each query approach.
Further Reading
- Simple Query — Query raw time-series data with filtering, sorting, and column selection
- Aggregation Queries — Compute aggregated and grouped values
- Downsampling Query — Reduce data density with time bucketing
- Persisted Queries — Save, manage, and execute reusable query definitions