Remote Settings
On boot, AnalyticsBrowser.load fetches the CDN settings JSON for your
writeKey ({cdnURL}/v1/projects/{writeKey}/settings) itself, hands it to
analytics-next (which then skips its own fetch — the request count is
unchanged), and reads a custom silo block out of it:
{ "integrations": { "...": "standard Segment fields" }, "silo": { "timeOnPage": { "enabled": true, "idleSeconds": 60 }, "consent": { "mode": "opt-out" }, "ubid": { "mode": "opt-in" } }}Because the settings are served per writeKey from the Silo CDN, features can be toggled and tuned from the web, without a redeploy of the consuming site.
Precedence
Section titled “Precedence”Plugin defaults < code config < remote settings. Remote values win — the point is post-deploy control. The block is partial: fields it omits fall through to whatever the site’s code config (or the library default) says.
If the settings fetch fails — network error, non-2xx, malformed body — the
library loads with pure code config and lets analytics-next fetch the
settings itself. Remote unreachable behaves exactly like a library without
remote settings.
silo.timeOnPage
Section titled “silo.timeOnPage”| Option | Type | Default | Description |
|---|---|---|---|
enabled | boolean | true | Kill switch — false skips plugin registration entirely (no listeners, no middleware, no beacons). |
minSeconds | number | — | Minimum seconds before sending an event. |
maxSeconds | number | — | Maximum seconds to cap the event at. |
idleSeconds | number | — | Seconds of zero user input after which the engagement counter pauses. 0 disables idle gating entirely. |
heartbeatSchedule | number[] | false | — | Bounded-exponential heartbeat schedule in seconds. false disables heartbeats entirely. |
scrollTracking | boolean | — | Document-relative scroll-depth tracking. |
A — default means the field falls through to the site’s code config
when absent — see Configuration for the library defaults.
Only enabled has a remote-level default, because it controls library
behavior no code config can express.
enabled: false skips plugin registration entirely: no listeners, no
middleware, no beacons. apiHost, writeKey, and eventName are
deliberately not remote-tunable (endpoint redirection attack surface /
downstream data-contract changes).
silo.consent
Section titled “silo.consent”| Option | Type | Default | Description |
|---|---|---|---|
mode | ConsentMode | "opt-out" | Per-writeKey consent regime — the do-nothing default applied when the visitor has expressed no choice. "opt-out": silo collects by default (US / no consent regime). "opt-in": silo collects nothing until consent (GDPR/ePrivacy/Law 25). The code-config offlineFallbackMode is the fallback when the CDN settings are unreachable. |
mode sets the per-writeKey do-nothing default for silo’s own collection —
flipping a property’s regime from the web is a single edit here, no redeploy.
What opt-in/opt-out mean, how GPC and the visitor’s live CMP choice take
precedence, and the offlineFallbackMode fallback are all documented in
Consent — the single source for consent behavior.
silo.ubid
Section titled “silo.ubid”| Option | Type | Default | Description |
|---|---|---|---|
mode | ConsentMode | "opt-in" | Per-writeKey consent regime for ubid. Default ("opt-in") lives in SILO_REMOTE_DEFAULTS (defaults.ts): a browser fingerprint is profiling tech, so it collects nothing until consent. Set "opt-out" per writeKey to collect ubid by default (US / no-consent-regime properties). This is the only knob that flips it, and is deliberately remote-only — opting ubid OUT of consent is a deliberate act, never a CDN-unreachable fallback. |
ubid (universal browser id) is its own consent capability with its own regime,
overridable per writeKey here. Unlike consent.mode, ubid defaults to
opt-in: a browser fingerprint is profiling tech, so it collects nothing
until the visitor consents — independent of the property’s consent.mode. Set
"opt-out" for a writeKey to collect ubid by default (US / no-consent-regime
properties). This is the only way to flip it, and is deliberately remote-only
— there is no code-config fallback, so opting ubid out of consent is always a
deliberate per-writeKey act, never a CDN-unreachable default. GPC still denies
ubid regardless. See Consent for how the gate resolves.
TypeScript contract
Section titled “TypeScript contract”The block’s shape is exported as SiloRemoteSettings /
SiloRemoteTimeOnPage / SiloRemoteConsent / SiloRemoteUbid — import them
into whatever serves or edits the settings JSON so both ends of the contract
compile against one type:
import type { SiloRemoteSettings } from "@adpharm/silo-analytics";The defaults shown in the tables above (the time-on-page enabled kill switch
and the per-capability consent modes) are also exported as a runtime const, so
an editor can render the effective default without hardcoding it:
import { SILO_REMOTE_DEFAULTS } from "@adpharm/silo-analytics";The enabled kill switch is mirrored by the library’s branch logic; the
consent/ubid modes are read at runtime as the final fallback. The editor
and these docs read this const so the default shown is always the one the
contract ships.