Observability (APM)

Open Pryv.io v2 ships an optional observability layer that forwards HTTP transactions, datastore calls, and error reports to a third-party Application Performance Monitoring (APM) provider. It is off by default; when enabled it activates a provider-agnostic instrumentation façade with a single concrete provider today: New Relic.

The façade is designed so additional providers (Datadog, OpenTelemetry, Sentry…) can be dropped in later without changes to core business code; new providers land as separate plans.

Data handling note — enabling observability means the operator has decided it is acceptable to ship request metadata (paths, status codes, timings, external host URLs) to the provider’s cloud. Request bodies, authorisation headers and cookies are never forwarded (high-security mode is hard-coded on).

Table of contents

  1. Overview
  2. Enabling New Relic on a cluster
  3. Log-level tuning
  4. Hostname labelling
  5. Rotating the license key
  6. Disabling
  7. Validation queries (NRQL)
  8. Caveats
  9. Adding a new provider later

Overview

Enabling New Relic on a cluster

Prerequisites:

On any core in the cluster, set the license key and enable the provider:

node bin/observability.js newrelic set-license-key <LICENSE_KEY>
node bin/observability.js enable newrelic

Then perform a rolling restart of every core (one at a time, wait until healthy before restarting the next). The agent loads the license key once per process at require() time, so an in-place config change on a running core is a no-op until that core restarts.

Verify:

node bin/observability.js show
enabled:          true
provider:         newrelic
appName:          open-pryv.io (pryv.me)
logLevel:         error
hostname:         core-use1.pryv.me
newrelic licenseKey set: yes

Log-level tuning

Default is error-only: only logger.error() calls reach the provider. info / warn / debug are captured by the usual boiler file + console logs.

Raise verbosity during active debugging:

node bin/observability.js set-log-level warn    # errors + warnings
node bin/observability.js set-log-level info    # errors + warnings + info

Followed by a rolling restart. Higher log levels cost more New Relic events and ship lower-signal chatter; revert to error when the incident is closed.

Hostname labelling

Transactions, infrastructure rows and external segments are labelled with the core’s FQDN, taken from new URL(core.url).hostname. For a typical multi-core deployment that means New Relic shows:

…matching the values operators already see in /reg/hostings and in LE certs. No separate “APM host name” field to curate.

Single-core / DNSless deployments fall back to single.<dns.domain> when core.url is not set.

Rotating the license key

node bin/observability.js newrelic set-license-key <NEW_KEY>

Then a rolling restart of every core. The key is stored AES-256-GCM encrypted in PlatformDB; the CLI’s show command never echoes it.

Disabling

Two ways:

  1. Cluster-wide, via PlatformDB (recommended):

    node bin/observability.js disable
    

    Then rolling restart.

  2. Local kill-switch (emergency): set observability.enabled: false in that core’s override-config.yml. The local override always wins over PlatformDB — useful when one core is misbehaving and you need to silence it immediately without touching cluster state. Restart the affected core only.

Validation queries (NRQL)

Useful queries to paste in the New Relic web console after enabling on a staging cluster:

-- Are my cores showing transactions?
SELECT count(*) FROM Transaction WHERE host LIKE 'core-%.pryv.me' FACET host SINCE 10 minutes ago

-- Is sensitive data being stripped?
SELECT count(*) FROM Transaction WHERE request.headers.authorization IS NOT NULL SINCE 1 hour ago
-- Expected: 0 (high-security mode strips the header)

-- Log forwarding at the current log level
SELECT count(*) FROM PryvLog FACET level SINCE 30 minutes ago

-- External call latency (cross-core forwards, rqlite, ACME, etc.)
SELECT average(duration) FROM ExternalService FACET externalHostname SINCE 1 hour ago

Caveats

Adding a new provider later

The façade at components/business/src/observability/ exposes a fixed method set: isActive(), setTransactionName(), recordError(), recordCustomEvent(), startBackgroundTransaction().

A new provider is a sibling directory under components/business/src/observability/providers/<id>/ exporting:

The boot shim at bin/_observability-boot.js dispatches based on PRYV_OBSERVABILITY_PROVIDER. No change to business code, CLI base, or PlatformDB shape is required when adding a provider.