Aggregating data from multiple industrial sites centrally means extending the same VPN hub and Modbus-to-MQTT gateway patterns already covered on this site across every site, with a consistent topic naming structure so a single central dashboard and database can distinguish between sites without manual reconciliation. The architecture doesn’t fundamentally change between two sites and twenty, only the discipline around naming and monitoring needs to scale with it.
The problem this solves
A single site’s monitoring setup, covered throughout this site’s other guides, doesn’t automatically become a multi-site setup just by repeating it at each location. Without deliberate planning, the most common failure mode is exactly the one this guide exists to prevent: five sites each running their own isolated MQTT broker and dashboard, with no single place to see all of them together, and no way to compare performance or catch a problem across the whole estate without logging into five separate systems.
The architecture, building on what’s already covered
This pattern combines three pieces already detailed elsewhere on this site, applied consistently across every site rather than once:
- A central VPS running a VPN concentrator, with every site connected in via its own WireGuard tunnel.
- At each site, a Modbus-to-MQTT gateway (or direct MQTT publishing, for devices that already speak it) translating local PLC and sensor data into MQTT messages.
- One central MQTT broker and database on the same VPS as the VPN hub, receiving data from every site over their respective tunnels, with Grafana and InfluxDB providing one dashboard across all of them.
Nothing here is new technology, the value is in deliberately designing for multiple sites from the start rather than discovering the gaps after the fifth site has been bolted on inconsistently.
Topic naming: the single most important decision
A consistent MQTT topic structure, ideally agreed before connecting the second site, is what makes central aggregation actually usable rather than a tangle of inconsistently named data:
site-id/device-type/device-id/measurement
# example:
site3-warehouse/plc/conveyor-2/temperature
This single naming convention enables wildcard subscriptions at exactly the granularity you need: +/plc/+/temperature for every PLC’s temperature reading across every site at once, or site3-warehouse/# for everything at one specific location. Retrofitting this naming scheme after several sites have already been connected inconsistently is real, avoidable work; agreeing it upfront costs nothing.
Handling site-specific differences honestly
Real multi-site deployments rarely have identical equipment everywhere. Different sites often run different PLC manufacturers, different register maps, sometimes genuinely different protocols entirely. The aggregation layer (MQTT topics, the central database) should normalise this: regardless of whether a temperature reading originated from a Modbus register on a 15-year-old PLC or a native MQTT-speaking modern sensor, it arrives at the central broker in the same topic structure and the same units, with any necessary unit conversion or register scaling handled at the site-level gateway, not pushed downstream to whoever’s building the central dashboard.
Database design for multi-site data
In InfluxDB specifically, site identifier is naturally a good candidate for a tag (indexed, used for filtering) rather than a field, since you’ll constantly want to filter or group by site when building dashboards or running queries. A measurement structure like temperature{site="site3-warehouse", device="conveyor-2"} makes “show me this measurement across every site” and “show me everything at one site” both fast, straightforward queries rather than requiring separate databases or complex joins per site.
Monitoring the aggregation layer itself
With multiple sites depending on one central point, monitoring that central point’s health matters more than it would for a single-site setup. Building on the wg show tunnel-health check covered in the VPN concentrator guide, a simple automated check comparing each site’s last-seen MQTT message timestamp against an expected threshold catches a silently disconnected site faster than waiting for someone to notice missing data on a dashboard days later.
Comparing performance across sites
Once data from every site lives in one consistent structure, genuinely useful comparisons become possible that aren’t available with isolated per-site systems: which site has the most equipment downtime this month, which location’s energy usage is trending up, whether a fault pattern at one site is also showing up elsewhere before it becomes a bigger problem there too. This cross-site visibility, not any single technical component, is usually the actual business case for building this pattern properly rather than leaving every site isolated.
Scaling beyond what one central VPS can handle
For most projects on this site, a single, reasonably specified VPS handles dozens of sites without strain, since the actual data volumes involved (industrial telemetry, not video) remain modest even aggregated. If a deployment genuinely outgrows this, splitting the VN concentrator and the database/dashboard layer onto separate VPS instances, communicating over the same internal network, is the natural next step, covered conceptually in VPS for IoT: The Complete Guide‘s discussion of splitting services.
Frequently asked questions
How many sites can realistically be aggregated onto one central VPS?
Dozens comfortably for most industrial telemetry volumes covered on this site; the limiting factor is usually database storage growth over time rather than the live data flow itself, addressed with the retention policies covered in the Grafana/InfluxDB guide.
Does each site need its own dedicated VPN tunnel, or can sites share one?
Each site needs its own WireGuard peer on the hub, covered in the VPN concentrator guide, but they all terminate on the same central VPS rather than needing separate hub infrastructure per site, which is exactly what makes this pattern efficient at scale.
What if two sites use the same device naming by coincidence?
This is precisely why the site identifier belongs at the start of the topic structure, as shown above, every site’s data is namespaced from the start, so identical device names at different sites never collide in the central system.
Can different sites have different polling frequencies or data retention needs?
Yes, this is normal and can be configured per site at the gateway level (polling frequency) and per measurement or tag in InfluxDB’s retention policies, without needing one uniform setting forced across every site regardless of its actual requirements.
Is this pattern overkill for just two or three sites?
Not really, the naming-convention discipline costs nothing extra to apply from the start even at small scale, and it’s considerably easier to establish correctly with two sites than to retrofit once you’re at ten. Building it properly early is cheap insurance against future growth.
A sensible rollout order for adding new sites
Connecting site after site to a growing aggregation hub benefits from a consistent checklist, rather than improvising each time: provision the new site’s WireGuard peer on the hub first and confirm the tunnel connects cleanly in isolation, before connecting any actual industrial equipment through it. Deploy the site’s Modbus-to-MQTT gateway (or confirm native MQTT devices are configured correctly) and verify data arrives at the central broker under the agreed topic naming convention before building or extending any dashboard. Only once data is flowing correctly and consistently should the new site’s data be added to shared, cross-site dashboards, avoiding a half-connected site polluting a view other people are already relying on.
Handling time zones across geographically spread sites
Worth a deliberate decision if sites span more than one time zone: storing all timestamps in UTC at the database level, with Grafana converting to local time for display per viewer, avoids the genuinely confusing alternative of mixed local-time timestamps that make cross-site comparison error-prone. This is usually InfluxDB and Grafana’s default behaviour, but worth confirming explicitly rather than assuming, particularly if any site-level gateway script generates its own timestamps rather than relying on the database to assign them.
What good central visibility actually looks like in practice
The genuine payoff of doing this properly shows up less in any single technical feature and more in a specific kind of question becoming answerable in seconds rather than requiring someone to manually check five separate systems: “which sites are currently reporting normally”, “has this fault pattern appeared at any other location before”, “which site has had the most unplanned downtime this quarter”. These are the questions that justify the upfront discipline of consistent naming and centralised aggregation, not any individual technical component in isolation.
How do I give each site’s local team visibility into just their own data, not every site?
Grafana supports per-dashboard and per-folder permissions, letting you scope a site’s local team to dashboards filtered to their own site tag while a central team retains the full cross-site view, all from the same underlying data without duplicating infrastructure.
Should historical data be kept at the same resolution for every site, or can this vary?
It can vary by site if genuinely needed (a higher-stakes site warranting longer full-resolution retention, for example), configured per measurement or tag in InfluxDB’s retention policies rather than requiring one uniform setting across the whole aggregated dataset.
What’s the disaster recovery story if the central VPS is lost entirely?
Regular snapshots, covered throughout this site’s other guides, are the baseline protection. For genuinely critical multi-site deployments, a documented rebuild process (this site’s guides themselves serve as that documentation for the technical setup) and confirming each site can fall back to local-only operation without the central hub, are both worth confirming work in practice, not just in theory.
Documenting the system for whoever maintains it next
A multi-site aggregation setup, by its nature, becomes infrastructure other people depend on, not just a personal project. Keeping a simple, current record of which sites are connected, their topic naming, and any site-specific quirks (a non-standard PLC register map, an unusual polling interval) pays for itself the first time someone other than the original builder needs to add a new site or troubleshoot an issue, rather than needing to reverse-engineer the system’s conventions from the live configuration alone.
Can this aggregation pattern also pull in data from non-industrial sources, like office building sensors?
Yes, the MQTT-based aggregation pattern doesn’t distinguish between an industrial PLC reading and a building’s smart thermostat data, both just become topics under the same naming convention, useful for organisations wanting one unified view across genuinely different categories of site.
How do I handle a site with significantly worse internet connectivity than the others?
WireGuard’s resilience to connection drops, covered in the VPN concentrator guide, handles intermittent connectivity reasonably gracefully, reconnecting automatically once the link returns. For genuinely poor or expensive connectivity (satellite links, for example), reducing polling and reporting frequency specifically for that site is worth considering to manage bandwidth costs and reduce the volume of catch-up data after a reconnection.
Should every site run an identical software stack, or can they vary?
They can vary in practice, since the aggregation layer only cares that data arrives in the agreed MQTT topic structure, not how each site internally produces it. Standardising where practical reduces maintenance overhead, but isn’t a strict technical requirement of the pattern itself.
Starting the pattern with just two sites
This entire architecture is worth building and proving with two sites before assuming it will work cleanly at twenty. The naming convention, the central database structure, and the dashboard permissions model all benefit from being battle-tested against a real second site’s quirks while the stakes of getting something wrong are still low, rather than discovering a structural problem only after a dozen sites are already depending on the system working correctly, at which point retrofitting a fix touches far more than just the newest connection.
Is there a risk of one site’s data volume overwhelming the central system?
In principle yes, worth applying basic monitoring of message rates per site, covered conceptually earlier in this guide, so an unusually chatty or misconfigured site is caught and addressed rather than silently degrading performance for every other site sharing the same central infrastructure.
A realistic example of this pattern in practice
Consider a facilities management company responsible for refrigeration monitoring across 15 supermarket sites, each with its own local Modbus-to-MQTT gateway feeding temperature data back through the VPN tunnel to a central VPS. Before adopting this pattern, the company’s technicians checked each site’s local display individually during scheduled visits, meaning a fault between visits could go unnoticed for days. After adopting it, one dashboard shows every site’s current status and recent history simultaneously, with automated alerting catching a fault within minutes rather than days, and the naming convention from the start of this guide means a new sixteenth site, when it’s added, follows the exact same pattern as the first fifteen without any special-case handling.
This is a genuinely typical shape for where this architecture earns its keep: not a single dramatic technical achievement, but a steady, compounding improvement in visibility that becomes more valuable with every additional site connected, precisely because the underlying structure was designed for multiple sites from the outset rather than retrofitted awkwardly after the fact.
