Discord Forum 스레드와 Codex 세션을 1:1로 연결하는 로컬 브리지 서버다. 각 Forum 스레드는 생성 시점에 고유한 Codex session key를 받고, 이후 /plan, /run, /status, /pause, /resume 명령은 항상 같은 세션으로 전달된다.
이 구현은 Agents SDK가 아니라 Codex CLI resume 방식을 사용한다. 새 스레드 생성 시 codex exec --json으로 실제 세션을 만들고, 이후 codex exec resume --json <session_id>로 같은 세션을 재사용한다.
- Python 3.14
- 로컬에 설치된
codexCLI - Codex CLI 로그인 완료 상태
- Discord Bot Token, Guild ID, Forum Channel ID
uv venv .venv --python "$(which python3)"
source .venv/bin/activate
uv sync --active
cp .env.example .env.env 파일을 채운 뒤 실행한다.
uv run python -m threadpilot.appFastAPI 서버는 기본값으로 http://127.0.0.1:8765 에서 뜬다.
GET /healthGET /threads/{thread_id}/status
동시에 Discord bot도 같은 프로세스에서 실행된다.
운영 로그는 기본값으로 ./logs/threadpilot.log에 기록되며, 콘솔에도 함께 출력된다. 로그 파일은 UTC 기준 일 단위로 회전하고 기본 14일을 유지한다.
대화 본문이 들어가는 SQLite message_logs는 운영 로그와 별도로 관리되며, 앱 시작 시 기본 30일보다 오래된 행을 정리한다.
설정 가능한 로그 관련 환경 변수:
LOG_DIR: 로그 파일 디렉터리, 기본값./logsLOG_LEVEL: 로그 레벨, 기본값INFOLOG_RETENTION_DAYS: 파일 로그 보관 일수, 기본값14MESSAGE_LOG_RETENTION_DAYS:message_logs보관 일수,0이면 정리 비활성화, 기본값30
- Discord Developer Portal에서 애플리케이션과 봇을 만든다.
- 봇을 대상 서버에 초대한다.
- 봇이 Forum 스레드에서 메시지 전송과 앱 커맨드 사용 권한을 갖도록 설정한다.
- 명령은 길드 스코프 슬래시 커맨드로 등록된다.
- 대상 Forum 채널 ID를
.env의DISCORD_FORUM_CHANNEL_ID에 넣는다.
/plan prompt:<text>- 같은 스레드의 기존 Codex 세션에 계획 요청을 보낸다.
/run prompt:<text>- 같은 스레드의 기존 Codex 세션에 실행 요청을 보낸다.
/status- 현재 session key, 상태, 최근 실행 시각, 최근 오류를 보여준다.
/pause- 새
/plan,/run접수를 막는다.
- 새
/resume- paused 상태를 해제한다.
일반 잡담 메시지는 처리하지 않는다. 앱 커맨드만 처리한다.
앱 시작 시 SQLite 파일을 만들고 아래 테이블을 초기화한다.
session_bindingsthread_id,codex_session_key,status,last_run_at,last_error
message_logs- Discord 요청/응답/오류 로그
- 스레드별 동시 실행은
asyncio.Lock으로 1개만 허용한다. - 앱 재시작 시 남아 있던
running상태는idle로 복구한다. - Codex CLI의 stderr 경고는 내부 로그로 남고, Discord에는 짧은 오류 메시지만 보낸다.
- 현재 구현은 로컬 단일 프로세스 기준 최소 버전이다. 프로세스가 재시작되면 메모리 큐는 초기화된다.
문법 검증:
uv run python -m py_compile threadpilot/app.py threadpilot/discord_bot.py threadpilot/db.py threadpilot/models.py threadpilot/session_manager.py threadpilot/codex_runner.py threadpilot/queue_manager.py threadpilot/config.py threadpilot/logging_config.py런타임 검증:
uv run python -m threadpilot.app
curl http://127.0.0.1:8765/health- 의존성 추가:
uv add <package> - 의존성 동기화:
uv sync - 전용 가상환경 경로:
.venv