42 Commits
Author SHA1 Message Date
ethanfelandClaude Opus 4.8 8bb07a962f feat: optional 'signal' input on Agent Receive for execution ordering
Add a wildcard (any-type) optional 'signal' input to Agent Receive. Wiring any
upstream output into it creates a dependency edge so ComfyUI runs that node
first — e.g. force an Agent Emit (send the prompt) to fire before Receive starts
waiting. The value is ignored; presence is what orders execution.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-30 21:25:50 +02:00
ethanfelandClaude Opus 4.8 fbd9087758 feat(examples): --ip/--port flags instead of full bridge URL
push.py and console_relay.py take --ip (default 127.0.0.1) and --port (9188),
building http://<ip>:<port>/mcp; --url still overrides. console_relay.sh takes
the IP as its first arg (./console_relay.sh 192.168.1.12) or prompts for it.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-29 19:21:42 +02:00
ethanfelandClaude Opus 4.8 0de2d8bb45 feat: examples/console_relay.sh interactive launcher (pick pane, set channel, run)
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-29 19:18:32 +02:00
ethanfelandClaude Opus 4.8 e6870826a0 docs: add examples/console_relay.py (relay a channel into a tmux pane)
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-29 19:14:57 +02:00
ethanfelandClaude Opus 4.8 3bf02078ed docs: add examples/push.py manual test client
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-29 11:07:46 +02:00
ethanfelandClaude Opus 4.8 654325fe34 feat: detailed channel logging + sender-side validation/warnings
Every emit/pull/push/receive now logs to the ComfyUI console with channel,
text preview, image path, and seed. comfy_push validates the sender's input and
emits clear '⚠ SENDER PROBLEM' warnings (also returned to the agent) when an
image_path doesn't exist on the host, a wrong type is passed, or the message is
empty. Agent Receive logs each step and, instead of crashing on a bad/missing
image path, logs exactly what the sender got wrong and falls back to a blank
image. Helps diagnose 'error when receiving' caused by the sender.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-29 11:03:37 +02:00
ethanfel 58cc66e666 Revert "feat: FIFO queue channels (no dropped messages)"
This reverts commit bbe96f366a.
2026-06-29 10:43:56 +02:00
ethanfelandClaude Opus 4.8 bbe96f366a feat: FIFO queue channels (no dropped messages)
Replace the single-slot inbox/outbox with FIFO deques: every emit and push is
kept and delivered oldest-first, exactly once. comfy_pull and Agent Receive now
dequeue the oldest item (empty when drained) instead of overwriting/replaying the
latest. keep_last now holds the last *delivered* message (store.peek returns
last_out). list_channels reports in_pending/out_pending depths. Docs + tests
updated for FIFO ordering.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-29 01:31:04 +02:00
ethanfelandClaude Opus 4.8 cee71f7f0b feat: carry seed (INT) across the bridge
Add a seed lane alongside text/image: Agent Emit gains an optional seed input
(graph -> agent), Agent Receive gains a seed output (agent -> graph, 0 if none),
and comfy_pull/comfy_push carry it. Wire a KSampler seed into Emit to tell the
agent, or have the agent comfy_push(seed=...) to drive the next generation.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 22:13:08 +02:00
ethanfelandClaude Opus 4.8 1f4950dec8 feat: Agent Receive honors ComfyUI Cancel during the wait
The blocking receive sat in a single cond.wait() and never checked ComfyUI's
interrupt flag, so Cancel didn't stop it. receive() now takes a should_abort
callback and waits in short slices; the node passes ComfyUI's
throw_exception_if_processing_interrupted so hitting Cancel breaks out promptly
(no-op outside ComfyUI). Covered by an abort test.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 19:15:03 +02:00
ethanfelandClaude Opus 4.8 ff46f865bf feat: Agent Receive keep_last (sticky) + stop_on_timeout (halt Auto Queue)
keep_last: on timeout, re-output the last message (via new store.peek, which
reads the outbox without consuming) instead of blanking - holds the display
steady between messages in Auto Queue.

