Skip to main content

Security model

Security model

Continuum Local runs connector requests and SNMP sweeps inside your network for Blueprintr. Blueprintr decides what to ask for. The agent decides what it will do, by a policy that only its configuration file sets, and treats every job from Blueprintr as untrusted input.

Trust boundaries

PartyRuns whereDecides
Your configuration fileThe agent's hostWhich systems the agent serves, the hosts each may reach, the address ranges it may sweep, and the credentials it uses
The agentA host, container or pod you runWhether each job fits that policy, before a socket opens
BlueprintrBlueprintr's serversWhich requests to propose, and what to do with the answers

The agent dials out and listens on no port. Every exchange starts on your side: it asks Blueprintr for work, runs it locally and posts the result back. The deb, rpm and MSI installs let the agent's own account read config.json but not change it, so a compromised agent process cannot rewrite its own configuration.

What Blueprintr stores

DataWhat it containsWhyWho can see itHow long
Agent recordThe name you gave it, its version, platform, protocol version and capabilities, the integration IDs it serves, its discovery ranges and when it was last seen. A keyed hash of its secret, never the secretTo send each job to an agent that can run it, and to show its statusPeople who can manage Continuum integrations on the organisation or team that owns it. Blueprintr staff who run the service see its name, owner, status, version, platform and capabilitiesUntil you delete the agent. Revoking keeps the record
Enrolment tokenA hash of the tokenTo enrol the agent onceNobody. The token is shown once, when it is createdDeleted 30 days after it is used or expires
Relay jobThe request Blueprintr asked the agent to make, with placeholders where credentials go, and the answer the agent returnedTo pass the answer to the connector that asked for itBlueprintr's servers only. Staff see counts of outcomes, not contentsThe job expires two minutes after it is created, and is deleted at the agent's next poll after that or by Blueprintr's scheduled clean-up
Saved panelThe fields the connector takes from that answer, saved as the tab's snapshotTo show it on the stratumEveryone who can read the blueprint, including anonymous readers, embeds and exports on a public blueprint. NetBox panels are for Blueprint editors unless you choose all Blueprint readers, and Infoblox and Veeam Backup & Replication panels are for Blueprint editors only. The connector reference lists what each panel showsUntil an editor refreshes or removes the tab. Unlinking cannot recall copies already in versions, exports or embeds
Sweep resultsThe devices, ports and links each network sweep finds, and the MAC and IP addresses those devices have learned. Never a device's contact field, or which SNMP credential or version answeredTo show your estate on the sweep results pagePeople who can manage Continuum integrations on the owning organisation or team. Staff see counts only90 days from when a sweep starts. The latest complete sweep from each agent is kept until a newer one completes. Deleting an agent deletes its sweeps
Audit log entriesAgent created, enrolled, renamed, revoked and deleted, tokens issued, sweeps and schedules, and credentials sent or removed: who, with a hash of their IP address and their browser's user agent, which agent, which integration, and the outcome. Never a credentialAccountabilityPeople who can read the organisation's audit log, and the team's for a team's agentWith the rest of the audit log, which does not expire automatically
Download recordWhich file and version you downloaded from the download page, and when, with a hash of your IP address and your browser's user agentTo answer who downloaded which build, for example after an incidentBlueprintr staff who run the service. It is recorded against your account, not the organisation, so it is not in the organisation's audit logWith the rest of the audit log, which does not expire automatically

Deleted rows stay in Blueprintr's database backups for up to 7 days.

Where credentials are kept

Blueprintr never stores a credential for an on-premise system.

CredentialWhere it is kept
Monitoring system credentials you configureconfig.json, or an environment variable or file it refers to (env:NAME, file:/path), or a credentialFile your secret manager writes
SNMP communities and SNMPv3 passphrasesThe discovery block of config.json, or the variables and files it refers to
Credentials sent from BlueprintrThe agent's state directory, one file per integration, mode 0600
The agent's own identity for BlueprintrThe agent's state directory, mode 0600
Access tokens minted by WhatsUp Gold and Veeam Backup & ReplicationThe agent's memory only

The agent does not encrypt these files itself. They are protected by file permissions, so use disk encryption on the host if your policy requires encryption at rest.

For a credential in the agent's configuration, Blueprintr never receives the value. Its request has an unguessable placeholder where the credential goes. The agent fills in the local value and refuses to send the request if any placeholder is left in it. When an answer repeats a credential the agent sent, or a token it kept, the agent replaces it with [redacted] before the answer leaves, in plain, JSON, percent-encoded and form-encoded spellings. Values shorter than six characters are not scrubbed.

Credentials sent from Blueprintr

