Skip to content

Add service job provider runtime#9

Open
ai-virtual-b wants to merge 9 commits intomainfrom
service-jobs-be-runtime
Open

Add service job provider runtime#9
ai-virtual-b wants to merge 9 commits intomainfrom
service-jobs-be-runtime

Conversation

@ai-virtual-b
Copy link
Copy Markdown
Contributor

@ai-virtual-b ai-virtual-b commented Apr 28, 2026

Summary

  • add acp serve commands for service-job provider runtimes: init, start, endpoints, deploy bundle, stop, logs
  • add handler/budget/offering scaffolds and a runtime that connects outbound to the BE service-job namespace
  • keep x402/MPP public endpoints on BE while the provider self-hosts or deploys the handler runtime
  • keep --settle-8183 reserved but disabled for x402/MPP until ERC-8183 service-job support exists

Notes

  • deploy currently creates a Docker-ready bundle and next steps; it does not execute a hosting-provider deployment
  • provider runtime needs ACP_AGENT_TOKEN and outbound access to BE

Tests

  • npm run build
  • tsx bin/acp.ts serve endpoints --dir /tmp/acp-cli-smoke --json

Note

High Risk
Adds a new provider runtime that verifies and settles x402/MPP payments and signs on-chain transactions via a configured private key, which is security- and funds-critical. Also introduces new token-auth flows and deployment bundling that may affect how credentials and config are handled in production.

Overview
Adds a new acp serve feature set to scaffold, run, and (optionally) deploy a provider-side “service-job” runtime that connects outbound to the BE /service-jobs Socket.IO namespace.

The runtime loads a developer handler.ts (plus optional budget.ts), serves a /health endpoint, can run a native ACP listener for registry jobs, and for BE-mediated jobs builds payment challenges and verifies/settles x402 (EIP-3009 USDC) and MPP (tempo via mppx) credentials before invoking the handler; --settle-8183 is explicitly reserved but blocked for x402/MPP.

CLI/config/auth updates support the new flow: registers serve commands (init/start/endpoints/deploy/stop/logs), adds agent-token issuance via /auth/agent (message signing) and stores it in config/env, centralizes API URL selection via getApiUrl(), and adds new dependencies (@x402/*, mppx) plus viem/lockfile bumps.

Reviewed by Cursor Bugbot for commit 6eccf1e. Bugbot is set up for automated code reviews on this repo. Configure here.

Comment thread src/commands/serve.ts
Comment thread src/commands/serve.ts Outdated
Comment thread serve/server/index.ts
Comment thread src/commands/serve.ts Outdated
Comment thread serve/runtime/loader.ts Outdated
Comment thread src/commands/serve.ts
Comment thread serve/runtime/sandbox.ts
Comment thread serve/server/index.ts
Comment thread serve/server/payment/chain.ts Outdated
Comment thread serve/server/payment/mpp.ts
Comment thread src/commands/serve.ts
Comment thread src/commands/serve.ts Outdated
Comment thread serve/server/payment/chain.ts
Comment thread serve/server/payment/chain.ts
Comment thread src/commands/serve.ts Outdated
Comment thread src/commands/serve.ts Outdated
Copy link
Copy Markdown

@cursor cursor Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes and found 2 potential issues.

Fix All in Cursor

❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.

Reviewed by Cursor Bugbot for commit 6eccf1e. Configure here.

Comment thread src/commands/serve.ts
process.kill(pid, "SIGTERM");
stopped += 1;
} catch {}
break;
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Unconditional break prevents fallback to legacy PID files

Medium Severity

The break statement in the stop command's PID file loop is unconditional — it sits outside the try/catch, so it always executes after the first existing PID file is found, even when process.kill() throws (e.g., stale PID). This prevents the loop from falling through to check the legacy PID file path, which is the entire reason the loop and pidFiles array exist.

Fix in Cursor Fix in Web

Reviewed by Cursor Bugbot for commit 6eccf1e. Configure here.

Comment thread src/commands/serve.ts
"package-lock.json",
"tsconfig.json",
]) {
const source = resolve(process.cwd(), relativePath);
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Deploy bundle copies from cwd instead of CLI source

Medium Severity

copyRuntimeBundle resolves CLI source directories (bin, src, serve, etc.) relative to process.cwd(), but process.cwd() is the user's working directory, not the CLI package's installation directory. The init command correctly uses import.meta.url to locate scaffold files, but deploy does not, so the bundle will silently miss CLI source files if the command is run from a directory other than the repo root.

Fix in Cursor Fix in Web

Reviewed by Cursor Bugbot for commit 6eccf1e. Configure here.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant