Skip to main content

Environment Variables

All process.env access in the package lives in src/shared/config.ts. Nowhere else in the bundles reads process.env — keep this invariant when extending the code.

Both sides​

VariableRequiredDefaultDescription
SYNC_SHARED_SECRETyes, when delivery is enabled—Shared secret. HMAC key in hmac mode or bearer token in token mode. Publisher startup fails when subscriber URLs are configured and this is blank. Subscriber auth fails closed when blank.
SYNC_AUTH_MODEnohmachmac | token. Must match on publisher and subscriber. See Authentication.
SYNC_ENTITIESnoworkflows,credentialsComma-separated subset of workflows, credentials, executions. Absent or blank values use the default; explicit invalid names or comma-only empty selections fail startup. executions requires workflows. Disabled families are rejected by the subscriber with non-retryable 422 SYNC_ENTITY_DISABLED.
LOG_LEVELnoinfodebug | info | warn | error. Structured JSON logger.

Publisher​

VariableRequiredDefaultDescription
SYNC_SUBSCRIBER_URLSyes, on publisher—Comma-separated target base URLs for fan-out. Falls back to SYNC_SUBSCRIBER_URL if unset. Entries must be absolute base URLs with no path, query, fragment, or userinfo. HTTPS is required unless SYNC_ALLOW_INSECURE_HTTP=true and NODE_ENV is development or test.
SYNC_SUBSCRIBER_URLno—Legacy single-target form of SYNC_SUBSCRIBER_URLS.
SYNC_ALLOW_INSECURE_HTTPnofalseDevelopment/test-only escape hatch for http:// subscriber URLs. Ignored unless NODE_ENV is development or test.
SYNC_SOURCE_IDyes, when delivery is enabled—Stable logical source identifier stamped on every event. Required when SYNC_SUBSCRIBER_URLS or SYNC_SUBSCRIBER_URL enables delivery. Must be non-blank and 512 characters or fewer.
SYNC_EVENTS_PATHno/rest/sync/v1/eventsEndpoint path on the subscriber. Must be a local absolute path with no query or fragment.
SYNC_TIMEOUT_MSno10000Per-attempt HTTP timeout in milliseconds. Integer range: 1 to 300000.
SYNC_MAX_RETRIESno3Total delivery attempts per event, including the first attempt. Integer range: 1 to 10.
SYNC_MAX_QUEUE_SIZEno1000Max queued events per target. Integer range: 1 to 100000. When full, the oldest queued event is dropped and logged before the new event is enqueued.
SYNC_PUBLISHER_STATE_PATHno/home/node/.n8n/sync-state/publisher-ordering.jsonDurable publisher source identity and counter store for eventId and per-entity entityRevision. A best-effort .lock file is created next to this path. Put both on persistent storage.
SYNC_PUBLISHER_INVALID_STATEnofailfail | quarantine-reset. Recovery policy when the parsed publisher order state matches no known shape (supported versions 1, 2, 3). Both modes quarantine the file via atomic rename to <statePath>.corrupt.<UTC-timestamp>.bak. fail stays degraded without reiniting counters; quarantine-reset reinits from zero only when the configured SYNC_SOURCE_ID differs from the quarantined file's stored sourceId, followed by a mandatory full subscriber resync. Invalid values fail startup.
SYNC_FILTER_BY_TAGnofalseWhen true, sync only workflows that carry SYNC_WORKFLOW_TAG. See Tag-based Filtering.
SYNC_WORKFLOW_TAGnosyncWorkflow tag name that gates syncing. Effective only when SYNC_FILTER_BY_TAG=true.
SYNC_ACTIVE_TAGnoactiveTag name that rewrites the DTO active to true when present. The real source value is preserved in meta.active_real. Effective only when SYNC_FILTER_BY_TAG=true.

Subscriber​

VariableRequiredDefaultDescription
SYNC_ROUTE_BASEno/rest/sync/v1Base path for mounted routes. Must be a local absolute path with no query or fragment. The subscriber mounts GET <base>/health, GET <base>/ready, and POST <base>/events.
SYNC_TARGET_PROJECT_IDno—Best-effort link of newly synced workflows/credentials to this project (*:owner role). If empty, the applier lazily tries the target owner's personal project and caches the result, including lookup misses.
SYNC_APPLY_ACTIVE_STATEnofalsePublish/unpublish the synced workflow on the target via n8n's WorkflowService (registers triggers/webhooks with the active workflow manager). Publication failures are warn-only; the event still returns applied.
N8N_CORE_PATHno/usr/local/lib/node_modules/n8nPath to n8n's core bundle (used to resolve WorkflowService/WorkflowHistoryService for target-side publishing).
SYNC_MAX_BODY_BYTESno16777216Request body size cap. Integer range: 1 to 67108864.
SYNC_SIGNATURE_TOLERANCE_MSno300000Max signature age/skew accepted in hmac mode. Integer range: 1 to 3600000.
SYNC_REPLAY_CACHE_SIZEno10000Max successful exact signed HMAC requests remembered for replay rejection in this process. Integer range: 1 to 100000. Entries expire with SYNC_SIGNATURE_TOLERANCE_MS; in-flight reservations are additional transient entries.
SYNC_SUBSCRIBER_STATE_PATHno/home/node/.n8n/sync-state/subscriber-ordering.jsonDurable subscriber ordering and tombstone store keyed by [sourceId, entityKind, entityId]. When executions are enabled, the execution identity map is stored beside it as <basename>.executions.json.
N8N_DI_PATHno/usr/local/lib/node_modules/n8n/node_modules/@n8n/diPath to n8n's @n8n/di module.
N8N_DB_PATHno/usr/local/lib/node_modules/n8n/node_modules/@n8n/dbPath to n8n's @n8n/db module.

Defaults at a glance​

# Minimal publisher
export EXTERNAL_HOOK_FILES=/opt/n8n-sync/publisher.cjs
export SYNC_SUBSCRIBER_URLS=https://target.example.com
export SYNC_SOURCE_ID=prod-source-a
export SYNC_SHARED_SECRET=<secret>

# Minimal subscriber
export EXTERNAL_HOOK_FILES=/opt/n8n-sync/subscriber.cjs
export SYNC_SHARED_SECRET=<secret>

Every other setting has a sensible default and only needs to be set when you want non-default behavior. See the Quick Start for a complete walkthrough.

Reference​