This is off unless the agent's configuration sets "allowRemoteCredentials": true. When it is on, a credential typed into send credentials takes this path:

  1. From your browser to Blueprintr's web application, over HTTPS.
  2. From the web application to Blueprintr's agent gateway, as an encrypted, single-use message.
  3. From the gateway to the agent, over the agent's open connection to agents.blueprintr.io.
  4. The agent checks it against its own limits and writes it to its state directory.

Nothing on that path writes the credential to a database, a queue or a log. There is nowhere to keep it in the meantime, so the agent has to be online and connected to the gateway at the time, or the send fails and nothing is queued. Where Blueprintr does not offer the gateway, every send is refused as not set up.

The agent applies limits that only its configuration can set:

  • remoteCredentialScope lists the hosts, domain suffixes and address ranges Blueprintr may configure. Addresses are checked again at every connection, against the address the name resolves to at that moment.
  • Loopback, link-local (including 169.254.169.254), unspecified addresses and localhost names are refused unless a cidrs entry in that scope covers them.
  • Certificate settings sent from Blueprintr are refused unless the scope sets allowTlsOverrides. allowWriteOperations is never accepted from Blueprintr.
  • An integration in config.json always wins. Blueprintr can neither replace nor remove it.
  • Credentials sent to an agent are deleted if it is enrolled again as a different agent.

What the agent enforces

Every job is checked before a socket opens:

  • A relay or probe must be for an integration in the agent's configuration, or one sent from Blueprintr, and a relay's provider must match that entry's.
  • A relay's host must be in that integration's allowedHosts, written exactly, with no wildcards, ports or paths. The check runs again after the credential is filled in, and on each of up to three redirects. A redirect to another host drops credential headers, and a request with a credential in its URL or body is not followed to another host.
  • An answer larger than the request allows (8 MB at most) is refused. So is a result larger than one poll to Blueprintr can carry, which is about 1 MB of answer. Both are reported as response_too_large. A relay runs for 10 minutes at most.
  • A sweep reaches only addresses inside discovery.cidrs and outside exclude. An SNMP probe of one device reaches only an address a sweep may reach or a host in the integration's allowedHosts, and a TCP connection test only a host in allowedHosts. An agent with no discovery block sends no SNMP at all.
  • Whatever allowWriteOperations says, a request that sets Host, Transfer-Encoding, Connection, Keep-Alive, Upgrade, TE, Trailer, Expect, Proxy-Connection or HTTP2-Settings, or sets one header twice in different letter case, is refused. The agent writes Content-Length itself.
  • Set-Cookie and Set-Cookie2 headers are removed from every answer, and Blueprintr removes them again before storing a result.

The read-only guard

The allow-list decides where the agent may connect. The read-only guard decides what a request may do there: the agent relays only requests that read, checked for each provider on method, path and, where the product needs it, the query or body. For NetBox, Infoblox, Veeam Backup & Replication and PRTG it accepts only the exact endpoints the connector uses. For SolarWinds, Zabbix, Checkmk, Icinga 2, ManageEngine OpManager and WhatsUp Gold it accepts any read that product's API offers, so give the agent an account that can read only what Blueprintr should see. The rules come from the provider in your configuration, never from the job. Anything else is refused with operation_not_allowed.

Some reads are refused too, because their answers would contain a stored secret: PRTG's getobjectproperty.htm and getpasshash.htm, OpManager operations that name keys, passwords or credentials, NetBox's token and config context endpoints, and Infoblox's credential fields. The guard also refuses a method-override header asking for anything but GET, and a path with encoded slashes, backslashes, encoded dots, path parameters or empty segments.

Setting "allowWriteOperations": true on one integration in config.json lifts the guard for that integration only. The agent logs a warning about it at every start.

The token vault

WhatsUp Gold and Veeam Backup & Replication exchange a username and password for an access token. The agent replaces access_token and refresh_token in that answer with a handle (BPLV_ and 32 hex characters), keeps the token in memory, and puts it back when the handle appears in a later request for the same integration.

  • A handle works only for the integration it was issued for.
  • Tokens are never written to disk. Each expires with the token, after a day at most, and all are lost on restart, after which the connector asks for a new one.
  • Blueprintr can ask for more fields to be kept back, never fewer.
  • An answer the agent cannot fully check for a token is refused with credential_unresolved. A refresh grant is refused.

Certificate checking

ConnectionTrusted rootsTurning checks off
To BlueprintrNode.js's bundled roots, the operating system's store (trustSystemCa, on by default), NODE_EXTRA_CA_CERTS and extraCaFile. apexUrl must be https://The agent has no setting for it
To your systemsThe same, except extraCaFile. An integration with a caFile trusts that file aloneallowInsecureTls or allowPlaintextHttp on one integration, each logged as a warning at every start