stop_on_timeout: on timeout, send an 'agent-bridge-stop-autoqueue' event; a new
web/ JS extension toggles ComfyUI's Auto Queue off so the loop halts when the
stream goes quiet (best-effort across frontend versions). Registers WEB_DIRECTORY.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 17:53:45 +02:00
ethanfelandClaude Opus 4.8 238c60585f fix: process-global ChannelStore so MCP server and nodes share one store
ComfyUI can import the store module under two identities (one for the nodes, one
for the in-process MCP server), giving each its own class-level singleton. Result:
an agent's comfy_push went to one store while the node-side Agent Receive read the
other, so messages never crossed (the reported 'no text' / 30s timeouts). Stash
the singleton on builtins so it's one instance per process regardless of import
path. Reproduced with a dual-module-identity test.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 17:40:50 +02:00
ethanfelandClaude Opus 4.8 ec138ad80e fix: Agent Receive re-runs every queue (IS_CHANGED) to pick up new messages
ComfyUI caches a node's output unless its inputs change. Agent Receive's inputs
(channel, wait_seconds) are constant, so re-queuing served a stale cached result
instead of the agent's newly pushed message. Add IS_CHANGED returning NaN so the
node is always dirty and re-polls the channel on every queue.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 17:10:42 +02:00
ethanfelandClaude Opus 4.8 783a294d43 feat: load nodes even when optional 'mcp' is missing; clearer hint
A missing 'mcp' package made the whole custom_node load fail with
ModuleNotFoundError. Now the Agent Emit/Receive nodes register regardless and the
bridge prints an actionable install hint (with ComfyUI's python path) instead of
crashing. Use __package__ to pick relative vs sys.path import so a broad except
no longer masks a missing-dependency error. Adds a no-mcp load test.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 16:23:48 +02:00
ethanfelandClaude Opus 4.8 1a2ec7c07a fix: relative imports so ComfyUI can load the custom node
ComfyUI execs __init__.py as a package without the node dir on sys.path, so the
absolute 'from src...' imports raised ModuleNotFoundError: No module named
'src.nodes'. Switch internal modules to package-relative imports and import them
relatively in __init__ (with a sys.path fallback for standalone/test use, so no
generic 'src' leaks onto sys.path to collide with other custom nodes). Adds a
regression test that loads the package the way ComfyUI does.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 15:56:27 +02:00
ethanfelandClaude Opus 4.8 08c0e1aa7a feat: default image temp dir to ComfyUI output + optional path translation
Zero-config images for remote/Docker: default COMFY_BRIDGE_TMP to ComfyUI's
output dir (output/agent_bridge via folder_paths), which is typically a shared
same-path mount, so comfy_pull/comfy_push paths resolve on both sides. For
containers that mount that folder at a different internal path, add
COMFY_BRIDGE_TMP_PUBLIC: comfy_pull advertises the agent-visible path and
comfy_push translates it back.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 15:42:30 +02:00
ethanfelandClaude Opus 4.8 de6c54cd8a feat: COMFY_BRIDGE_MCP_HOST to bind 0.0.0.0 for Docker/remote access
Adds a host bind env var (mirrors the port var) plus a README section on
running ComfyUI in Docker: bind 0.0.0.0, publish the port, point the agent at
the server IP, and handle images via a shared folder with matching paths.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 14:51:25 +02:00
ethanfelandClaude Opus 4.8 e7c06c1905 docs: point install instructions at the published GitHub repo
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 14:37:28 +02:00
ethanfelandClaude Opus 4.8 903ede1436 docs: lead README 'Connecting an agent' with Codex plugin install
Lead the section with the Codex plugin install (codex plugin marketplace
add + codex plugin add), which auto-registers the comfy MCP server, then
the simpler 'codex mcp add comfy --url ...', keep the stdio shim fallback,
and the Claude Code HTTP command. Commands match what was verified on
codex-cli 0.142.3.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 14:07:51 +02:00
ethanfelandClaude Opus 4.8 554a1365a8 feat: Codex plugin + marketplace manifests
Package the repo as a folder-installable Codex plugin (verified on
codex-cli 0.142.3):

- .agents/plugins/marketplace.json: marketplace 'comfyui-agents' listing
  the repo root itself as the plugin (source.path '.'), policy
  authentication ON_USE so the local no-auth HTTP server installs without
  an OAuth prompt.
- .codex-plugin/plugin.json: plugin 'comfyui-agents', skills ./skills/,
  mcpServers ./.codex-plugin/mcp.json (string-file form, matching the
  real OpenAI connector plugins).
- .codex-plugin/mcp.json: declares the 'comfy' HTTP MCP server at
  http://127.0.0.1:9188/mcp via {type: http}; Codex registers it as a
  streamable_http transport.
- skills/comfyui-bridge/SKILL.md: concise skill teaching the named-channel
  model, the five tools, and the core push/run/pull loop.

Verified: codex plugin marketplace add . -> codex plugin add
comfyui-agents@comfyui-agents -> codex mcp get comfy reports the URL.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 14:07:51 +02:00
ethanfelandClaude Opus 4.8 28dfd22c16 docs: Codex setup + reconcile MCP port in design doc
README: add a Codex section with both connection methods (HTTP url entry
and the stdio shim), matching the schema codex 0.142.3 writes; note that
AgentReceive's wait_seconds blocks a ComfyUI worker; add COMFY_BRIDGE_TMP_TTL
to the env-vars table. Design doc: add a decisions-log line recording that
the MCP server ships on a separate daemon-thread side port (9188, /mcp).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 14:02:20 +02:00
ethanfelandClaude Opus 4.8 f80ed87b94 docs: note run_workflow poll is best-effort
Add a comment clarifying the run_workflow history poll returns as soon as
any output node appears, and that the design's upgrade path is the ComfyUI
websocket `executed` event.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 14:00:50 +02:00
ethanfelandClaude Opus 4.8 71aa6b9f5e refactor: use X | None instead of Optional
Switch store.py and workflows.py to the PEP 604 X | None syntax and drop
the now-unused `from typing import Optional`. Pure refactor; no behavior
change.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 14:00:32 +02:00
ethanfelandClaude Opus 4.8 339658dd31 chore: drop deprecated Pillow mode= arg
Image.fromarray(arr) infers RGB from the (H,W,3) array shape; the explicit
mode="RGB" is deprecated in Pillow and slated for removal in 13. Clears the
three Pillow DeprecationWarnings.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 13:59:51 +02:00
ethanfelandClaude Opus 4.8 aea5ffdd5c feat: age-based GC for temp images
save_tensor_png now reaps img_*.png files older than COMFY_BRIDGE_TMP_TTL
(env, default 3600s) after each write, so .comfy_bridge_tmp/ no longer
grows forever. Robust to races (ignores FileNotFoundError/OSError) and
never deletes the file just written.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 13:59:19 +02:00
ethanfelandClaude Opus 4.8 4c0e9d9b07 feat: real stdio<->HTTP MCP proxy for Codex CLI
Replace the honest stub with a working stdio<->streamable-HTTP MCP proxy:
connect upstream to COMFY_BRIDGE_URL as an HTTP MCP client, then run a
low-level stdio MCP server whose list_tools/call_tool forward to the
upstream session. Exits non-zero with a clear stderr message on connection
failure. Adds a real end-to-end round-trip test (boots the in-process
bridge on a free port, spawns the shim, drives it via a stdio MCP client).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 13:58:17 +02:00
ethanfel 8fe1a76f59 test: full suite green + manual verification notes 2026-06-28 13:50:55 +02:00
ethanfel 8e4c2e58bd docs: README + Codex stdio shim scaffold 2026-06-28 13:50:37 +02:00
ethanfel 899de4df44 feat: ComfyUI entrypoint with node mappings + MCP autostart 2026-06-28 13:47:51 +02:00
ethanfel cd88f9cd10 feat: FastMCP server build + background lifecycle 2026-06-28 13:47:09 +02:00
ethanfel 03d0f49852 feat: SDK-independent MCP tool functions 2026-06-28 13:42:47 +02:00
ethanfel d4a48e00fd feat: thin async submit_prompt + fetch_result 2026-06-28 13:42:13 +02:00
ethanfel 4b0d53811f feat: workflow load + input injection (pure) 2026-06-28 13:41:43 +02:00
ethanfel 376a11663f feat: Agent Receive node (agent->graph) 2026-06-28 13:38:26 +02:00
ethanfel 262a68d62d feat: Agent Emit node (graph->agent) 2026-06-28 13:37:55 +02:00
ethanfel 561d38aff5 feat: tensor<->PNG image helpers 2026-06-28 13:37:21 +02:00
ethanfel 962960f420 feat: ChannelStore.list_channels 2026-06-28 13:21:26 +02:00
ethanfel 1fd72eac0b feat: ChannelStore outbox (agent->graph) with consume + blocking receive 2026-06-28 13:20:55 +02:00
ethanfel 055eedee24 feat: ChannelStore inbox (graph->agent) with emit/pull 2026-06-28 13:20:19 +02:00
ethanfel 3ffb1d21c3 chore: scaffold comfyui-nodes-agents package 2026-06-28 13:19:46 +02:00
ethanfelandClaude Opus 4.8 4f607ae2c8 docs: ComfyUI Agent Bridge implementation plan
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 13:15:31 +02:00
ethanfelandClaude Opus 4.8 430c1f89df docs: ComfyUI Agent Bridge design
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 13:11:28 +02:00