add-dial-number
既存のダイヤルチャンネルにもう一つの電話番号を追加すれば、エージェント用の2つ目(または3つ目)の公衆回線として、1つのNanoClawのインストールで複数の番号のSMSやAI音声通話に応答できます。
Add another Dial number
One NanoClaw install can serve multiple Dial numbers at once. Each number is
its own public, threaded line — its own messaging group (platform_id = the
Dial number), each remote correspondent a thread inside it — and the agent
replies from whichever number a person texted.
This skill is for adding a number to an already-installed Dial channel. Its
mechanical steps use nc: directives so an agent and the deterministic skill
engine perform the same validated, idempotent workflow.
Pre-flight
Confirm Dial is installed and registered. If this fails, run /add-dial first,
then retry:
test -f src/channels/dial.ts && grep -q "import './dial.js';" src/channels/index.ts
Adding another number requires the multi-number adapter, which routes on the
line each event arrived on (data.to). If this fails, run /update-skills to
refresh the installed adapter, rebuild, and retry:
grep -q "eventLine" src/channels/dial.ts
Resolve the Dial CLI and the install's user-agent token once for every account request below:
command -v dial
node -p "'nanoclaw/'+(require('./package.json').version||'unknown')" 2>/dev/null || echo nanoclaw/unknown
Choose the number
List the account's current numbers:
DIAL_USER_AGENT={{dial_ua}} "{{dial_path}}" number list --json | jq -r 'if (.numbers|length)==0 then "none" else [.numbers[].number] | join(", ") end'
Tell the operator what is available. Buying a number spends account funds, so
leave that explicit: if they need a new one, they should purchase it with
dial number purchase --inbound-instruction "…" --explicit-programmatic-consent "<account-holder consent attestation>", then enter the returned number below.
Dial numbers on this account: {{dial_numbers}}. Choose one that is not already wired to NanoClaw. If you need a new number, purchase it first; this may charge the Dial account.
Which Dial number should be added? Enter its E.164 value, for example +14155550123.
Verify that the chosen number belongs to the signed-in account:
DIAL_USER_AGENT={{dial_ua}} "{{dial_path}}" number list --json | jq -e --arg number '{{platform_id}}' '.numbers[] | select(.number==$number)' >/dev/null
Choose the agent
List the agent groups:
ncl groups list --json | jq -r 'if (.data|length)==0 then "no agent groups yet" else [.data[] | "\(.id) (\(.name))"] | join(", ") end'
Agent groups on this install: {{agent_groups}}.
Which agent group should answer this number? Enter its ag-… id.
Reject a typo before creating anything:
ncl groups list --json | jq -e --arg id '{{agent_group_id}}' '.data[] | select(.id==$id)' >/dev/null
Choose a safe display name and who may start conversations on this line.
strict admits only known users; public lets anyone who knows the number reach
the agent. The choice belongs to this number and does not change existing lines:
What should this line be called? Use letters, numbers, spaces, dots, dashes, or underscores.
Who may text this line: strict or public?
Wire the line
Create the threaded Dial messaging group. This is idempotent on the number, so a re-run returns an existing row without resetting later policy changes:
ncl messaging-groups create --channel-type dial --platform-id {{platform_id}} --is-group 1 --name "{{line_name}}" --unknown-sender-policy {{inbound_access}}
Wire it to the selected agent group. The adapter's declaration supplies the thread and engagement defaults:
ncl wirings create --channel-type dial --platform-id {{platform_id}} --agent-group-id {{agent_group_id}}
Restart and verify
Restart the service so the new line is picked up consistently:
bash setup/lib/restart.sh
Verify the exact messaging-group and wiring pair exists:
mg=$(ncl messaging-groups list --json | jq -er --arg number '{{platform_id}}' '.data[] | select(.channel_type=="dial" and .platform_id==$number) | .id') && ncl wirings list --json | jq -e --arg mg "$mg" --arg ag '{{agent_group_id}}' '.data[] | select(.messaging_group_id==$mg and .agent_group_id==$ag)' >/dev/null
The new number now reaches the selected agent as a separate threaded line, and replies leave from the number that received the message. Existing lines are unchanged.
Troubleshooting
- The multi-number check fails → run
/update-skills, rebuild, and retry. - The selected number is rejected → sign in to the correct Dial account or purchase the number first, then copy its exact E.164 value.
- New texts land in an old line or replies use the wrong number → the running service still has the old adapter; refresh it and restart again.
- New inbound events never arrive → one
dial listendaemon covers the whole account; confirmdial doctor --jsonreportslisten.running: trueanddial local-target list --jsoncontains NanoClaw's command target. nclerrors → the host service must be running;nclconnects over a Unix socket.