The agent adopts a gateway that Blueprintr advertises only when it is https:// on your apexUrl's host or a subdomain of it. The proxy is used for traffic to Blueprintr only, never for connections to your systems, as Proxies describes.

Service hardening

InstallRuns asRestrictions
deb, rpmcontinuum-local, a system account with no login shellconfig.json is root:continuum-local, mode 0640, in a 0750 directory. The systemd unit sets no new privileges, an empty capability set, a read-only filesystem apart from /var/lib/continuum-local (0700), no access to home directories, a private /tmp and devices, protected kernel settings, IPv4, IPv6 and Unix sockets only, restricted namespaces and a 512 MB memory ceiling. Write-execute memory stays allowed, because the JavaScript engine's compiler needs it
Windows MSINT AUTHORITY\LocalServiceC:\ProgramData\Continuum Local has its own access list with no inherited entries: SYSTEM and Administrators have full control, and the service may read config.json but not change it, and write only to state and logs. A first install leaves the service stopped and set to Manual
ContainerThe unprivileged node user (uid 1000)The state directory is 0700. npm, npx, corepack and yarn are removed from the image
Helm chartuid 1000, non-rootRead-only root filesystem, every capability dropped, no privilege escalation, the runtime's default seccomp profile, one replica, and no Service or Ingress

Logs mask every credential and secret reference value the agent loaded, and anything shaped like a placeholder. The agent writes a warning at every start, whatever the log level, for each setting that widens what it may do: write operations, certificate checks off, http://, credentials from Blueprintr with no scope or with certificate overrides, a gateway off your Blueprintr domain, a configuration or credential file others can read, and a CA file that contains a private key.

Supply chain

  • The agent has no runtime dependencies. Its SNMP stack, including SNMPv3 security and DES, is part of the agent, and the bundle is one unminified JavaScript file your team can read.
  • The deb, rpm and MSI include Node.js 24. The build refuses a Node.js archive whose SHA-256 is not pinned in the agent's repository, and the pinned values were checked against the Node.js project's signed checksum list. The Windows service wrapper, WinSW, is pinned by checksum as well. The container image starts from the official Node.js 24 Alpine image, pinned by digest.
  • Every release is signed with Sigstore keyless signing by the agent's release workflow, and recorded in Sigstore's public transparency log. Accept a signature only from that workflow at the version's tag, with the verification commands. SHA256SUMS covers the downloads, and the container image and chart are signed by digest.
  • From 0.2.0, each release also includes a CycloneDX SBOM bound to the bundle by a signed attestation, and the container image's package list and vulnerability scan. A release is not published if that scan finds a critical vulnerability with a fix available.

If Blueprintr were compromised

An attacker in control of Blueprintr could:

  • make the reads each connector's rules allow, to the hosts you listed, with your credentials, and see the answers without the credentials, tokens or cookies in them. A least-privilege, read-only account limits what those answers contain;
  • start sweeps inside your discovery ranges, and SNMP probes there or on hosts you listed, on a UDP port it chooses, with your SNMP credentials, and see the results within the collectors you allow;
  • test TCP connections to hosts in an integration's allowedHosts;
  • with allowRemoteCredentials on, read credentials typed into Blueprintr as they pass through, and configure integrations for any host your scope allows. With no remoteCredentialScope, that is any host except loopback, link-local and unspecified addresses;
  • with allowWriteOperations on an integration, send writes to its hosts;
  • stop sending work, or show you wrong results.

It could not:

  • reach a host outside allowedHosts, discovery.cidrs or your scope;
  • see the credentials in config.json: Blueprintr's requests have placeholders, and the agent scrubs the values it inserted from each answer, in the spellings listed above;
  • see an SNMP community or passphrase, which never appears in a result, or a token the vault keeps;
  • send a write where allowWriteOperations is off, turn it on, or send certificate settings without allowTlsOverrides;
  • change config.json, or replace or remove an integration defined there;
  • widen a sweep, or read ARP, forwarding or contact data through a raw probe when you have turned those collectors off;
  • connect to the agent, redirect its connection to a host outside your apexUrl's domain, upgrade it, or give it code to run. Every job is one of a fixed set of request types.

Reporting a vulnerability

Email [email protected] with "Security: Continuum Local" in the subject. Include the agent version (continuum-local --version), how it is installed, what you found, how to reproduce it and what an attacker gains. Remove credentials, host names and customer data from any proof of concept, and never send a config.json or state file: both contain live credentials.

Blueprintr aims to acknowledge a report within 3 working days and to give its assessment within 10, agrees a disclosure date with you, and credits you in the release notes if you want. Test only against an agent and a Blueprintr account that are yours. Fixes ship as a new release, and only the latest release is supported before version 1.0.