This document defines the boundary between:
DEXBot2: runtime infrastructure, BitShares connectivity, credentials, and execution substrateClaw: bridge layer, shared infrastructure, and workflow owner
The goal is simple:
Clawprovides shared infrastructure helpers and a bridge surfaceClawcan talk to DEXBot2 and the blockchain directly- The infrastructure layer stays reusable and decision-free
The current scaffold lives in ../modules/claw_infra.js, ../modules/dexbot_profiles.js, ../modules/nanoclaw_bridge.js, ../modules/openfang_bridge.js, ../modules/zeroclaw_bridge.js, and ../modules/nullclaw_bridge.js, and is exported from ../index.js.
The Claw infrastructure layer should:
- provide shared runtime helpers
- provide connection and credential adapters
- provide configuration, logging, and state helpers
- provide market-data and BitShares utility wrappers
- provide low-level order/grid math helpers only
- expose write-capable clients only behind explicit caller intent
- manage bot-level settings only; keep DEXBot general settings default-first and explicit-only
- treat
profiles/general.settings.jsonas read-only context, not a Claw write surface - avoid process management
- avoid exposing raw private keys or bypassing the credential daemon boundary
- avoid owning persistent execution state
- avoid making strategy decisions
The Claw workflow layer should:
- manage lifecycle and persistence
- place, cancel, and rebalance orders
- talk to DEXBot2 when it needs shared runtime support
- decide whether to apply or ignore recommendations
- keep launcher orchestration, PM2 startup, and Docker entrypoint behavior in the
launcher-opsskill boundary instead of the infrastructure API boundary
The cleanest shape is a small library with a narrow, typed surface:
- input: plain objects / JSON
- output: plain objects / JSON
- no side effects unless explicitly requested
Think of Claw's infrastructure layer as the shared foundation that the workflow layer builds on.
ZeroClaw should use Claw as a compatibility layer, not as a second signing or credential system.
- ZeroClaw can invoke the JSON/CLI bridge in ../scripts/zeroclaw_bridge.js.
- The manifest lives in ../modules/zeroclaw_manifest.js and is safe to query without starting the BitShares runtime.
- Claw keeps private-key access inside its existing DEXBot2 credential path.
- ZeroClaw gets read access to market, profile, HONEST, and order context, plus explicit action entrypoints when it needs to request a trade operation.
The bridge surface currently includes:
- runtime and manifest inspection
- profile, market, and account snapshots
- open-order queries
- HONEST context and pricing
- limit order create, cancel, update, and batch execution
- MPA borrow, repay, collateral adjustment, and settlement
- BTS-backed short open, take-profit, close, and plan builders
- MPA position lookup
Launcher behavior such as node unlock-start --claw-only and node pm2 claw-only is documented and maintained separately under skills/launcher-ops/.
Recommended trust boundary:
- ZeroClaw sends an intent or request.
- Claw resolves the request and, when needed, asks DEXBot2 for the signing key.
- DEXBot2 returns the key only to Claw over the local daemon socket.
- Claw broadcasts the operation.
- ZeroClaw never receives or stores the key.
To generate the skill file from Claw, run:
npm run zeroclaw:skill -- --profile-root /home/alex/BTS/Git/DEXBot2 --output ~/.zeroclaw/workspace/skills/ai-bots/SKILL.tomlNullClaw uses the same bridge surface, with a native skill path centered on SKILL.toml in the workspace.
- NullClaw can invoke the JSON/CLI bridge in ../scripts/nullclaw_bridge.js.
- The manifest lives in ../modules/nullclaw_manifest.js and is safe to query without starting the BitShares runtime.
- Claw keeps private-key access inside its existing DEXBot2 credential path.
- NullClaw gets the same read access to market, profile, HONEST, and order context, plus explicit action entrypoints when it needs to request a trade operation.
To generate the skill file from Claw, run:
npm run nullclaw:skill -- --profile-root /home/alex/BTS/Git/DEXBot2 --output ~/.nullclaw/workspace/skills/bitshares-claw/SKILL.tomlNanoClaw uses the same bridge surface, with a native SKILL.md path in the workspace skill tree.
- NanoClaw can invoke the JSON/CLI bridge in ../scripts/nanoclaw_bridge.js.
- The bridge lives in ../modules/nanoclaw_bridge.js and uses the shared Claw command surface.
- Keep the generated skill named
bitshares-clawso it does not collide with NanoClaw's bundledclawskill.
To generate the skill file from Claw, run:
npm run nanoclaw:skill -- --profile-root /home/alex/BTS/Git/DEXBot2 --output /path/to/nanoclaw/.claude/skills/bitshares-claw/SKILL.mdOpenFang uses the same bridge surface through a CLI-first wrapper and a workspace skill file.
- OpenFang can invoke the JSON/CLI bridge in ../scripts/openfang_bridge.js.
- The bridge lives in ../modules/openfang_bridge.js and uses the shared Claw command surface.
- Keep the generated skill named
bitshares-clawso it stays separate from runtime-specific OpenFang skills and remains a thin wrapper around the shared CLI bridge.
To generate the skill file from Claw, run:
npm run openfang:skill -- --profile-root /home/alex/BTS/Git/DEXBot2 --output ~/.openfang/skills/bitshares-claw/SKILL.mdHermes should consume Claw through the shared MCP server, with an optional local SKILL.md for workflow guidance.
- Hermes can invoke the MCP server in ../scripts/claw_mcp_server.js.
- The manifest wrapper lives in ../modules/hermes_manifest.js and advertises Hermes as an MCP-first runtime over the shared Claw command surface.
- Keep the generated skill named
bitshares-clawand focused on workflow guidance rather than copying bridge logic into Hermes. - Claw keeps private-key access inside its existing DEXBot2 credential path.
To generate the Hermes skill file from Claw, run:
npm run hermes:skill -- --profile-root /home/alex/BTS/Git/DEXBot2 --output ~/.hermes/skills/bitshares-claw/SKILL.mdAdd the MCP server to ~/.hermes/config.yaml:
mcp_servers:
claw:
command: "node"
args: ["/absolute/path/to/claw/scripts/claw_mcp_server.js", "--profile-root", "/home/alex/BTS/Git/DEXBot2"]The shared runtime wiring Claw assembles for its consumers.
type RuntimeContext = {
accountName: string | null;
createdAt: string;
cwd: string;
dataDir: string;
logger: {
info: (...args: unknown[]) => void;
warn: (...args: unknown[]) => void;
error: (...args: unknown[]) => void;
debug?: (...args: unknown[]) => void;
};
name: string;
profileRoot: string | null;
readyFilePath: string;
socketPath: string;
stateDir: string;
config: Record<string, unknown>;
};The bot-specific state Claw already owns and passes through the infrastructure layer.
type BotState = {
botId: string;
name: string;
activeOrders?: number;
incrementPercent?: number;
targetSpreadPercent?: number;
weightDistribution?: { sell: number; buy: number };
botFunds?: { sell: string | number; buy: string | number };
minPrice?: string | number;
maxPrice?: string | number;
gridPrice?: string | number | null;
lastResetAt?: number;
lastCenterPrice?: number;
};The execution limits Claw wants its own logic to respect.
type ConstraintSet = {
minIncrementPercent?: number;
maxIncrementPercent?: number;
minSpreadPercent?: number;
maxSpreadPercent?: number;
minOrdersPerSide?: number;
maxOrdersPerSide?: number;
reservePercent?: number;
minOrderSize?: number;
maxOrderSize?: number;
avoidDust?: boolean;
};Creates a shared runtime object for Claw.
type RuntimeOptions = {
name: string;
accountName?: string;
socketPath?: string;
readyFilePath?: string;
dataDir?: string;
stateDir?: string;
profileRoot?: string;
logger?: unknown;
config?: Record<string, unknown>;
};This should be the central bootstrap helper for a consistent runtime shape.
Returns a read/write BitShares client wrapper.
This helper should:
- connect to BitShares
- reuse the shared client pattern already in Claw
- ask the DEXBot2 credential daemon for keys when needed
- keep key handling out of callers
Returns a thin client for DEXBot2's Unix-socket credential daemon.
This is the bridge between Claw and the DEXBot2 credential infrastructure.
Returns a simple filesystem-backed state store.
Use this for:
- bot metadata
- position snapshots
- cached market snapshots
- restart recovery
Returns a data access layer for market snapshots and chain-derived state.
This is infrastructure only:
- reads
- subscriptions
- normalization
- no decision making
Returns the DEXBot2 order subsystem exports directly:
- grid math
- order sizing
- spread calculation
- bounds validation
- fee estimation
This is the right place for reusable mechanics that Claw needs before it decides what to do.
Reads the DEXBot2 profiles/ directory and normalizes:
profiles/config.jsonwhen presentprofiles/bots.jsonprofiles/general.settings.jsonprofiles/market_profiles.json- per-bot files in
profiles/orders/
This is the profile-folder bridge for Claw.
profiles/general.settings.json is read-only context here, not a Claw write surface.
Returns the current DEXBot2 bot config in a normalized, read-only view.
The result includes:
- raw bot data
- effective values with DEXBot2 defaults merged in
- current validation status
- file locations for the selected bot
- mutability metadata for the bridge
Validates a bot-settings patch without writing it.
Use this before any settings write to check:
- merged next-state values
- validation errors
- whether the patch would require a recalc trigger
Applies a bot-settings patch through the DEXBot2 profile lock.
This helper should:
- acquire the
bots.jsonlock before reading and writing - merge the patch against the current bot record
- validate the merged result before persisting
- optionally write the recalc trigger atomically while still inside the lock
- reload the bundle before returning the updated bot view
This is the preferred write path for bot tuning and for any bridge command that needs to change DEXBot2 bot settings safely.
Returns one normalized JSON object that combines:
- DEXBot2 profile files
- selected bot metadata
- selected bot order snapshots
- selected AMA profile match
- derived summary fields
This is the preferred one-call entrypoint for Claw.
Returns a HONEST-focused infrastructure helper that:
- loads
HONEST.*assets - exposes the hardcoded
HONEST.MONEY/BTSbridge - resolves HONEST pair contexts with DEXBot2 pool utilities
- resolves pair prices without introducing strategy decisions
Useful companion method:
resolveHonestPairPrice(assetA, assetB, options)for the special-case bridge plus DEXBot2 fallback pool pricing
The bridge exposed by ../modules/claw_bridge.js supports:
manifestruntimeprofile-contextmarket-snapshotaccount-snapshotopen-ordershonest-contexthonest-pairhonest-pricecreate-limit-ordercancel-limit-orderbuild-update-limit-order-opupdate-limit-orderexecute-batchborrow-mparepay-mpaadjust-mpa-collateralsettle-mpaopen-short-btstake-profit-btsclose-short-btsbuild-open-short-planbuild-take-profit-planbuild-close-short-planmpa-positionbot-settingsbot-settings-previewbot-settings-apply
The barrel export in claw/index.js spreads every module into one flat namespace. Several modules define functions with the same name but different semantics. The barrel resolves these collisions with explicit trailing overrides:
| Export name | Source module | Purpose |
|---|---|---|
resolveAccountName |
chain_queries |
Async lookup — returns the account name string for an ID, or passes through the original name |
resolveSigningAccountName |
chain_broadcast |
Sync extraction — returns the signing account name string from a context object |
describeZeroClawBridge |
zeroclaw_manifest |
Returns the ZeroClaw manifest descriptor (runtime name, command examples) |
describeZeroClawRuntimeBridge |
zeroclaw_bridge |
Returns the ZeroClaw runtime bridge descriptor |
When consuming claw/index.js as a library, use the disambiguated names above. The non-prefixed resolveAccountName and describeZeroClawBridge point to the query/manifest variants by default.
The dynamic weight service (modules/dynamic_weight_service.js) defaults to requiring BTS as the quote asset. Two mechanisms extend this for markets with non-BTS quote assets.
Pass supportsNonBtsQuotes: true to createDynamicWeightService(deps) to allow bots whose quote asset is not BTS to pass eligibility checks.
When omitted, the service auto-detects: if a custom fetchTrendInput function is injected (i.e. it differs from the built-in default), supportsNonBtsQuotes defaults to true on the assumption that custom trend sources know how to price non-BTS pairs. Pass supportsNonBtsQuotes: false explicitly to override the auto-detection.
When a bot has a non-BTS quote and the trend source does not support it, isEligibleBot rejects with reason trend_source_requires_bts_quote before any trend data is fetched.
fetchTrendInput now receives a second argument — a context object:
type TrendInputContext = {
bot: object; // deep clone of the selected bot
marketRef: string; // resolved market asset reference
quoteRef: string; // resolved quote asset reference
requireBtsQuote: boolean; // current policy value
};Custom fetchTrendInput implementations can use the context to route pricing for non-BTS markets (e.g. fetching an external oracle instead of the BTS feed).
The built-in fetchTrendInput ignores the context parameter, so existing callers are unaffected.
- Claw collects market data and its own state.
- Claw creates shared runtime helpers via
createRuntimeContext. - Claw loads the DEXBot2 profile bundle through the adapter.
- Claw uses HONEST and profile context helpers when needed.
- Claw makes all decisions.
- Claw executes against DEXBot2 and the blockchain.
That keeps the separation clean:
- Claw infrastructure provides the foundation
- Claw workflow decides
- DEXBot2 supports runtime execution
The Claw infrastructure layer should be allowed to provide:
- connection wrappers
- credential daemon access
- file-backed state stores
- market-data adapters
- order and grid math helpers
- validation and normalization utilities
- explicit execution adapters that still keep key material behind DEXBot2
The Claw infrastructure layer should not be responsible for:
- strategy decisions
- signing policy
- key ownership
- PM2 lifecycle
- bot orchestration
- persisting execution decisions
- autonomous trade execution without explicit caller intent
If you want the simplest possible integration, use one request and one response for infrastructure wiring.
{
"runtime": {
"name": "claw-runtime",
"accountName": "your-account",
"socketPath": "./profiles/run/dexbot-cred-daemon.sock"
},
"state": {
"botId": "claw-01",
"dataDir": "./data",
"stateDir": "./data/state"
}
}Example response with the resolved absolute socket path:
{
"runtime": {
"ready": true,
"resolvedSocketPath": "/app/profiles/run/dexbot-cred-daemon.sock",
"notes": ["Credential daemon is reachable."]
},
"stores": {
"stateStore": "filesystem",
"cacheStore": "filesystem"
},
"tools": {
"orderMath": "available",
"marketAdapter": "available",
"bitsharesClient": "available"
}
}If you want a simple division of responsibility:
Clawinfrastructure provides the common foundationClawworkflow makes trading decisionsDEXBot2handles the runtime substrate and credentials
That gives you a reusable infrastructure layer without coupling it to any single executor.