Query endpoint
You are currently looking at a work in progress version of the Relynk API documentation. Consider the underlying APIs and messaging formats as stable, but we strive to make the documentation as developer friendly as possible. If you feel anything is missing please reach out to hello@relynk.io, any feedback would be much appreciated.
Relynk's core feature is its point data (sensor data), and the '/query' API endpoint is the primary way to access it. This guide will explain the query endpoint and show you how to effectively retrieve the data you need. We will first go over the endpoint's schema and then provide examples of common use cases.
Prerequisites
This guide assumes you are familiar with our data model and Real Estate Core. If you are not, please refer to the following documentation: Data Model and Real Estate Core.
Accessing the Query Endpoint
To create a query, you need to make a POST request to '/query' with a JSON body containing the query parameters. The JSON body must follow the structure defined below:
The query endpoint will return a maximum of 2,000 records at a time. If you need to retrieve more records, you will need to use the 'limit' and 'offset' parameters to split your query into multiple requests, please refer to Retrieving Large Amounts of Data for more information.
By default, the query endpoint returns data ordered by time in descending order, meaning the first returned record will be the most recent one in the database.
Filtering Data
Initially the query will include all point data in Relynk. You can use filters to narrow down the data returned by your query. Filters are structured as a list of objects, with each object representing a filter. Each filter has the following structure:
To create a filter, you need to specify the 'filter_on' parameter, which defines the type of filtering you want to do, and the 'values' list, which specifies the values you want to filter on. If you specify multiple values, the query will return data that matches any of them.
You need to specify at least one 'filter_on' parameter, and at least one value.
If you filter on 'resource_id', the query will also include all child resources of the resource you are filtering on. For example, if you filter on a level, the query will also return data for all the rooms on that level.
Grouping Data
The 'group_on' parameter allows you to group the data by a particular field. For example, if you filter on a level and want to get data for every room on that level, you would specify 'group_on' as 'https://w3id.org/rec#Room'. This will return data grouped by room, only for rooms that are children of the level you filtered on.
If you do not supply any 'group_on' value then every point and unit will be returned with no grouping. Useful if you would like to export all point data.
When a grouping contains multiple data points, the API will provide aggregations of all the data points within that group. The aggregations include the time weighted average, average, count, sum, minimum, and maximum values of the data points within the group.
Moreover, the specific values assigned to the returned data points can vary based on the chosen grouping. If you group by resource type, such as 'https://w3id.org/rec#Room' or 'https://w3id.org/rec#Level', the values 'group_resource_id,' 'group_resource_name,' and 'group_resource_type' will be populated. Conversely, if you group by any other criterion, the values 'group_point_id' and 'group_point_name' will be populated instead.
The following 'group_on' values are supported:
Understanding Resolution
The resolution parameter is used in conjunction with the concept of 'time buckets'. A time bucket is a time period that is used to group data together. For example, if you have a time bucket of 1 hour, then all data points that fall within that hour will be grouped together. The 'resolution' parameter is used to specify the size of the time buckets.
When used in combination with the 'group_on' parameter, the API endpoint will group the data by the 'group_on' parameter, and by the resolution parameter.
The following resolutions are supported:
Retrieving Timeseries Data
The 'is_timeseries' parameter defines whether the returned data should be in timeseries format or not. If 'is_timeseries' is set to true, the data will be returned in timeseries format in time buckets based on the 'resolution' parameter. If not, the API will aggregate all the data down to a single datapoint per group.
If 'only_latest_value' is set to true then the 'is_timeseries' parameter is ignored.
Retrieving the Latest Value Only
The 'only_latest_value' parameter allows you to retrieve only the latest value for each group. This can be useful when you only need the most recent value for each room, for example. When set to true, the result will only contain one data point per group for each measurement, rule or unit matching the specified filters.
Specifying a Time Period
The 'from' and 'to' parameters allow you to specify a time period for your query. You can use none, one, or both of these parameters. If you do not specify any, the API will not filter the data based on time.
The time must be specified in ISO 8601 format, for example '2021-01-01T00:00:00.000Z' or '2021-01-01T00:00:00.000+01:00' to include your time zone.
Retrieving Large Amounts of Data
As mentioned before, by default the API will return a maximum of 2,000 records at a time. If you need to retrieve more records, you will need to use the 'limit' and 'offset' parameters to split your query into multiple requests.
The 'limit' parameter defines how many records you want to retrieve, and the 'offset' parameter defines how many records you want to skip.
When splitting a query into multiple requests, make sure that all other parameters in the query remain the same.
For example, the first request would have 'limit' set to 2000 and 'offset' set to 0. The second request would have 'limit' set to 2000 and 'offset' set to 2000. Once the number of records returned is less than the specified 'limit', you have reached the end of your query.
Return data value format
Below is an example of the data returned by the query endpoint. The data is returned in a list of objects, with each object representing a data point.
There are multiple fields representing the value of the point: The raw value, 'value' and the aggregated fields 'average_value', 'time_weighted_average_value', 'count_value', 'sum_value', 'min_value' and 'max_value'. Depending on the configuration of the query, some of these fields may be empty. Below are the rules that dictate which fields are populated:
- If "is_latest_value" is set to true, only the "value" field will be populated.
- If "is_timeseries" is set to true and the resolution is not set to "raw", only the aggregated fields will be populated.
- If "is_timeseries" is set to true and the resolution is set to "raw", only the "value" field will be populated.
- If "is_timeseries" is set to false and "is_latest_value" is set to false, only the aggregated fields will be populated.
Example Query Payloads
Here are a few examples of how you can use the Query API endpoint to retrieve point data in Relynk:
Retrieving the Latest Temperature Readings of All Rooms on a Level
The following query retrieves the latest temperature readings of all rooms on a level with id 'b5bada34-ae4e-488c-8edc-1e1daa0621ed':
{
"filters": [
{
"filter_on": "resource_id",
"value": [
"b5bada34-ae4e-488c-8edc-1e1daa0621ed" // This is the resource id of the level
]
},
{
"filter_on": "point_subtype",
"value": ["https://brickschema.org/schema/Brick#Temperature_Sensor"]
}
],
"group_on": "https://w3id.org/rec#Room",
"resolution": "1 hour", // This is ignored because only_latest_value is set to true
"is_timeseries": true, // This is ignored because only_latest_value is set to true
"only_latest_value": true
}
Retrieving the Average Humidity of All points in a Building
The following query retrieves the average humidity of all points in a building with resource_id of '7f47b79f-539e-401f-9261-12b63c772a78' on January 1st, 2023 between 08:00 and 16:00 in the +01 timezone:
{
"filters": [
{
"filter_on": "resource_id",
"value": [
"7f47b79f-539e-401f-9261-12b63c772a78" // This is the resource id of the building
]
},
{
"filter_on": "point_subtype",
"value": ["https://brickschema.org/schema/Brick#Relative_Humidity_Sensor"]
}
],
"group_on": "https://w3id.org/rec#Building",
"resolution": "1 hour", // This is ignored because is_timeseries is set to false
"is_timeseries": false,
"only_latest_value": false,
"to": "2023-01-01T08:00:00.000Z+01:00",
"from": "2023-01-01T16:00:00.000+01:00"
}
Retrieving Room Occupancy over Time
The following query retrieves the presence of a room with id 'a1f066a4-a336-4937-8bd8-103e034cb2af' over time at a 1 hour resolution:
{
"filters": [
{
"filter_on": "resource_id",
"value": [
"a1f066a4-a336-4937-8bd8-103e034cb2af" // This is the resource id of the room to get presence from
]
},
{
"filter_on": "point_subtype",
"value": ["https://brickschema.org/schema/Brick#Occupancy_Sensor"]
}
],
"group_on": "Room",
"resolution": "1 hour",
"is_timeseries": true,
"only_latest_value": false
}
Conclusion
You can use the examples above as a guide to understand how to structure your query payloads to effectively retrieve point data using the Query API endpoint in Relynk. Remember to use filters, grouping, and resolution to effectively retrieve the data you need, and use the 'is_timeseries', 'only_latest_value', 'to' and 'from' and 'limit' and 'offset' parameters as appropriate.
View the full Query API Reference here API Reference - Query Endpoint