Skip to content

Operation

This section is for operators running Synchronic Web infrastructure in real environments. It covers deployment, service roles, network API behavior, routine operations, and protocol specifications. Unless otherwise noted, examples target the deploy/compose/general stack.

This section describes how to bring up and manage the reference runtime stack used throughout the rest of this guide.

The Compose deployment is the baseline operating mode for local, staging, and many production-like environments. It works with Compose-compatible runtimes such as Docker Compose, Podman Compose, and podman-compose. It provides a predictable process model so operators can troubleshoot behavior without guessing which component wiring changed.

Required/important environment variables:

  • COMPOSE_PROJECT_NAME (recommended): stack identity; isolates generated volumes and prefixes container/network names
  • SECRET (required): interface authentication secret
  • HTTP_PORT (default 8192): published HTTP port
  • HTTPS_PORT (default 8193): published HTTPS port
  • PERIOD (default 2): stepping cadence parameter passed to journal
  • WINDOW (default 1024): retention window for unpinned history
  • TLS_CERT_HOST_PATH (optional): host certificate file mounted into router
  • TLS_KEY_HOST_PATH (optional): host key file mounted into router

Start:

Terminal window
COMPOSE_PROJECT_NAME=sync-local SECRET=password tests/api/local-compose.sh up

Smoke validation:

Terminal window
COMPOSE_PROJECT_NAME=sync-local tests/api/local-compose.sh smoke

Direct local HTTP deployment (no TLS):

Terminal window
COMPOSE_PROJECT_NAME=sync-dev SECRET=password \
HTTP_PORT=8192 HTTPS_PORT=8193 \
docker compose -f deploy/compose/general/compose.yaml up -d

Optional public TLS deployment with the same compose file:

Terminal window
COMPOSE_PROJECT_NAME=sync-prod \
TLS_CERT_HOST_PATH=/absolute/path/to/fullchain.pem \
TLS_KEY_HOST_PATH=/absolute/path/to/privkey.pem \
SECRET=password ORIGIN=https://example.com HTTP_PORT=80 HTTPS_PORT=443 \
docker compose -f deploy/compose/general/compose.yaml up -d

Stop without deleting data:

Terminal window
COMPOSE_PROJECT_NAME=sync-dev docker compose -f deploy/compose/general/compose.yaml down

Only add -v when you intentionally want to delete that stack’s database and identity-provider volumes.

The default stack includes:

  • journal runtime (journal-sdk plus mounted general Lisp deployment inputs)
  • router/nginx entrypoint
  • gateway API service
  • explorer UI
  • workbench UI
  • file-system WebDAV service

