CoderClaw uses Bonjour (mDNS / DNS‑SD) as a LAN‑only convenience to discover an active Gateway (WebSocket endpoint). It is best‑effort and does not replace SSH or Tailnet-based connectivity.
If the node and gateway are on different networks, multicast mDNS won’t cross the boundary. You can keep the same discovery UX by switching to unicast DNS‑SD (“Wide‑Area Bonjour”) over Tailscale.
High‑level steps:
_coderclaw-gw._tcp under a dedicated zone
(example: coderclaw.internal.).CoderClaw supports any discovery domain; coderclaw.internal. is just an example.
iOS/Android nodes browse both local. and your configured wide‑area domain.
{
gateway: { bind: "tailnet" }, // tailnet-only (recommended)
discovery: { wideArea: { enabled: true } }, // enables wide-area DNS-SD publishing
}
coderclaw dns setup --apply
This installs CoreDNS and configures it to:
coderclaw.internal.) from ~/.coderclaw/dns/<domain>.dbValidate from a tailnet‑connected machine:
dns-sd -B _coderclaw-gw._tcp coderclaw.internal.
dig @<TAILNET_IPV4> -p 53 _coderclaw-gw._tcp.coderclaw.internal PTR +short
In the Tailscale admin console:
Once clients accept tailnet DNS, iOS nodes can browse
_coderclaw-gw._tcp in your discovery domain without multicast.
The Gateway WS port (default 18789) binds to loopback by default. For LAN/tailnet
access, bind explicitly and keep auth enabled.
For tailnet‑only setups:
gateway.bind: "tailnet" in ~/.coderclaw/coderclaw.json.Only the Gateway advertises _coderclaw-gw._tcp.
_coderclaw-gw._tcp — gateway transport beacon (used by macOS/iOS/Android nodes).The Gateway advertises small non‑secret hints to make UI flows convenient:
role=gatewaydisplayName=<friendly name>lanHost=<hostname>.localgatewayPort=<port> (Gateway WS + HTTP)gatewayTls=1 (only when TLS is enabled)gatewayTlsSha256=<sha256> (only when TLS is enabled and fingerprint is available)canvasPort=<port> (only when the canvas host is enabled; currently the same as gatewayPort)sshPort=<port> (defaults to 22 when not overridden)transport=gatewaycliPath=<path> (optional; absolute path to a runnable coderclaw entrypoint)tailnetDns=<magicdns> (optional hint when Tailnet is available)Security notes:
lanHost, tailnetDns, gatewayPort, and gatewayTlsSha256 as hints only.gatewayTlsSha256 to override a previously stored pin.Useful built‑in tools:
Browse instances:
dns-sd -B _coderclaw-gw._tcp local.
Resolve one instance (replace <instance>):
dns-sd -L "<instance>" _coderclaw-gw._tcp local.
If browsing works but resolving fails, you’re usually hitting a LAN policy or mDNS resolver issue.
The Gateway writes a rolling log file (printed on startup as
gateway log file: ...). Look for bonjour: lines, especially:
bonjour: advertise failed ...bonjour: ... name conflict resolved / hostname conflict resolvedbonjour: watchdog detected non-announced service ...The iOS node uses NWBrowser to discover _coderclaw-gw._tcp.
To capture logs:
The log includes browser state transitions and result‑set changes.
\032)Bonjour/DNS‑SD often escapes bytes in service instance names as decimal \DDD
sequences (e.g. spaces become \032).
BonjourEscapes.decode).CODERCLAW_DISABLE_BONJOUR=1 disables advertising (legacy: CODERCLAW_DISABLE_BONJOUR).gateway.bind in ~/.coderclaw/coderclaw.json controls the Gateway bind mode.CODERCLAW_SSH_PORT overrides the SSH port advertised in TXT (legacy: CODERCLAW_SSH_PORT).CODERCLAW_TAILNET_DNS publishes a MagicDNS hint in TXT (legacy: CODERCLAW_TAILNET_DNS).CODERCLAW_CLI_PATH overrides the advertised CLI path (legacy: CODERCLAW_CLI_PATH).