Bundled mode
In Bundled mode, you configure walkerOS with JSON files and build standalone bundles using the CLI. The output is a separate artifact (one script for web, a directory for server) that can be deployed independently of your application.
Quickstart
1. Install the CLI
npm install -g @walkeros/cli
# Verify installation
walkeros --version2. Create a flow configuration
Create flow.json:
- Web (browser)
- Server (Node.js)
{
"version": 4,
"flows": {
"default": {
"config": {
"platform": "web",
"bundle": {
"packages": {
"@walkeros/collector": { "version": "^4" },
"@walkeros/web-source-browser": { "version": "^4" }
}
}
},
"sources": {
"browser": {
"package": "@walkeros/web-source-browser",
"config": {
"settings": {
"pageview": true
}
}
}
},
"collector": { "run": true }
}
}
}{
"version": 4,
"flows": {
"default": {
"config": {
"platform": "server",
"bundle": {
"packages": {
"@walkeros/collector": { "version": "^4" },
"@walkeros/server-source-express": { "version": "^4" },
"@walkeros/destination-demo": { "version": "^4" }
}
}
},
"sources": {
"http": {
"package": "@walkeros/server-source-express",
"config": {
"settings": { "paths": ["/collect"] }
}
}
},
"destinations": {
"console": {
"package": "@walkeros/destination-demo",
"config": {
"settings": { "name": "Event Logger" }
}
}
},
"collector": { "run": true }
}
}
}3. Build the bundle
walkeros bundle flow.jsonThis writes the bundle to stdout. Use -o to write to disk:
- Web:
-o ./dist/walker.js(IIFE format, loadable via script tag) - Server:
-o ./dist/(writesdist/flow.mjsin ESM format plusdist/package.jsonanddist/node_modules/; ship the whole directory)
4. Deploy
- Web
- Server
Add to your HTML:
<script src="/walker.js"></script>
Start the bundle with the runtime (flow.mjs exports a start function, so plain node does not start it):
npx --package=@walkeros/runner runneros start dist/flow.mjs
Or with Docker, mounting the whole directory:
docker run -p 8080:8080 -v "$PWD/dist:/app/flow:ro" walkeros/flow:<version>
For containers, see Docker deployment below.
Adding destinations
Add destinations to your flow.json:
{
"version": 4,
"flows": {
"default": {
"config": {
"platform": "web",
"bundle": {
"packages": {
"@walkeros/collector": { "version": "^4" },
"@walkeros/web-source-browser": { "version": "^4" },
"@walkeros/web-destination-api": { "version": "^4" },
"@walkeros/web-destination-gtag": { "version": "^4" }
}
}
},
"sources": {
"browser": {
"package": "@walkeros/web-source-browser",
"config": { "settings": { "pageview": true } }
}
},
"destinations": {
"api": {
"package": "@walkeros/web-destination-api",
"config": {
"settings": { "url": "https://your-api.com/events" }
}
},
"ga4": {
"package": "@walkeros/web-destination-gtag",
"config": {
"settings": {
"ga4": { "measurementId": "G-XXXXXXXXXX" }
}
}
}
},
"collector": { "run": true }
}
}
}Rebuild: walkeros bundle flow.json -o ./dist/walker.js
Adding consent
Add consent requirements in the destination config:
"destinations": {
"api": {
"package": "@walkeros/web-destination-api",
"config": {
"settings": { "url": "https://your-api.com/events" },
"consent": { "functional": true }
}
},
"ga4": {
"package": "@walkeros/web-destination-gtag",
"config": {
"settings": { "ga4": { "measurementId": "G-XXXXXXXXXX" } },
"consent": { "analytics": true }
}
}
}Set consent at runtime:
// After loading walker.js
elb('walker consent', { functional: true, analytics: true });
Until a destination's required consent is granted, its events wait in an in-memory queue and are delivered once walker consent grants it. The queue holds up to 1000 events per destination by default; when it is full, the oldest events are dropped. Change the limit with config.queueMax on the destination, see buffer bounds.
Key concepts
The package: property
In Bundled mode, you reference packages by name:
"sources": {
"browser": {
"package": "@walkeros/web-source-browser"
}
}
The CLI downloads and bundles the package. This differs from Integrated mode where you use code: with a direct import.
Variables and environment
Use variables for environment-specific values:
{
"version": 4,
"variables": {
"GA_ID": "$env.GA_MEASUREMENT_ID:G-DEFAULT",
"API_URL": "$env.API_ENDPOINT:https://api.example.com"
},
"flows": {
"default": {
"config": { "platform": "web" },
"destinations": {
"ga4": {
"package": "@walkeros/web-destination-gtag",
"config": {
"settings": { "ga4": { "measurementId": "$var.GA_ID" } }
}
}
}
}
}
}Environment variables ($env.NAME:default) are resolved at build time for web bundles, which bake the value into walker.js. Server bundles read them from the environment at runtime and fall back to the default. Config variables ($var.name) reference values from the variables section.
Multiple flows
Define different flows for different environments:
{
"version": 4,
"flows": {
"development": {
"config": { "platform": "web" },
"destinations": {
"console": { "package": "@walkeros/destination-demo" }
}
},
"production": {
"config": { "platform": "web" },
"destinations": {
"ga4": { "package": "@walkeros/web-destination-gtag" }
}
}
}
}Build specific flow: walkeros bundle flow.json --flow production
CLI commands
| Command | Purpose |
|---|---|
walkeros bundle | Build production bundle |
walkeros push --simulate | Test with mocked destinations |
walkeros push | Test with real API calls |
runneros start | Run a built server flow (the separate @walkeros/runner package) |
See CLI documentation for full details.
Docker deployment
For production server deployments:
# Build the bundle directory
walkeros bundle flow.json -o ./dist/
# Run with Docker (the image expects flow.mjs in /app/flow)
docker run -d -p 8080:8080 \
-v "$PWD/dist:/app/flow:ro" \
walkeros/flow:<version>Use a walkeros/flow version that ships runneros, ideally the CLI version you bundled with. See the runtime for image tags, the canonical Dockerfile and every environment variable.
See your event
Before you build and deploy, run the event through the flow offline with the named destination mocked.
- Web (browser)
- Server (Node.js)
Using the flow.json with destinations you created above, push builds the flow
and runs the event through it with the named destination mocked. Nothing is sent
to a vendor.
npx walkeros push flow.json \
-e '{"name":"page view"}' \
--simulate destination.ga4Using the server flow.json above (which defines the console
destination), push builds and simulates it:
npx walkeros push flow.json \
-e '{"name":"page view"}' \
--simulate destination.consolepush --simulate builds the flow, runs the event through it with
destination.console replaced by a mock, and prints the outcome, the matched
mapping rule and the recorded vendor calls; add --json to get the same result
as JSON.
Nothing is sent to a vendor. Event names use a space (page view).
Observe a running flow
To watch a deployed web bundle's events live, add the public connect pair to
the flow's config and rebuild once:
"config": {
"platform": "web",
"observe": {
"url": "https://observer.example.com",
"binding": "pb_x"
}
}Rebuild: walkeros bundle flow.json -o ./dist/walker.js
Both values are public and safe to commit; set both, a partial pair warns at
build time and wires nothing. The bundle never contains a credential: the
per-session credential arrives at runtime via a ?elbObserve= URL parameter.
See Observe for the full setup and the
credential lifecycle.
Next steps
- CLI documentation: All CLI commands and options
- Runtime: Run built flows in production
- Mapping: Transform events for destinations
See also
- Integrated mode: Build into your app with TypeScript
- Collector reference: Understanding the collector engine