diff --git a/docs/tutorials/auto-provision-devices-at-scale.md b/docs/tutorials/auto-provision-devices-at-scale.md new file mode 100644 index 00000000..388afe58 --- /dev/null +++ b/docs/tutorials/auto-provision-devices-at-scale.md @@ -0,0 +1,59 @@ +--- +sidebar_position: 8 +--- + +# Auto-provision and onboard OEM devices at scale + +If you build and distribute your own hardware, you do not want to register every unit by hand. This tutorial shows how **auto-provisioning** lets a device **self-register** the first time it connects: OpenRemote authenticates it, creates an **asset** of the type you defined, and links its **attributes** to the right MQTT topics — true **zero-touch device onboarding**. + +:::tip Why this matters for OEMs and integrators +Provisioning in OpenRemote creates the client credentials **and** the digital asset **and** the attribute links in a single flow, included in the open-source core. That means a freshly flashed device becomes a fully modelled, queryable asset the moment it powers on in the field. +::: + +## Prerequisites + +- A running OpenRemote instance — see the [Quick Start](https://docs.openremote.io/docs/quick-start). +- Superuser access to a realm where your devices will live. +- A device (or test client) that can do MQTT over TLS with an X.509 client certificate — for example an ESP32/ESP8266. + +## Step 1 — Define the asset type your device represents + +Decide what each device *is* in your model (e.g. a `Thing`, or a custom `EnvironmentSensor` asset type from a custom project). The provisioning flow will create one asset of this type per device, so model the attributes you want populated (temperature, humidity, battery, etc.). + +## Step 2 — Create a provisioning configuration + +1. Go to the **Provisioning** configuration for your realm (Manager UI). +2. Create an **X.509 provisioning config** and paste the **CA certificate** that signed your device certificates. +3. Select the **asset type** to create per device and set the realm. +4. Choose whether to **auto-link attributes** to standard MQTT topics and whether newly provisioned assets are **disabled until approved** (useful for a manufacturing QA gate). + +See [Auto provisioning devices and users](https://docs.openremote.io/docs/user-guide/gateways-and-devices/auto-provisioning) for the message format and the full configuration reference. + +## Step 3 — Flash devices with a unique certificate + +Each unit ships with a unique client certificate signed by your CA. The device's unique ID (for example a serial number embedded in the certificate's common name) becomes the identity OpenRemote uses to create and name the asset. + +## Step 4 — Let the device provision itself + +On first connection the device publishes a provisioning request to the provisioning topic. OpenRemote validates the certificate against your CA, then: + +1. Creates the asset of your chosen type (if it does not already exist). +2. Links its attributes to the device's publish/subscribe topics. +3. Returns the asset ID so the device can start publishing telemetry immediately. + +For a concrete firmware example, follow [Connect ESP32 or ESP8266 using MQTT](https://docs.openremote.io/docs/user-guide/gateways-and-devices/connect-esp32-or-esp8266-using-mqtt), then point it at your provisioning config instead of a manually created service user. + +## Step 5 — Verify and scale + +1. Power on one device and confirm a new asset appears in the asset tree with live values. +2. Power on a second unit with a different certificate and confirm a second, separate asset is created. +3. Roll out the remaining fleet — no manual asset creation required. + +:::note +Combine this with [multi-tenant realms](./white-label-multi-tenant-iot-platform) so each customer's devices provision straight into that customer's realm. +::: + +## Next steps + +- Keep field devices current with [OTA firmware updates using hawkBit](./ota-firmware-updates-with-hawkbit). +- Deploy a local [edge gateway with a secure tunnel](./edge-gateway-secure-tunnel) for sites with intermittent connectivity. diff --git a/docs/tutorials/change-celsius-to-fahrenheit-with-flow.md b/docs/tutorials/change-celsius-to-fahrenheit-with-flow.md index e38c0552..41573d7a 100644 --- a/docs/tutorials/change-celsius-to-fahrenheit-with-flow.md +++ b/docs/tutorials/change-celsius-to-fahrenheit-with-flow.md @@ -1,10 +1,16 @@ --- -sidebar_position: 4 +sidebar_position: 11 --- # Celsius to Fahrenheit with Flow -An example for converting an attribute value, using the Flow editor is the conversion from temperature Celsius into Fahrenheit. +This tutorial offers an example for converting an attribute value, using the Flow editor. This example describes the conversion from temperature Celsius into Fahrenheit. + +## Prerequisites + +- A running OpenRemote instance — see the [Quick Start](https://docs.openremote.io/docs/quick-start). + +## Step 1 — Create a new attribute First of all create the attribute you want to show the temperature in Fahrenheit. Note that you have to add the configuration item “Rule state” to be able to use it in the flow editor. In the example we also: @@ -15,6 +21,8 @@ First of all create the attribute you want to show the temperature in Fahrenheit ![Add Fahrenheit attribute](img/flow-new-attribute-for-flow.png) +## Step 2 — Create the flow rule + Next create a flow in the flow editor, which looks like this: ![Flow from Celsius to Fahrenheit](img/flow-celsius-to-fahrenheit.png) diff --git a/docs/tutorials/configure-mobile-app-behaviour.md b/docs/tutorials/configure-mobile-app-behaviour.md index 57a596c1..36178a2f 100644 --- a/docs/tutorials/configure-mobile-app-behaviour.md +++ b/docs/tutorials/configure-mobile-app-behaviour.md @@ -1,5 +1,5 @@ --- -sidebar_position: 5 +sidebar_position: 12 --- # Configure mobile app behaviour @@ -32,7 +32,7 @@ This file has the following structure } ``` -## Domain +## Step 1 - Domain The domain must always be manually entered by the user. Users can enter: - a full URL (e.g. https://myapp.example.com), with optional port @@ -40,7 +40,7 @@ The domain must always be manually entered by the user. Users can enter: - an IP address, with or without scheme (e.g. 192.168.1.1) - a simple domain (string with no dot in name), the URL used is then https://_domain_.openremote.app -## App +## Step 2 - App By default, the system discovers the available apps and presents them to the user as a list for selection. If there's only one available app, it's automatically selected and no option is presented to the user. @@ -76,7 +76,7 @@ In this case, even if only one application is available, it is not automatically You can also specify the app to be used and forbid selection by the user (the app selection option is never presented). Customize the `console_config.json` file, setting the `app` field to the name of the app you want to be used. -## Realm +## Step 3 - Realm As for apps, by default, the console presents the user with a list of possible realms for selection. If there's only one available realm, it's automatically selected and no option is presented to the user. @@ -101,7 +101,7 @@ For example If you don't want the console to present a list of available realms, you can force the user to manually enter the realm name in a text field. Customize the `console_config.json` file, setting the `showRealmTextInput` to `true`. -## Providers +## Step 4 - Providers For example ```json diff --git a/docs/tutorials/connect-modbus-devices.md b/docs/tutorials/connect-modbus-devices.md new file mode 100644 index 00000000..cb36ed69 --- /dev/null +++ b/docs/tutorials/connect-modbus-devices.md @@ -0,0 +1,58 @@ +--- +sidebar_position: 5 +--- + +# Connect Modbus TCP/RTU devices (PLCs, meters, inverters) + +**Modbus** is everywhere in industrial and energy hardware — PLCs, energy meters, solar inverters, HVAC controllers. This tutorial shows how to connect Modbus devices to OpenRemote running as a gateway, using the **native Modbus agent**, mapping registers straight onto **asset attributes** over Ethernet (**Modbus TCP**) or serial (**Modbus RTU**). + +:::tip Why this matters for OEMs and integrators +The Modbus agent runs **inside the OpenRemote Manager** — there is no separate gateway application to deploy and operate just to speak an industrial protocol. The same is true for KNX, and SNMP and more, which keeps your **industrial IoT** architecture simple. +::: + +## Prerequisites + +- A running OpenRemote instance — see the [Quick Start](https://docs.openremote.io/docs/quick-start). +- A reachable Modbus device: a Modbus TCP slave on your network, or a Modbus RTU device on a serial line accessible to the Manager host. +- The device's register map (function code, address, data type, scaling). + +## Step 1 — Create a Modbus agent + +1. On the **Assets** page, click **+** and add a **Modbus TCP Agent** (or **Modbus RTU Agent**). +2. For TCP, set the host/IP and port (default `502`) and the unit/slave ID. +3. For RTU, set the serial port, baud rate, parity and stop bits, and the unit ID. + +See the [Modbus agent reference](https://docs.openremote.io/docs/user-guide/agents-protocols/modbus) for all parameters. + +## Step 2 — Create the asset that represents the device + +Create an asset (e.g. an `ElectricityMeter` or a generic `Thing`) and add attributes for each value you want to read or write — for example `power` (number), `voltage` (number), `relayState` (boolean). + +## Step 3 — Link attributes to Modbus registers + +For each attribute, add the **Agent Link** configuration item and select your Modbus agent, then specify: + +- the **register type** (coil, discrete input, input register, holding register), +- the **address**, +- the **data type** (e.g. `INT16`, `UINT32`, `FLOAT32`), +- the **read/write** behaviour and a **polling interval**, +- optional **scaling** to convert raw registers into engineering units. + +:::note +Writing to a holding register or coil lets you actuate the device (e.g. toggle a relay) straight from an attribute write, the Manager UI, the REST API, or a rule. +::: + +## Step 4 — Verify live data + +1. Open the asset and confirm attribute values update on each poll. +2. Check the History panel to confirm values are being stored as time series. +3. Test a write by changing a writable attribute and confirming the device responds. + +## Step 5 — Turn raw values into insight + +Use [Flow rules](https://docs.openremote.io/docs/user-guide/rules-and-forecasting/flow-rules) to derive virtual attributes (e.g. compute energy from power), and [When-Then rules](https://docs.openremote.io/docs/user-guide/rules-and-forecasting/when-then-rules) to alarm on thresholds. + +## Next steps + +- Deploy a local [edge gateway with a secure tunnel](./edge-gateway-secure-tunnel) for sites with intermittent connectivity. + diff --git a/docs/tutorials/connect-your-mqtt-client.md b/docs/tutorials/connect-your-mqtt-client.md index b1e190f3..49dd7fb2 100644 --- a/docs/tutorials/connect-your-mqtt-client.md +++ b/docs/tutorials/connect-your-mqtt-client.md @@ -1,12 +1,12 @@ --- -sidebar_position: 2 +sidebar_position: 3 --- # Connect your MQTT Client In this tutorial we will use the [MQTT API](../user-guide/manager-apis.md#mqtt-api-mqtt-broker) to subscribe to changes of asset attributes values and publish data to them from a MQTT Client. The OpenRemote Manager functions as the MQTT Broker. You can use a desktop MQTT client (e.g. [MQTT Explorer](https://mqtt-explorer.com/) or [MQTT X](https://mqttx.app/)) for this tutorial, or better yet the device you want to connect. -## Create an asset with attributes +## Step 1 - Create an asset with attributes We will create a Thing asset, but feel free to use an AssetType that matches your physical device 1. On the assets page, click the `+` in the asset tree on the left 1. Select the Thing asset type, give it a friendly name and click 'Add' @@ -20,30 +20,30 @@ We will create a Thing asset, but feel free to use an AssetType that matches you - name: `writeAttribute` - Valuetype: `Number` -## Create a service user +## Step 2 - Create a service user The service user will give programmatic access to the MQTT client. 1. Go to the users page and create a new service user (second panel on the page) 2. Name the service user `mqttuser` and give the user the read and write role for the sake of convenience. It is advised to configure a more restricted role for your service users. 3. Click 'Create', a secret will be generated automatically. 4. Open the 'mqttuser' user to see and copy the secret -## Establish a connection from client to broker +## Step 3 - Establish a connection from client to broker In your MQTT client set up a new connection: - host: `mqtt://localhost` (or URL of your hosted environment e.g. demo.openremote.io) - Port: `8883` with TLS/SSL enabled; most clients will work with our self generated Let's Encrypt certificates, but if using a self signed certificate or your client isn't able to validate the cert chain then you may need to explicitly load the cert into your client or disable/relax the client's TLS verification settings (refer to your specific client's documentation). It is possible to expose the broker un-encrypted on port `1883` by creating a port mapping for that on the `manager` service in your Docker Compose file - password: the secret generated for the MQTT service user (you can find it on the mqttuser users page) - username: `master:mqttuser` (`{realm}:{user}`) -- clientID: `client123` (this can be anything you like but must be unique - Any existing connection with the same client ID will be replaced. Make sure this clientID remains identical.) +- clientId: `client123` (this can be anything you like but must be unique - Any existing connection with the same client ID will be replaced. Make sure this clientId remains identical.) -## Subscribe to attributes using the MQTT API +## Step 4 - Subscribe to attributes using the MQTT API In this tutorial we will be looking at specific attributes of a specific asset. There are [many more options](../user-guide/manager-apis.md#mqtt-api-mqtt-broker) of subscribing to (all) updates of assets and attributes. The asset attributes that you will be subscribing to can be written by the user, by rules, or can be a live value gathered through an Agent link with another device in the field. You can imagine this boolean value could toggle a function of the device subscribed to the attribute 1. Get the ID of the Thing asset by navigating to its asset page and copying the ID in the URL (e.g. `http://localhost:9000/manager/#!assets/false/6xIa9MkpZuR7slaUGB6OTZ` => `6xIa9MkpZuR7slaUGB6OTZ`) 2. Create a subscription for the subscribeAttribute in your MQTT client with the topic: `{realm}/{clientId}/attribute/{attributeName}/{assetId}`. So in our case this will be `master/client123/attribute/subscribeAttribute/6xIa9MkpZuR7slaUGB6OTZ` 3. In the view mode of the Thing asset in the OpenRemote Manager, write a new value to the 'Subscribe attribute' by clicking the checkbox. 4. Verify that you see the value (`true`/`false`) coming in on your MQTT client! -## Publish attribute values from the MQTT client +## Step 5 - Publish attribute values from the MQTT client You can publish data from your MQTT client (device) to the OpenRemote manager so that you can monitor the device and create rules. -1. Define the correct topic. For directly writing an attribute value: `{realm}/{clientID}/writeattributevalue/{attributeName}/{assetID}`. So in our case this will be `master/client123/writeattributevalue/writeAttribute/6xIa9MkpZuR7slaUGB6OTZ` +1. Define the correct topic. For directly writing an attribute value: `{realm}/{clientId}/writeattributevalue/{attributeName}/{assetId}`. So in our case this will be `master/client123/writeattributevalue/writeAttribute/6xIa9MkpZuR7slaUGB6OTZ` 2. Send the JSON over this topic. For a Number, this is really simple: `23` 3. Go to the Manager and check if the value updated! diff --git a/docs/tutorials/edge-gateway-secure-tunnel.md b/docs/tutorials/edge-gateway-secure-tunnel.md new file mode 100644 index 00000000..caacc0f2 --- /dev/null +++ b/docs/tutorials/edge-gateway-secure-tunnel.md @@ -0,0 +1,47 @@ +--- +sidebar_position: 7 +--- + +# Deploy OpenRemote as an edge gateway with a secure tunnel + +For sites with intermittent connectivity, local control loops or data-residency requirements, you want compute at the edge. This tutorial shows how to run OpenRemote as an **edge gateway**, link it to a **central** instance, and **remotely access** the on-site gateway through a **secure tunnel** — a hybrid **on-premise** plus cloud architecture. + +:::tip Why this matters for integrators +The edge gateway is the **same OpenRemote codebase** running on-site, so an instance can act as both server and gateway — the asset model, agents and rules you already know run locally too. Gateway UIs can be reached from the central instance over a secure tunnel for remote maintenance. +::: + +## Prerequisites + +- Two OpenRemote instances: a **central** instance and an on-site **edge** instance (both from the [Quick Start](https://docs.openremote.io/docs/quick-start) / Docker images; `amd64` and `arm64` are supported, so the edge can run on small hardware). +- Network access from the edge instance out to the central instance. +- Read [OpenRemote as Edge Gateway](https://docs.openremote.io/docs/user-guide/gateways-and-devices/edge-gateway). + +## Step 1 — Run OpenRemote on the edge + +Deploy a standard OpenRemote instance on the on-site hardware. Connect your local devices to it using whichever agents fit — [Modbus](./connect-modbus-devices), [KNX](../user-guide/agents-protocols/knx), MQTT, Z-Wave, etc. The edge instance keeps working and storing data even if the uplink drops. + +## Step 2 — Register the gateway on the central instance + +1. On the **central** Manager, create a **Gateway** asset/connection for the site. +2. This issues credentials the edge instance uses to authenticate its outbound connection. + +## Step 3 — Connect the edge to the central instance + +Configure the edge instance with the central instance's address and the gateway credentials. Once connected, the site's assets become visible and manageable from the central instance, while continuing to run locally. + +## Step 4 — Remotely access the gateway UI via the secure tunnel + +Open the gateway's local UI from the central instance through the **secure tunnel**, so field engineers can configure and troubleshoot a site without a site visit or a public inbound port. Follow the tunnel setup in [OpenRemote as Edge Gateway](https://docs.openremote.io/docs/user-guide/gateways-and-devices/edge-gateway). + +:::caution +Restrict who can open tunnels and access gateway UIs using [roles and restricted users](./enterprise-identity-sso-rbac); remote access to field equipment should be tightly scoped. +::: + +## Step 5 — Decide what runs where + +Keep latency-sensitive control and local automation in [edge rules](https://docs.openremote.io/docs/user-guide/rules-and-forecasting/create-rules), and use the central instance for cross-site dashboards, fleet-wide rules and long-term analytics. + +## Next steps + +- Push [OTA firmware updates](./ota-firmware-updates-with-hawkbit) to devices behind the gateway. +- Onboard edge devices automatically with [auto-provisioning](./auto-provision-devices-at-scale). diff --git a/docs/tutorials/enterprise-identity-sso-rbac.md b/docs/tutorials/enterprise-identity-sso-rbac.md new file mode 100644 index 00000000..1a481909 --- /dev/null +++ b/docs/tutorials/enterprise-identity-sso-rbac.md @@ -0,0 +1,64 @@ +--- +sidebar_position: 6 +--- + +# Enterprise identity — SSO, RBAC and OAuth2 + +How does our platform handle **identity and access**? This tutorial covers the essentials: **single sign-on (SSO/OIDC)** through the built-in **Keycloak**, linking to **Active Directory/LDAP**, **role-based access control (RBAC)** with realms and restricted users, and **OAuth2 service accounts** for headless device and machine access. + +:::tip Why this matters for enterprise users +Industry-standard identity is built into the open-source core: Keycloak-based authentication, fine-grained roles, restricted (per-asset) users, federated SSO and OAuth 2.0 service users — no separate edition required to satisfy an enterprise security review. +::: + +## Prerequisites + +- A running OpenRemote instance — see the [Quick Start](https://docs.openremote.io/docs/quick-start). +- Superuser access; ideally a [tenant realm already created](./white-label-multi-tenant-iot-platform). +- For SSO/AD: access to your identity provider (Microsoft Entra ID/AD, Google, Okta, or any OIDC/SAML IdP). + +## Step 1 — Understand the access model + +OpenRemote separates concerns into: + +- **Realms** — isolated tenants (see the [white-label tutorial](./white-label-multi-tenant-iot-platform)). +- **Roles** — what a user can do (read, write, configure, manage users, etc.). +- **Restricted users** — users who can only see the specific assets linked to them (device- or customer-level access control). + +## Step 2 — Create roles and assign users + +1. Go to the **Users** page in your realm. +2. Create users and assign **roles** appropriate to their job (for example a read-only "viewer" vs a "configurator"). +3. For end customers who should only see their own equipment, mark them **restricted** and link the relevant assets to them. Also add the configuration item 'restricted access read/write' to the attributes you want the restricted user to see. + +## Step 3 — Enable single sign-on (SSO) + +Because identity is managed by Keycloak, you can federate to an external Identity Provider: + +1. Open the Keycloak admin console for your realm. +2. Add an **Identity Provider** (OIDC or SAML) for your IdP and map claims/roles. +3. Users now sign in with corporate credentials; access maps to OpenRemote roles automatically. + +To synchronise users/groups from a directory, follow [Linking to Active Directory](https://docs.openremote.io/docs/user-guide/identity-and-security/linking-to-active-directory). + +## Step 4 — Create OAuth2 service users for devices and integrations + +For headless access (a device, a backend service, a CI job) create a **service user**: + +1. On the **Users** page, add a **service user** (e.g. `integration-svc`). +2. Grant it the minimum roles it needs (prefer least privilege over the convenience of full read/write). +3. Use its client ID/secret with standard **OAuth 2.0** to obtain tokens for the REST, WebSocket or MQTT APIs. + +:::caution +Give each device or integration its own service user with a narrow role, so you can revoke one without affecting the rest. +::: + +## Step 5 — Verify + +1. Sign in via your IdP and confirm the SSO flow and resulting roles. +2. Log in as a restricted user and confirm they see only their linked assets. +3. Obtain a token for the service user and call a [REST API](https://docs.openremote.io/docs/category/rest-api) endpoint. + +## Next steps + +- Use these service users in the [MQTT/auto-provisioning](./auto-provision-devices-at-scale) flow. +- Apply per-tenant branding in the [white-label, multi-tenant tutorial](./white-label-multi-tenant-iot-platform). diff --git a/docs/tutorials/open-weather-api-using-http-agent.md b/docs/tutorials/open-weather-api-using-http-agent.md index 0848f609..443b122a 100644 --- a/docs/tutorials/open-weather-api-using-http-agent.md +++ b/docs/tutorials/open-weather-api-using-http-agent.md @@ -1,17 +1,21 @@ --- -sidebar_position: 1 +sidebar_position: 2 --- -# Weather data using HTTP Agent +# Using HTTP Agent for weather service -This tutorial explains how to connect to the [Open Weather Map](https://openweathermap.org/) API using the [Http Agent](../user-guide/agents-protocols/http) and is based on the basic environment described in the quick start. +This tutorial explains how to use the generic [HTTP Agent](../user-guide/agents-protocols/http) with an example to connect to the [OpenWeatherMap](https://openweathermap.org/) API. + +:::note +If you specifically want to connect to OpenWeatherMap, you can use the dedicated [OpenWeatherMap Agent](../user-guide/agents-protocols/openweathermap). +::: ## Prerequisites * A running Open Remote instance (this tutorial assumes `https://localhost`) * A free API key for the [Open Weather Map](https://openweathermap.org/) API -## Create the Agent +## Step 1 - Create the Agent 1. Login to the manager UI (`https://localhost/` `admin/secret`) 2. Navigate to the Assets page and click the `+` at the top of the Asset list on the left to add an Agent or Asset. 3. In the dialog do the following: @@ -31,7 +35,7 @@ This tutorial explains how to connect to the [Open Weather Map](https://openweat You now have a basic HTTP API protocol ready to be linked to by asset attributes. -## Create the weather asset +## Step 2 - Create the weather asset Now we will create a weather asset where we show the temperature and humidity in Rotterdam that we collect using the OpenWeatherMap API. 1. Click the `+` to add an asset: * Select the asset type from the list: `Weather Asset` @@ -39,7 +43,7 @@ Now we will create a weather asset where we show the temperature and humidity in * Confirm with `Add` The weather asset will now appear in the list as a child of the `HTTP API Agent`. You can change its parent if you wish. -## Add the Agent Links +## Step 3 - Add the Agent Links 1. Go to the modify mode by clicking the toggle at the top of the asset page. In the modify mode you can alter the attributes of an asset and set configuration items. 2. First we will set up the humidity value: * Expand the `humidity` attribute @@ -67,7 +71,7 @@ What this means is that the information can be found at the base URI + `weather` Switch to view mode (top right) to view the live values. You now have the live weather data of Rotterdam linked. -## Setting multiple attributes with one agent link +## Step 4 - Setting multiple attributes with one agent link As you may have noticed we do two calls in the above example, one to get the humidity and one to get the temperature. You can imagine that collecting all the attributes this way, and for several assets, will greatly increase the number of calls you make. This can be optimized by doing one call and extracting all the values you need and pushing them to the attributes of your assets. At the moment `Attribute links` does not have an auto-generated UI, so we'll have to add JSON code. We will recreate the example above using this method. @@ -123,7 +127,7 @@ As you may have noticed we do two calls in the above example, one to get the hum With the attribute link configuration item you filter the values collected with the agent link and push them to the attributes in your specified asset. When you go to view mode you will see the weather data, temperature, and humidity value in their respective attributes. -## Additional Exercises +## Step 5 - Additional Exercises Try and create additional attributes that link to the OpenWeatherMap API, some ideas: * Get temperature in Fahrenheit diff --git a/docs/tutorials/ota-firmware-updates-with-hawkbit.md b/docs/tutorials/ota-firmware-updates-with-hawkbit.md new file mode 100644 index 00000000..3bfd157f --- /dev/null +++ b/docs/tutorials/ota-firmware-updates-with-hawkbit.md @@ -0,0 +1,50 @@ +--- +sidebar_position: 9 +--- + +# Over-the-air (OTA) firmware updates + +Shipping hardware means shipping bugs you will need to fix later. This tutorial shows how to deliver **over-the-air (OTA) firmware updates** to a device fleet using OpenRemote's integration with **[Eclipse hawkBit](https://www.eclipse.org/hawkbit/)** — a dedicated software update server with managed **rollouts** and **campaigns**, not just a file drop. + +:::tip Why this matters for OEMs and integrators +OpenRemote integrates a purpose-built rollout engine (hawkBit) for **device lifecycle management**: staged rollouts, target filtering and update status — so you can patch thousands of deployed devices safely rather than pushing a binary and hoping. +::: + +## Prerequisites + +- A running OpenRemote instance — see the [Quick Start](https://docs.openremote.io/docs/quick-start). +- A hawkBit instance reachable from OpenRemote (can be co-located with your stack). +- Devices whose firmware can poll a hawkBit DDI endpoint and apply an update image. + +## Step 1 — Enable the hawkBit integration + +Configure OpenRemote to connect to your hawkBit server. Once linked, OpenRemote can represent firmware/device-update state on your assets and surface update actions. See [Firmware updating with Hawkbit](https://docs.openremote.io/docs/user-guide/gateways-and-devices/firmware-updating-with-hawkbit) for the supported features and configuration. + +## Step 2 — Register devices as hawkBit targets + +Each device becomes a **target** in hawkBit. Use a consistent target/controller ID (for example the same serial used during [auto-provisioning](./auto-provision-devices-at-scale)) so a device's OpenRemote asset and its hawkBit target line up one-to-one. + +## Step 3 — Upload a software module and distribution set + +1. In hawkBit, create a **software module** containing your new firmware image. +2. Bundle it into a **distribution set** (the versioned package you assign to targets). +3. Tag your targets (for example `region:eu`, `model:v2`, `ring:canary`) so you can roll out by group. + +## Step 4 — Create a managed rollout + +1. Create a **rollout** against a target filter (e.g. start with the `ring:canary` group). +2. Define rollout groups and success/error thresholds so a failing batch pauses the rollout automatically. +3. Start the rollout and watch devices move through *scheduled → running → finished*. + +:::caution +Always start with a small canary group and verify devices come back online and report the new version before rolling out to the whole fleet. +::: + +## Step 5 — Track update status in OpenRemote + +Monitor update progress and firmware version on the device assets in the Manager. Combine this with [rules](https://docs.openremote.io/docs/user-guide/rules-and-forecasting/create-rules) to alert an operator if a device fails to check in after an update. + +## Next steps + +- Trigger update alerts and escalation with [ML Forecasting Service](../user-guide/services/service-ml-forecast). +- Manage on-site devices behind an [edge gateway with a secure tunnel](../user-guide/gateways-and-devices/edge-gateway). diff --git a/docs/tutorials/receive-lorawan-sensor-data-from-chirpstack.md b/docs/tutorials/receive-lorawan-sensor-data-from-chirpstack.md index d479f5c2..26858b52 100644 --- a/docs/tutorials/receive-lorawan-sensor-data-from-chirpstack.md +++ b/docs/tutorials/receive-lorawan-sensor-data-from-chirpstack.md @@ -1,5 +1,5 @@ --- -sidebar_position: 3 +sidebar_position: 4 --- # ChirpStack LoRaWAN Integration diff --git a/docs/tutorials/simulating-data-in-attribute.md b/docs/tutorials/simulating-data-in-attribute.md index 5673b06e..6d035777 100644 --- a/docs/tutorials/simulating-data-in-attribute.md +++ b/docs/tutorials/simulating-data-in-attribute.md @@ -1,5 +1,5 @@ --- -sidebar_position: 6 +sidebar_position: 10 --- # Simulating data in attribute diff --git a/docs/tutorials/white-label-multi-tenant-iot-platform.md b/docs/tutorials/white-label-multi-tenant-iot-platform.md new file mode 100644 index 00000000..b41ccd7e --- /dev/null +++ b/docs/tutorials/white-label-multi-tenant-iot-platform.md @@ -0,0 +1,78 @@ +--- +sidebar_position: 1 +--- + +# White-label your IoT platform with multi-tenant realms + +This tutorial shows how to turn OpenRemote into a **white-label, multi-tenant IoT platform**: you will brand the Manager with your own logo and colours, give each customer (or distributor) their own isolated **realm**, and optionally serve it on a custom domain. This is exactly what device manufacturers (OEMs) and system integrators need when they want to resell an IoT solution under their own brand. + +:::tip Why this matters for OEMs and integrators +White-labeling and multi-tenancy are part of the open-source core of OpenRemote — there is no separate "enterprise" edition or paid add-on to unlock branding, custom realms or role-based access. You can ship a fully branded, multi-customer platform without a per-feature licence. +::: + +## Prerequisites + +- A running OpenRemote instance — see the [Quick Start](https://docs.openremote.io/docs/quick-start). +- Superuser (`admin`) access to the **master** realm. +- Your brand assets: a `logo.png`, a `logo-mobile.png`, a `favicon.png`, and your brand colour hex codes. + +## Step 1 — Create a realm per customer + +Realms are OpenRemote's tenancy boundary: each realm has its own users, assets, agents, rules and branding, fully isolated from the others. + +1. Log in as `admin` and open the **Realms** page from the top-right menu. +2. Click the **+** to add a realm, e.g. `acme`, give it a friendly display name (`ACME Buildings`) and enable it. +3. Repeat for each customer or distributor you want to onboard. + +:::note +The `master` realm is for platform administration. Keep your customers in their own realms so a tenant can never see another tenant's data. +::: + +## Step 2 — Brand the Manager (Appearance settings) + +You can brand each realm independently from the UI. + +1. Switch to the realm you want to brand (realm picker, top-right). +2. Go to **Settings → Appearance**. +3. Upload your **logo**, **mobile logo** and **favicon**, set the **app title** (e.g. `ACME IoT`), and configure the colour variables to match your brand. +4. Configure map defaults, navigation items and default language for that realm. + +For a fully reproducible, version-controlled setup, define the same values in a `manager_config.json` instead: + +```json +{ + "realms": { + "acme": { + "appTitle": "ACME IoT", + "logo": "/images/acme-logo.png", + "logoMobile": "/images/acme-logo-mobile.png", + "favicon": "/images/acme-favicon.png", + "styles": ":host > * {--or-app-color2: #F9F9F9; --or-app-color3: #22211f; --or-app-color4: #1b5630; --or-app-color5: #CCCCCC;}" + } + } +} +``` + +:::caution +By default, superusers (e.g. `admin`) will see styling changes from `manager_config.json`. If you have set `"manager": {"applyConfigToAdmin": false}` then most branding/styling changes will *not* be shown for `admin`. + +To verify per-tenant branding reliably, log in as a normal realm user. + +See [Custom deployment](https://docs.openremote.io/docs/user-guide/deploying/custom-deployment) and the [Appearance page](https://docs.openremote.io/docs/user-guide/manager-ui/appearance) for the full set of options. +::: + +## Step 3 — Serve each tenant on its own domain (optional) + +Point your customer's domain (e.g. `iot.acme.com`) at the Docker host running the OpenRemote stack and set the `OR_HOSTNAME`/proxy configuration. The built-in HAProxy-based reverse proxy provisions TLS/SSL automatically (Let's Encrypt), so each branded tenant is served securely over HTTPS without extra tooling. + +## Step 4 — Verify isolation + +1. Create a test user in the `acme` realm and log in as that user in a separate browser session. +2. Confirm the branded login page, logo and colours appear. +3. Confirm the user can only see `acme` assets — not those of other realms. + +## Next steps + +- Lock down who can see what with [enterprise identity, SSO and RBAC](./enterprise-identity-sso-rbac). +- Let your customers' devices register themselves with [auto-provisioning at scale](./auto-provision-devices-at-scale). +- Build a customer-facing dashboard with the Insights dashboard builder.