153 lines
5.2 KiB
Markdown
153 lines
5.2 KiB
Markdown
# NAS Telegram Codex Bridge
|
|
|
|
Telegram bridge for a NAS-hosted Codex app-server.
|
|
|
|
The bot does not interpret normal chat messages. It forwards them to Codex and
|
|
only keeps connection-management commands.
|
|
|
|
## Commands
|
|
|
|
```text
|
|
/start
|
|
/help
|
|
/whoami
|
|
/repo <path-under-workspace-root>
|
|
/ask <prompt>
|
|
/work <prompt>
|
|
/usage
|
|
/new
|
|
/status
|
|
/settings
|
|
/set_model <model|latest|default>
|
|
/set_effort <minimal|low|medium|high|xhigh|default>
|
|
/set_speed <standard|fast|보통|고속|default>
|
|
/fast <on|off|status>
|
|
/models
|
|
/schedules
|
|
/records
|
|
/todos
|
|
/purchases
|
|
/birthdays
|
|
/sessions
|
|
/sessions archived
|
|
/use_session <thread_id>
|
|
/archive_session [thread_id]
|
|
/unarchive_session <thread_id>
|
|
```
|
|
|
|
`ALLOW_PLAIN_TEXT=true` makes regular Telegram messages behave like `/ask`.
|
|
Use `/work <prompt>` for write-capable tasks such as editing files, committing,
|
|
pushing, or opening pull requests. Plain text and `/ask` stay read-oriented by
|
|
default.
|
|
|
|
On Synology/NAS Docker deployments, keep `CODEX_WRITE_SANDBOX=danger-full-access`
|
|
for `/work`. The stricter `workspace-write` sandbox may fail with bubblewrap
|
|
namespace errors inside the container.
|
|
|
|
If no `/repo` is set, the bridge tries to auto-select a workspace folder when a
|
|
Telegram prompt mentions an exact folder name such as `card_game` or
|
|
`nas_connection`. Use `/repo <name>` when you want to pin the workspace
|
|
explicitly.
|
|
|
|
`/settings`, `/models`, `/schedules`, `/records`, and `/sessions` return inline
|
|
buttons, so you can change speed/model/reasoning settings, delete schedules,
|
|
manage personal records, and switch or archive sessions without copying ids.
|
|
`/usage` asks the local Codex app-server for account, plan, rate-limit, and
|
|
credit information when the installed Codex version exposes it.
|
|
|
|
## Runtime settings
|
|
|
|
Runtime settings are stored in `BOT_STATE_PATH` and applied to new turns:
|
|
|
|
- `model`, for example `gpt-5.5`
|
|
- `reasoning_effort`: `minimal`, `low`, `medium`, `high`, or `xhigh`
|
|
- `speed_mode`: `standard` or `fast`
|
|
|
|
Changing these settings closes existing persistent WebSocket clients. The next
|
|
Telegram message reconnects with the updated settings. Fast mode requires a
|
|
supported model/account; if the local Codex app-server rejects an override, the
|
|
bridge retries with narrower settings rather than failing the whole turn.
|
|
|
|
The model picker first tries `codex debug models` inside the NAS container and
|
|
builds buttons from the model catalog Codex sees. If that fails, it falls back
|
|
to a short built-in list.
|
|
|
|
## Scheduling
|
|
|
|
The bridge registers a local MCP server named `telegram_bridge` in
|
|
`$CODEX_HOME/config.toml`. Codex can call these tools when the user asks for
|
|
scheduled Telegram notifications:
|
|
|
|
- `telegram_create_schedule`
|
|
- `telegram_list_schedules`
|
|
- `telegram_delete_schedule`
|
|
|
|
## Personal assistant records
|
|
|
|
Codex can persist personal assistant records to the same NAS-backed state file.
|
|
Use natural language in Telegram, for example:
|
|
|
|
```text
|
|
이건 업무 이력으로 저장해줘. 2025-09-15부터 2026-04-15까지 전국통합데이터 개방확대 사업에 참여했어.
|
|
이건 할 일로 기억해줘. 다음 주까지 신세계 TV쇼핑 채팅 연동 QA 정리.
|
|
구매 후보로 저장해줘. 모니터암 가격 8만원 이하가 되면 사고 싶어.
|
|
어머니 생일은 5월 12일이야. 기억해줘.
|
|
```
|
|
|
|
Codex uses these MCP tools:
|
|
|
|
- `telegram_save_personal_record`
|
|
- `telegram_list_personal_records`
|
|
- `telegram_update_personal_record`
|
|
- `telegram_delete_personal_record`
|
|
|
|
Record categories are `work_log`, `todo`, `purchase`, `birthday`, `contact`,
|
|
`note`, and `preference`. Telegram commands `/records`, `/todos`, `/purchases`,
|
|
and `/birthdays` show records with management buttons.
|
|
|
|
The bridge scheduler runs inside the Telegram bot process. When a schedule is
|
|
due, it calls Codex app-server and sends the result back to the stored Telegram
|
|
chat id.
|
|
|
|
## Gitea integration
|
|
|
|
Set these optional values in `.env` to let Codex manage Gitea repositories,
|
|
issues, pull requests, and HTTPS git authentication from Telegram:
|
|
|
|
```env
|
|
GITEA_BASE_URL=https://gitea.example.com
|
|
GITEA_USERNAME=your-gitea-user
|
|
GITEA_EMAIL=you@example.com
|
|
GITEA_TOKEN=your-personal-access-token
|
|
GITEA_DEFAULT_OWNER=your-gitea-user-or-org
|
|
GITEA_DEFAULT_REPO=your-default-repo
|
|
GITEA_GIT_AUTH_ENABLED=true
|
|
```
|
|
|
|
Codex receives Gitea MCP tools for repository, issue, branch, and pull-request
|
|
metadata. The container also configures `GIT_ASKPASS` so HTTPS `git clone`,
|
|
`fetch`, and `push` can use the token without embedding it in command lines.
|
|
|
|
Example Telegram workflow:
|
|
|
|
```text
|
|
/repo nas_connection
|
|
/work 이슈 #3을 확인하고 코드 수정 후 테스트해. 변경사항을 codex/gitea-tools 브랜치로 커밋하고 push한 뒤 PR을 열어줘.
|
|
```
|
|
|
|
## Deployment
|
|
|
|
1. Copy `.env.example` to `.env`.
|
|
2. Fill `TELEGRAM_BOT_TOKEN`.
|
|
3. Use `/whoami` to find your Telegram user id and set
|
|
`ALLOWED_TELEGRAM_USER_IDS`.
|
|
4. Run `docker compose up -d --build`, or use `deploy/deploy.ps1` for the NAS.
|
|
|
|
## Notes
|
|
|
|
- Codex state and auth live under the mounted `codex-home` volume.
|
|
- The app-server listens on `ws://127.0.0.1:4500` inside the container.
|
|
- Normal chat messages use a persistent app-server WebSocket per Telegram chat.
|
|
- Idle persistent WebSockets are closed after `PERSISTENT_WS_IDLE_SECONDS`.
|
|
- Session commands call app-server thread APIs.
|