The compose stack does not use a separate immutable general image. Instead, journal-sdk starts through deploy/compose/general/run.sh, which reads mounted records/lisp/*.scm files. Fresh databases install from those files; existing databases only absorb changed Lisp inputs when JOURNAL_UPDATE=1.

The service split allows teams to scale or replace one layer at a time. For example, router behavior can be adjusted independently from journal runtime updates. The router service is the public nginx entry point for the deployment. It serves runtime query routes and UI routes:

RoutePurpose
/interfaceScheme or JSON request endpoint selected by request Content-Type.
/docsGateway Swagger/OpenAPI documentation and route orientation.
/api/v1/...Versioned gateway API endpoints proxied to gateway service.
/explorer/Browser UI with dedicated Ledger, Stage, and admin-only Admin modes for committed browsing, local staged editing, and application-level journal administration.
/workbench/Developer-oriented query workspace with API aids.
/webdav/WebDAV file-system projection: /stage (mutable), /ledger/state (current committed, index optional), /control/pin (pin directives).

Router mode is selected at startup:

  • HTTP mode when TLS cert/key files are not found.
  • TLS mode when both cert/key files are present.

Implemented by records/lisp/interface.scm on top of root.scm, standard.scm, and ledger.scm. Permission boundaries are central to safe operation, so operators should treat function families as security domains.

FamilyDescriptionFunctions
Public (no authentication)Read-mostly methods intended for external visibility without secrets.size, synchronize, info, config, get, trace
Restricted (interface secret)Stateful or sensitive operations that require interface authentication.resolve, set!, pin!, unpin!, bridge!, bridge-synchronize!, *step!*, *secret*, *admins-get*, *admins-set*, *window-set*
Root/AdminRoot commands for runtime mutation and administrative lifecycle management.*eval*, *call*, *step*, *set-secret*, *set-step*, *set-query*

Use this reference when building runbooks or on-call procedures. The same function names appear in Explorer/Workbench, automated scripts, and incident diagnostics.

FunctionPurpose
sizeCurrent permanent-chain size
synchronizeSerialize digest/proof data for bridge sync
infoPublic node metadata (for example public key and window)
configFull current config expression
getRead staged state content
traceReturn serialized proof/path view rooted at an index
FunctionPurpose
resolveResolve committed content, optionally with pin/proof detail
set!Stage a write
pin!Persist proof/data in permanent chain
unpin!Remove persisted pin
bridge!Register bridge/publication target with local bridge info and optional prefetched remote info
bridge-synchronize!Merge a prepared bridge synchronization response
*step!*Run interface stepping, including bridge synchronization
*secret*Rotate interface secret
*admins-get*Read the interface admin username list
*admins-set*Replace the interface admin username list
*window-set*Update the public ledger retention window
FunctionPurpose
*eval*Evaluate arbitrary Scheme in admin context
*call*Invoke function with root object
*step*Execute full step cycle
*set-secret*Rotate root/admin secret
*set-step*Replace step handler
*set-query*Replace query handler

root.scm provides authentication of privileged operations, enforces root mutation/update discipline, and defines hook points for query and step behavior.

These are the public root methods exposed by the root module’s base record object.

MethodSignatureDescription
get((root 'get) path)Read value at path; returns value, (nothing), or directory metadata.
set!((root 'set!) path value)Write value at path; supports structured node/object values and deletion via (nothing).
copy!((root 'copy!) source target)Copy value from source path to target path.
equal?((root 'equal?) source target)Exact structural equality check between two paths.
equivalent?((root 'equivalent?) source target)Digest-equivalence check between two paths.

These are public root commands handled by the transition function in root.scm.

CommandSignatureDescription
*eval*(*eval* <admin-secret> <expression>)Evaluate expression in admin context.
*call*(*call* <admin-secret> <function>)Invoke function with root object and persist resulting state.
*step*(*step* <admin-secret>)Execute configured step handler pipeline.
*set-secret*(*set-secret* <old> <new>)Rotate admin secret used by root plane.
*set-step*(*set-step* <admin-secret> <step-function>)Replace step handler logic.
*set-query*(*set-query* <admin-secret> <query-function>)Replace query handler logic.

This API is intentionally powerful and low-level, so access should be tightly controlled and audited.

interface.scm overlays the instantiated ledger object and dispatches ((function ...)) requests to ledger and bridge-helper methods, with permission checks on each call. It also handles remote bridge fetch/merge flows before handing the final operation to ledger.

MethodPermissionDescription
sizePublicReturn permanent chain size.
synchronizePublicReturn serialized sync proof at index.
infoPublicReturn public node configuration.
configPublicReturn full inline ledger configuration.
getPublicRead staged content.
tracePublicReturn serialized proof/path content rooted at an index.
resolveRestrictedReturn resolved path content, optionally with pin/proof detail.
set!RestrictedStage write to local state path.
pin!RestrictedPersist selected path/proof in permanent chain.
unpin!RestrictedRemove previously pinned path/proof.
bridge!RestrictedAdd bridge/publication target, fetching remote info when omitted.
bridge-synchronize!RestrictedSynchronize a named bridge into local staged state.
*step!*RestrictedRun bridge synchronization and local step progression.
*secret*RestrictedRotate interface secret used by interface API auth checks.
*admins-get*RestrictedRead the interface admin username list.
*admins-set*RestrictedReplace the interface admin username list.
*window-set*RestrictedUpdate the public ledger retention window.

Root commands (*eval*, *call*, *step*, *set-secret*, *set-step*, *set-query*) are also callable, but remain part of the root-plane surface and should be treated as admin-level operations. This keeps externally visible behavior stable while allowing implementation details inside ledger classes to evolve.

Public ledger/interface paths use flat Scheme lists or JSON arrays, for example (*state* alice notes) and ["*state*", "alice", "notes"]. Nested path lists remain an internal ledger storage detail and should not be used in API requests.

This section provides common operational procedures. Each example includes both Lisp and JSON forms. These are direct calls that can be run manually, but they also serve as templates for operational automation.

Secret rotation is the minimum operational hygiene task for any deployed environment and should be part of regular runbooks.

((function *secret*)
(arguments ((secret "new-password")))
(authentication ((credentials "old-password"))))
(*set-secret* "old-admin" "new-admin")

Use root-level calls for controlled live updates. Typical update targets are: root hooks, standard, tree, chain, interface, and ledger. Because these changes alter live semantics, apply them in lower environments first and validate with smoke checks before promotion.

Update root hooks (*set-query*, *set-step*)

Section titled “Update root hooks (*set-query*, *set-step*)”
(*set-query* "admin-password"
(lambda (root query)
(if (equal? query '(*ping*)) 'pong (error 'query-error "No handler"))))

For step hook updates, use the same pattern with *set-step*.

(*call* "admin-password"
(lambda (root)
(define standard-cls '(define-class (standard) ...))
((root 'set!) '(root class standard) standard-cls)
((root 'set!) '(root object standard)
(((eval (caddr standard-cls)) #f standard-cls)))))
((function config)
(authentication ((credentials "password"))))

For in-place configuration mutation, use the interface *call*/*eval* root path or the ledger’s update-config! method from an authenticated admin flow.

Operational pattern:

  1. Replace class definition under (root class <name>).
  2. Rebuild affected object with standard.make.
  3. Reinsert updated object under (root object ledger) or related path.
  4. Validate with smoke tests.
(*call* "admin-password"
(lambda (root)
(define ledger-cls '(define-class (ledger) ...))
((root 'set!) '(root class ledger) ledger-cls)
...))