{"openapi":"3.1.0","info":{"title":"DCEC Platform","version":"0.1.0"},"paths":{"/api/v1/health":{"get":{"tags":["health"],"summary":"Liveness","description":"HEALTHCHECK 용.","operationId":"liveness_api_v1_health_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/health/details":{"get":{"tags":["health"],"summary":"Readiness","description":"DB + Redis + Docker 연결 상태.","operationId":"readiness_api_v1_health_details_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/health/resources":{"get":{"tags":["health"],"summary":"Resources","description":"NAS 리소스 (CPU/RAM/디스크).","operationId":"resources_api_v1_health_resources_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/health/summary":{"get":{"tags":["health"],"summary":"Summary","description":"10초 비동기 NAS 상태 스냅샷.","operationId":"summary_api_v1_health_summary_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/health/watchdog":{"get":{"tags":["health"],"summary":"Watchdog Events","description":"Watchdog 관제 목록 — 컨테이너 이벤트 **+ 도메인 이상**.\n\n2026-09-01 사용자 지시(\"Watchdog 관제 목록에 도메인도 포함 시켜\"). 종전에는 컨테이너\n재시작 이벤트만 봤는데, 이 시스템에서 실제로 겪는 장애는 **도메인이 안 열리는 것**이고\n그 원인(인증서 만료·DDNS 정지·라우팅 규칙 누락)은 컨테이너가 멀쩡해도 발생한다.\n\n도메인 점검이 실패해도 컨테이너 이벤트는 그대로 돌려준다 — 새 관심사가 기존 관제를\n끄면 안 된다.","operationId":"watchdog_events_api_v1_health_watchdog_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":20,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/health/serving-cert":{"get":{"tags":["health"],"summary":"Serving Cert","description":"실제 서비스되는 TLS 인증서(관제 도메인 정보의 정본).\n\n`host` 미지정 시 요청의 Host 헤더를 쓴다 — DSM 리버스 프록시가 원 Host 를 전달하므로\n\"지금 이 화면이 어느 도메인으로 서비스되는가\"가 그대로 측정 대상이 된다.","operationId":"serving_cert_api_v1_health_serving_cert_get","parameters":[{"name":"host","in":"query","required":false,"schema":{"type":"string","default":"","title":"Host"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/status":{"get":{"tags":["status"],"summary":"Service Status","description":"서비스 가동상태 집계 (공개). 민감 정보 없음 — up/down·버전·런타임 **전부 실측**.","operationId":"service_status_api_v1_status_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/docker/containers":{"get":{"tags":["docker"],"summary":"List Containers","description":"컨테이너 목록.","operationId":"list_containers_api_v1_docker_containers_get","parameters":[{"name":"all","in":"query","required":false,"schema":{"type":"boolean","default":true,"title":"All"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/docker/containers/{container_id}":{"get":{"tags":["docker"],"summary":"Get Container","description":"컨테이너 상세.","operationId":"get_container_api_v1_docker_containers__container_id__get","parameters":[{"name":"container_id","in":"path","required":true,"schema":{"type":"string","title":"Container Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/docker/containers/{container_id}/restart":{"post":{"tags":["docker"],"summary":"Restart Container","description":"컨테이너 재시작.","operationId":"restart_container_api_v1_docker_containers__container_id__restart_post","parameters":[{"name":"container_id","in":"path","required":true,"schema":{"type":"string","title":"Container Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/docker/containers/{container_id}/stop":{"post":{"tags":["docker"],"summary":"Stop Container","description":"컨테이너 중지.","operationId":"stop_container_api_v1_docker_containers__container_id__stop_post","parameters":[{"name":"container_id","in":"path","required":true,"schema":{"type":"string","title":"Container Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/docker/containers/{container_id}/start":{"post":{"tags":["docker"],"summary":"Start Container","description":"컨테이너 시작.","operationId":"start_container_api_v1_docker_containers__container_id__start_post","parameters":[{"name":"container_id","in":"path","required":true,"schema":{"type":"string","title":"Container Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/docker/containers/{container_id}/logs":{"get":{"tags":["docker"],"summary":"Get Logs","description":"컨테이너 로그.","operationId":"get_logs_api_v1_docker_containers__container_id__logs_get","parameters":[{"name":"container_id","in":"path","required":true,"schema":{"type":"string","title":"Container Id"}},{"name":"tail","in":"query","required":false,"schema":{"type":"integer","default":100,"title":"Tail"}},{"name":"keyword","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Keyword"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dashboards/docker/summary":{"get":{"tags":["dashboards"],"summary":"Docker Summary","description":"Docker 카드 합산.\n\nResponse: {checked_at, total, running, stopped, failed, unhealthy, by_status}.\nAudit research.md §5.1 / verification.md §3.2 spec.","operationId":"docker_summary_api_v1_dashboards_docker_summary_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/npm/zone":{"get":{"tags":["npm"],"summary":"이 축(duckdns)의 존·DDNS — /domains 와 섞지 않는다","operationId":"npm_zone_api_v1_npm_zone_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/npm/hosts":{"get":{"tags":["npm"],"summary":"NPM 프록시 호스트(도메인↔컨테이너·서비스타입·SSL만료·상태, 라이브)","operationId":"proxy_hosts_api_v1_npm_hosts_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"tags":["npm"],"summary":"프록시 호스트 신규 생성(도메인 등록, NPM POST)","operationId":"create_host_api_v1_npm_hosts_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/npm/hosts/{host_id}":{"get":{"tags":["npm"],"summary":"NPM 프록시 호스트 상세(라이브)","operationId":"host_detail_api_v1_npm_hosts__host_id__get","parameters":[{"name":"host_id","in":"path","required":true,"schema":{"type":"integer","title":"Host Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"put":{"tags":["npm"],"summary":"프록시 호스트 수정(도메인명·포워드·보안, merge-before-PUT)","operationId":"update_host_api_v1_npm_hosts__host_id__put","parameters":[{"name":"host_id","in":"path","required":true,"schema":{"type":"integer","title":"Host Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"delete":{"tags":["npm"],"summary":"프록시 호스트 삭제(NPM DELETE, 삭제 후 부재 확인)","operationId":"delete_host_api_v1_npm_hosts__host_id__delete","parameters":[{"name":"host_id","in":"path","required":true,"schema":{"type":"integer","title":"Host Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/npm/hosts/{host_id}/enable":{"post":{"tags":["npm"],"summary":"프록시 호스트 활성화(NPM enable)","operationId":"enable_host_api_v1_npm_hosts__host_id__enable_post","parameters":[{"name":"host_id","in":"path","required":true,"schema":{"type":"integer","title":"Host Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/npm/hosts/{host_id}/disable":{"post":{"tags":["npm"],"summary":"프록시 호스트 비활성화(NPM disable)","operationId":"disable_host_api_v1_npm_hosts__host_id__disable_post","parameters":[{"name":"host_id","in":"path","required":true,"schema":{"type":"integer","title":"Host Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/npm/certificates":{"get":{"tags":["npm"],"summary":"NPM SSL 인증서 목록(만료 관제, 라이브)","operationId":"certificates_api_v1_npm_certificates_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"tags":["npm"],"summary":"SSL 인증서 신규 발급(Let's Encrypt, 검증·payload — 실발급은 관리자 UI)","operationId":"create_certificate_api_v1_npm_certificates_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/npm/certificates/{cert_id}/renew":{"post":{"tags":["npm"],"summary":"SSL 인증서 수동 갱신(Let's Encrypt renew)","operationId":"renew_certificate_api_v1_npm_certificates__cert_id__renew_post","parameters":[{"name":"cert_id","in":"path","required":true,"schema":{"type":"integer","title":"Cert Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/npm/registry/reconcile":{"post":{"tags":["npm"],"summary":"service_registry 를 NPM+docker(SSOT) 기준 현행화(멱등)","operationId":"reconcile_registry_api_v1_npm_registry_reconcile_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/npm/container-domains":{"get":{"tags":["npm"],"summary":"컨테이너→도메인 역참조(NPM 라이브 SSOT 우선 + registry 폴백)","operationId":"container_domains_api_v1_npm_container_domains_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/domains/":{"get":{"tags":["domains"],"summary":"서브도메인 인벤토리 — DSM 라우팅(설정) + TLS·HTTP(실측) 병합","operationId":"list_domains_api_v1_domains__get","parameters":[{"name":"refresh","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Refresh"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/domains/summary":{"get":{"tags":["domains"],"summary":"와일드카드 커버리지·만료 요약 (서브도메인 확장성 판단)","description":"새 서브도메인을 추가할 때 **인증서 작업이 필요한지**를 한 줄로 답한다.","operationId":"summary_api_v1_domains_summary_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/domains/guide":{"get":{"tags":["domains"],"summary":"서브도메인 등록 가이드 — 수치·목록을 실측에서 채운다","description":"페이지 안에서 보는 등록 절차. **유지 관리 방식이 설계의 핵심이다.**\n\n사용자 지시(2026-09-01): \"실측된 것을 문서화 해서 dcec 에도 볼 수 있도록 가이드 문서도\n페이지내 제공하고 **유지 관리**해\".\n\n문서를 복사해 두면 반드시 낡는다 — 이 저장소에서 이미 겪었다(2026-08-31 판이\n`audio`/`dsm` 의 출처를 틀리게 적었고, 아무도 그 사실을 몰랐다). 그래서 절차 **문장**만\n코드에 두고, **수치·목록·존은 전부 지금 측정한 값으로 채운다**. 값이 비면 \"미확인\"으로\n보이지 조용히 옛날 값이 남지 않는다.","operationId":"guide_api_v1_domains_guide_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/domains/watchdog":{"get":{"tags":["domains"],"summary":"도메인 관제 목록(정상 포함) — health/watchdog 와 같은 형태","operationId":"domains_watchdog_api_v1_domains_watchdog_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/domains/{domain}/tls":{"get":{"tags":["domains"],"summary":"단건 TLS 실측(강제 새로고침) — 관리 대상 도메인만","description":"**관리 중인 도메인만** 실측한다.\n\n경로 인자를 그대로 `open_connection` 에 넘기면 이 컨테이너가 임의 내부 호스트의\n443 응답 여부를 알려주는 스캐너가 되고, 느린 호스트로 세마포어(4)를 채워\n`/` 와 `/summary` 를 멈춰 세울 수 있다(2026-08-31 `/security-review`).","operationId":"domain_tls_api_v1_domains__domain__tls_get","parameters":[{"name":"domain","in":"path","required":true,"schema":{"type":"string","title":"Domain"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/gitea/status":{"get":{"tags":["gitea"],"summary":"Gitea 서비스 상태(연결·버전·token 보유 여부)","operationId":"gitea_status_api_v1_gitea_status_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/gitea/repos":{"get":{"tags":["gitea"],"summary":"Gitea 리포지토리 목록(token 시 비공개 포함)","operationId":"repos_api_v1_gitea_repos_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":50,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/gitea/commits":{"get":{"tags":["gitea"],"summary":"리포 최근 커밋(기본 SSOT crossman/dcec, repo 지정 가능)","operationId":"commits_api_v1_gitea_commits_get","parameters":[{"name":"repo","in":"query","required":false,"schema":{"type":"string","default":"","title":"Repo"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":10,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/gitea/issues":{"get":{"tags":["gitea"],"summary":"리포 열린 이슈(기본 SSOT crossman/dcec, repo 지정 가능)","operationId":"issues_api_v1_gitea_issues_get","parameters":[{"name":"repo","in":"query","required":false,"schema":{"type":"string","default":"","title":"Repo"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":20,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/gitea/commit":{"get":{"tags":["gitea"],"summary":"단일 커밋 세부(메시지 전문·변경 파일·통계) — sha 필수, repo 지정 가능","operationId":"commit_detail_api_v1_gitea_commit_get","parameters":[{"name":"sha","in":"query","required":false,"schema":{"type":"string","default":"","title":"Sha"}},{"name":"repo","in":"query","required":false,"schema":{"type":"string","default":"","title":"Repo"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/deployment/summary":{"get":{"tags":["deployment"],"summary":"Deployment Summary","operationId":"deployment_summary_api_v1_deployment_summary_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/deployment/history":{"get":{"tags":["deployment"],"summary":"Deployment History","operationId":"deployment_history_api_v1_deployment_history_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":10,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/deployment/targets":{"get":{"tags":["deployment"],"summary":"Deployment Targets","operationId":"deployment_targets_api_v1_deployment_targets_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/deployment/release-packets":{"get":{"tags":["deployment"],"summary":"Deployment Release Packets","operationId":"deployment_release_packets_api_v1_deployment_release_packets_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":10,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"post":{"tags":["deployment"],"summary":"Create Release Packet","operationId":"create_release_packet_api_v1_deployment_release_packets_post","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReleasePacketRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/deployment/control":{"get":{"tags":["deployment"],"summary":"Deployment Control","operationId":"deployment_control_api_v1_deployment_control_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/deployment/execution-capability":{"get":{"tags":["deployment"],"summary":"Deployment Execution Capability","operationId":"deployment_execution_capability_api_v1_deployment_execution_capability_get","parameters":[{"name":"target_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"title":"Target Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/deployment/records":{"post":{"tags":["deployment"],"summary":"Record Deployment Result","operationId":"record_deployment_result_api_v1_deployment_records_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeploymentRecordRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/deployment/execute":{"post":{"tags":["deployment"],"summary":"Execute Deployment Packet","operationId":"execute_deployment_packet_api_v1_deployment_execute_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeploymentExecuteRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/deployment/rollback":{"post":{"tags":["deployment"],"summary":"Rollback Deployment Target","operationId":"rollback_deployment_target_api_v1_deployment_rollback_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeploymentRollbackRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/insights/collect/sources":{"get":{"tags":["insights"],"summary":"수집 소스 목록(테이블·수집기·건수·상태)","operationId":"collection_sources_api_v1_insights_collect_sources_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/insights/kpi/summary":{"get":{"tags":["insights"],"summary":"KPI 요약 — 개발·품질·관제·API 카테고리별 최신값·단위·방향","description":"의미 있는 KPI 요약(개발·품질·관제·API 카테고리별 최신값·단위·방향). 소스 온디맨드 집계.","operationId":"kpi_summary_api_v1_insights_kpi_summary_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/insights/collect/sources/{source_name}":{"get":{"tags":["insights"],"summary":"Collection Source Detail","description":"소스별 레코드 drill-down — 페이징(limit/offset) + 상태(status) + 계획/연구(pr) + 검색(q).\n\n`pr`: plan|research|any|both|none (dev_activity 전용). UI 배치도 상태 필터와 검색 사이.\n`group=work_key`: dev_activity 를 **잡 단위 1행**으로 묶어 반환(W000207).\n`work_key=…`: 그 잡의 이벤트만 **시간순**으로 — 세부 이력 화면용.","operationId":"collection_source_detail_api_v1_insights_collect_sources__source_name__get","parameters":[{"name":"source_name","in":"path","required":true,"schema":{"type":"string","title":"Source Name"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":15,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","default":0,"title":"Offset"}},{"name":"q","in":"query","required":false,"schema":{"type":"string","default":"","title":"Q"}},{"name":"status","in":"query","required":false,"schema":{"type":"string","default":"","title":"Status"}},{"name":"pr","in":"query","required":false,"schema":{"type":"string","default":"","title":"Pr"}},{"name":"group","in":"query","required":false,"schema":{"type":"string","default":"","title":"Group"}},{"name":"work_key","in":"query","required":false,"schema":{"type":"string","default":"","title":"Work Key"}},{"name":"row_id","in":"query","required":false,"schema":{"type":"integer","default":0,"title":"Row Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/insights/collect/sources/{source_name}/part":{"get":{"tags":["insights"],"summary":"Collection Source Record Part","description":"단일 레코드의 무거운 파트(plan/research 전체내용, tools 사용기록) — 클릭 시 비동기 로드.","operationId":"collection_source_record_part_api_v1_insights_collect_sources__source_name__part_get","parameters":[{"name":"source_name","in":"path","required":true,"schema":{"type":"string","title":"Source Name"}},{"name":"part","in":"query","required":true,"schema":{"type":"string","title":"Part"}},{"name":"i","in":"query","required":false,"schema":{"type":"integer","default":0,"title":"I"}},{"name":"q","in":"query","required":false,"schema":{"type":"string","default":"","title":"Q"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/insights/collect/sources/action_audit/diagnose":{"post":{"tags":["insights"],"summary":"Audit Diagnose","description":"action_audit 레코드 진단(기본 에이전트) — problem/improvement 기록 후 반환.\n\nchange_id 우선(offset drift 방지). 미지정 시 offset(i) 폴백.","operationId":"audit_diagnose_api_v1_insights_collect_sources_action_audit_diagnose_post","parameters":[{"name":"i","in":"query","required":false,"schema":{"type":"integer","default":0,"title":"I"}},{"name":"q","in":"query","required":false,"schema":{"type":"string","default":"","title":"Q"}},{"name":"change_id","in":"query","required":false,"schema":{"type":"string","default":"","title":"Change Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/insights/agent-run":{"post":{"tags":["insights"],"summary":"Agent Run","description":"dcec 기본 에이전트로 임의 프롬프트 실행(내부 소비자용 — 텔레그램 task_worker 등).\n\n기본 에이전트(dcec_meta/default_provider + default_model) 해석 → _call_provider 재사용.","operationId":"agent_run_api_v1_insights_agent_run_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/insights/collect/stats":{"get":{"tags":["insights"],"summary":"Collection Stats","operationId":"collection_stats_api_v1_insights_collect_stats_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/insights/analyze/sessions":{"get":{"tags":["insights"],"summary":"Analyze Sessions","operationId":"analyze_sessions_api_v1_insights_analyze_sessions_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/insights/analyze/tools":{"get":{"tags":["insights"],"summary":"Analyze Tools","operationId":"analyze_tools_api_v1_insights_analyze_tools_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/insights/analyze/violations":{"get":{"tags":["insights"],"summary":"Analyze Violations","operationId":"analyze_violations_api_v1_insights_analyze_violations_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/insights/analyze/request":{"post":{"tags":["insights"],"summary":"Analyze User Request","description":"분석 세부 사용자 요구 접수 (multipart: day, source, request, files[이미지]).","operationId":"analyze_user_request_api_v1_insights_analyze_request_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/insights/analyze/attachment/{name}":{"get":{"tags":["insights"],"summary":"Analyze Attachment","description":"사용자 요구 첨부 이미지 서빙 (basename만 — traversal 방지).","operationId":"analyze_attachment_api_v1_insights_analyze_attachment__name__get","parameters":[{"name":"name","in":"path","required":true,"schema":{"type":"string","title":"Name"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/insights/env-context":{"get":{"tags":["insights"],"summary":"Get Env Context","description":"설정 환경의 dcec 정보(에이전트 근거) 조회.","operationId":"get_env_context_api_v1_insights_env_context_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"tags":["insights"],"summary":"Set Env Context","description":"설정 환경의 dcec 정보 저장. body: {context}.","operationId":"set_env_context_api_v1_insights_env_context_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/insights/analyze/record":{"get":{"tags":["insights"],"summary":"Analyze Record","description":"단일 분석 레코드(세부 페이지용).","operationId":"analyze_record_api_v1_insights_analyze_record_get","parameters":[{"name":"day","in":"query","required":true,"schema":{"type":"string","title":"Day"}},{"name":"source","in":"query","required":true,"schema":{"type":"string","title":"Source"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/insights/analyze/run":{"post":{"tags":["insights"],"summary":"Analyze Run","description":"자율 분석 잡 트리거 (cron KST 00:00 / 수동). body: {day?: 'YYYY-MM-DD'}.","operationId":"analyze_run_api_v1_insights_analyze_run_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/insights/problems/resolve":{"post":{"tags":["insights"],"summary":"Resolve Problem","description":"분석 문제 해결 처리(플래그). body: {day, source, problem, resolved?:bool}.","operationId":"resolve_problem_api_v1_insights_problems_resolve_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/insights/improve/suggestions":{"get":{"tags":["insights"],"summary":"Suggestions","operationId":"suggestions_api_v1_insights_improve_suggestions_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"type":"string","default":"pending","title":"Status"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/insights/improve/suggestions/{sid}":{"patch":{"tags":["insights"],"summary":"Resolve Suggestion","description":"개선 제안 상태 변경. body: {status: applied|dismissed|pending}.","operationId":"resolve_suggestion_api_v1_insights_improve_suggestions__sid__patch","parameters":[{"name":"sid","in":"path","required":true,"schema":{"type":"integer","title":"Sid"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/insights/improve/llm-services":{"get":{"tags":["insights"],"summary":"Llm Services","description":"설정된 실제 에이전트/모델 목록(선택지). 미설정 시 빈 목록.","operationId":"llm_services_api_v1_insights_improve_llm_services_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/insights/improve/{suggestion_id}/results":{"get":{"tags":["insights"],"summary":"Improvement Results","description":"저장된 개선 리포트 결과(에이전트·모델별 비교).","operationId":"improvement_results_api_v1_insights_improve__suggestion_id__results_get","parameters":[{"name":"suggestion_id","in":"path","required":true,"schema":{"type":"integer","title":"Suggestion Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/insights/improve/suggestion/{sid}":{"get":{"tags":["insights"],"summary":"Improve Suggestion One","description":"단일 개선 제안(세부 페이지용).","operationId":"improve_suggestion_one_api_v1_insights_improve_suggestion__sid__get","parameters":[{"name":"sid","in":"path","required":true,"schema":{"type":"integer","title":"Sid"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/insights/improve/{suggestion_id}/execute":{"post":{"tags":["insights"],"summary":"Execute Improvement","description":"개선 항목을 LLM으로 실행.","operationId":"execute_improvement_api_v1_insights_improve__suggestion_id__execute_post","parameters":[{"name":"suggestion_id","in":"path","required":true,"schema":{"type":"integer","title":"Suggestion Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/notices":{"get":{"tags":["notices"],"summary":"List Notices","description":"공지 조회. status=active(티커) / all(이력 전체).","operationId":"list_notices_api_v1_notices_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"type":"string","default":"active","title":"Status"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","default":0,"title":"Offset"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"post":{"tags":["notices"],"summary":"Create Notice","description":"공지 발행 (에이전트/시스템).","operationId":"create_notice_api_v1_notices_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/notices/{notice_id}/resolve":{"patch":{"tags":["notices"],"summary":"Resolve Notice","description":"공지 완료 처리 (사용자 인지·조치).","operationId":"resolve_notice_api_v1_notices__notice_id__resolve_patch","parameters":[{"name":"notice_id","in":"path","required":true,"schema":{"type":"integer","title":"Notice Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/client/info":{"get":{"tags":["client"],"summary":"Client Info","operationId":"client_info_api_v1_client_info_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/client/sessions":{"get":{"tags":["client"],"summary":"Active Sessions","operationId":"active_sessions_api_v1_client_sessions_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/client/environments":{"get":{"tags":["client"],"summary":"Environments","operationId":"environments_api_v1_client_environments_get","parameters":[{"name":"machine_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Machine Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/client/clients":{"get":{"tags":["client"],"summary":"Clients","description":"접속 클라이언트 목록 — session_activity 머신별 최신(다수). 요청자 1명 폐지.","operationId":"clients_api_v1_client_clients_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/client/access_log":{"get":{"tags":["client"],"summary":"Access Log","description":"접속 로그 누적 — session_activity 이력(수집 축). 현재 상태는 /peers 소관.","operationId":"access_log_api_v1_client_access_log_get","parameters":[{"name":"machine_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Machine Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","default":0,"title":"Offset"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/client/session_log":{"get":{"tags":["client"],"summary":"Session Log","description":"세션 로그 누적 — session_log(SessionEnd 기록, 수집 축).","operationId":"session_log_api_v1_client_session_log_get","parameters":[{"name":"machine_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Machine Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","default":0,"title":"Offset"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/client/geoip/{ip}":{"get":{"tags":["client"],"summary":"Geoip","description":"IP 클릭 시 GeoIP 위치 조회.","operationId":"geoip_api_v1_client_geoip__ip__get","parameters":[{"name":"ip","in":"path","required":true,"schema":{"type":"string","title":"Ip"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/claude-code/guidelines":{"get":{"tags":["claude-code"],"summary":"Guidelines","description":"핵심 개발 지침 요약.","operationId":"guidelines_api_v1_claude_code_guidelines_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/claude-code/docs":{"get":{"tags":["claude-code"],"summary":"Docs List","description":"카테고리별 가이드 문서 목록. 배포 미포함 시 base_available=False(빈 목록).","operationId":"docs_list_api_v1_claude_code_docs_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/claude-code/docs/search":{"get":{"tags":["claude-code"],"summary":"가이드/지침/참조 문서 전문 검색","description":"제목·본문에서 q 를 매칭하는 문서 검색 — 에이전트 빠른·정확한 접근(요구 6).\n\n전 카테고리(_DOC_CATEGORIES) .md 스캔 → 카테고리·파일명·제목·발췌 반환.\n에이전트가 프로그램적으로 가이드/지침을 탐색하는 1급 경로. 라우트 순서상\n/docs/{category}/{name} 보다 먼저 정의(고정 세그먼트 'search' 우선 매칭).","operationId":"docs_search_api_v1_claude_code_docs_search_get","parameters":[{"name":"q","in":"query","required":true,"schema":{"type":"string","title":"Q"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/claude-code/docs/{category}/{name}":{"get":{"tags":["claude-code"],"summary":"Docs Content","description":"단일 가이드 마크다운 원문. path traversal 이중 방어: 화이트리스트+정규식+relative_to.","operationId":"docs_content_api_v1_claude_code_docs__category___name__get","parameters":[{"name":"category","in":"path","required":true,"schema":{"type":"string","title":"Category"}},{"name":"name","in":"path","required":true,"schema":{"type":"string","title":"Name"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/claude-code/env-info":{"get":{"tags":["claude-code"],"summary":"dcec 환경 정보(environment.md SSOT 전문)","description":"dcec 개발 환경 문서(docs/environment.md) 전문 — 환경정보 탭·에이전트 근거(요구 5).\n\nGitea SSOT(docs/environment.md)를 배포 서브셋(_DOCS_BASE)에서 서빙. 로컬머신/OS/도구/\nNAS/SSOT 계층/캐시 위치 등 상세. 하드코딩 없이 실 SSOT 반영(빈약한 수동 envctx 대체).","operationId":"env_info_api_v1_claude_code_env_info_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/claude-code/mcp":{"get":{"tags":["claude-code"],"summary":"Mcp Servers","description":"등록된 MCP 서버 목록.","operationId":"mcp_servers_api_v1_claude_code_mcp_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/claude-code/bootstrap.ps1":{"get":{"tags":["claude-code"],"summary":"Bootstrap Redirect","description":"신규 머신 부트스트랩 다운로드 — Gitea raw(SSOT)로 307 리다이렉트.\n\n사이트가 다운로드 URL을 제공: GET /api/v1/.../bootstrap.ps1 → Gitea raw.\n`irm http://<nas>:8900/.../bootstrap.ps1 | iex` 로 first-contact 실행 가능.","operationId":"bootstrap_redirect_api_v1_claude_code_bootstrap_ps1_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/claude-code/skills":{"get":{"tags":["claude-code"],"summary":"Skills List","description":"스킬 목록 — live(skills_machine_map, 머신별 재현 스킬) + 정적 카테고리.\n\nD37: 결과 확인=DCEC 페이지. MVP-3 skills-lock 재현 결과(npx 공통 스킬 설치)를\nNAS SSOT(skills_machine_map)에서 live 로 읽어 페이지에 노출. live 실패 시 정적 폴백.\n필터: installed AND npx_skill AND scope='common' AND sr.deleted_at IS NULL\n(deleted_at: 2026-06-09 오염 중복 정리분 제외 — apply/reconcile is_active SSOT와 정합).","operationId":"skills_list_api_v1_claude_code_skills_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/claude-code/agents":{"get":{"tags":["claude-code"],"summary":"Agent Teams","description":"에이전트 팀 구성.","operationId":"agent_teams_api_v1_claude_code_agents_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/claude-code/sessions":{"get":{"tags":["claude-code"],"summary":"Recent Sessions","description":"최근 Claude Code 세션 이력.","operationId":"recent_sessions_api_v1_claude_code_sessions_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/claude-code/workers":{"get":{"tags":["claude-code"],"summary":"Agent Workers","description":"등록된 LLM 워커 세션 목록.","operationId":"agent_workers_api_v1_claude_code_workers_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/claude-code/workers/tasks":{"get":{"tags":["claude-code"],"summary":"Agent Task List","description":"워커 작업 목록.","operationId":"agent_task_list_api_v1_claude_code_workers_tasks_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"type":"string","default":"","title":"Status"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/claude-code/tasks/delegate":{"post":{"tags":["claude-code"],"summary":"Delegate Task Bridge","description":"Hub MCP delegate_task → agent_tasks PG 브릿지.\n\nHub에서 delegate_task 호출 시 이 엔드포인트를 통해\nDCEC agent_tasks 테이블에도 기록한다.","operationId":"delegate_task_bridge_api_v1_claude_code_tasks_delegate_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DelegateTaskRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/claude-code/tasks/{task_id}":{"patch":{"tags":["claude-code"],"summary":"Update Task Status","description":"작업 상태 업데이트 (running/completed/failed).","operationId":"update_task_status_api_v1_claude_code_tasks__task_id__patch","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","title":"Task Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateTaskRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/codex/status":{"get":{"tags":["codex"],"summary":"Status","description":"Codex 런타임/로그인 상태.","operationId":"status_api_v1_codex_status_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/codex/environment":{"get":{"tags":["codex"],"summary":"Environment","description":"Codex 환경 저장값/적용값.","operationId":"environment_api_v1_codex_environment_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/codex/app/status":{"get":{"tags":["codex"],"summary":"App Status","description":"Codex App 등록 상태.","operationId":"app_status_api_v1_codex_app_status_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/codex/app/sessions":{"get":{"tags":["codex"],"summary":"App Sessions","description":"Codex App 세션 목록.","operationId":"app_sessions_api_v1_codex_app_sessions_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":20,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/codex/cli/status":{"get":{"tags":["codex"],"summary":"Cli Status","description":"Codex CLI 상태 + 요약 카운트.","operationId":"cli_status_api_v1_codex_cli_status_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/codex/cli/sessions":{"get":{"tags":["codex"],"summary":"Cli Sessions","description":"Codex CLI 세션 목록.","operationId":"cli_sessions_api_v1_codex_cli_sessions_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":20,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/codex/cli/tasks":{"get":{"tags":["codex"],"summary":"Cli Tasks","description":"Codex CLI 작업 목록.","operationId":"cli_tasks_api_v1_codex_cli_tasks_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"type":"string","default":"","title":"Status"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":30,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/codex/cli/conversations":{"get":{"tags":["codex"],"summary":"Cli Conversations","description":"Codex CLI conversation 목록.","operationId":"cli_conversations_api_v1_codex_cli_conversations_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":20,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/codex/sessions":{"get":{"tags":["codex"],"summary":"Sessions","description":"Codex 관련 세션 목록 (호환 유지).","operationId":"sessions_api_v1_codex_sessions_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":20,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/codex/tasks":{"get":{"tags":["codex"],"summary":"Tasks","description":"Codex 대상 또는 Codex 발 작업 목록 (호환 유지).","operationId":"tasks_api_v1_codex_tasks_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"type":"string","default":"","title":"Status"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":30,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/codex/conversations":{"get":{"tags":["codex"],"summary":"Conversations","description":"Codex가 참여한 A2A conversation 상태 목록 (호환 유지).","operationId":"conversations_api_v1_codex_conversations_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":20,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/development/summary":{"get":{"tags":["development"],"summary":"Development Summary","description":"Peer workload summary for the development collaboration surface.","operationId":"development_summary_api_v1_development_summary_get","parameters":[{"name":"source_machine_id","in":"query","required":false,"schema":{"type":"string","minLength":1,"default":"dcec-web-console","title":"Source Machine Id"}},{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Include Archived"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/development/projects":{"get":{"tags":["development"],"summary":"Development Projects","description":"Project selector source of truth = Gitea repositories.","operationId":"development_projects_api_v1_development_projects_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/development/peer/{machine_id}":{"get":{"tags":["development"],"summary":"Development Peer Detail","description":"Detailed peer trace: backlog, tasks, and thread for the selected peer.","operationId":"development_peer_detail_api_v1_development_peer__machine_id__get","parameters":[{"name":"machine_id","in":"path","required":true,"schema":{"type":"string","title":"Machine Id"}},{"name":"source_machine_id","in":"query","required":false,"schema":{"type":"string","minLength":1,"default":"dcec-web-console","title":"Source Machine Id"}},{"name":"project_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Key"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":120,"minimum":1,"default":16,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/development/room":{"get":{"tags":["development"],"summary":"Development Project Room","description":"Project-wide room view over all visible LLM peers for one Gitea project.","operationId":"development_project_room_api_v1_development_room_get","parameters":[{"name":"project_key","in":"query","required":true,"schema":{"type":"string","minLength":1,"title":"Project Key"}},{"name":"source_machine_id","in":"query","required":false,"schema":{"type":"string","minLength":1,"default":"dcec-web-console","title":"Source Machine Id"}},{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Include Archived"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":300,"minimum":1,"default":24,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/development/main-room":{"get":{"tags":["development"],"summary":"Development Main Room","description":"Main room view over all visible DCEC LLM peers.","operationId":"development_main_room_api_v1_development_main_room_get","parameters":[{"name":"source_machine_id","in":"query","required":false,"schema":{"type":"string","minLength":1,"default":"dcec-web-console","title":"Source Machine Id"}},{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Include Archived"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":300,"minimum":1,"default":24,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/development/main-room/send":{"post":{"tags":["development"],"summary":"Development Main Room Send","description":"Fan-out one main-room message to all visible DCEC LLM peers.","operationId":"development_main_room_send_api_v1_development_main_room_send_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DevelopmentMainRoomRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/development/broadcast":{"post":{"tags":["development"],"summary":"Development Broadcast","description":"Fan-out one project message to all currently connected DCEC LLM peers.","operationId":"development_broadcast_api_v1_development_broadcast_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DevelopmentBroadcastRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/devenv/guidelines":{"get":{"tags":["devenv"],"summary":"Guidelines","description":"핵심 개발 지침 요약.","operationId":"guidelines_api_v1_devenv_guidelines_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/devenv/docs":{"get":{"tags":["devenv"],"summary":"Docs List","description":"카테고리별 가이드 문서 목록. 배포 미포함 시 base_available=False(빈 목록).","operationId":"docs_list_api_v1_devenv_docs_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/devenv/docs/search":{"get":{"tags":["devenv"],"summary":"가이드/지침/참조 문서 전문 검색","description":"제목·본문에서 q 를 매칭하는 문서 검색 — 에이전트 빠른·정확한 접근(요구 6).\n\n전 카테고리(_DOC_CATEGORIES) .md 스캔 → 카테고리·파일명·제목·발췌 반환.\n에이전트가 프로그램적으로 가이드/지침을 탐색하는 1급 경로. 라우트 순서상\n/docs/{category}/{name} 보다 먼저 정의(고정 세그먼트 'search' 우선 매칭).","operationId":"docs_search_api_v1_devenv_docs_search_get","parameters":[{"name":"q","in":"query","required":true,"schema":{"type":"string","title":"Q"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/devenv/docs/{category}/{name}":{"get":{"tags":["devenv"],"summary":"Docs Content","description":"단일 가이드 마크다운 원문. path traversal 이중 방어: 화이트리스트+정규식+relative_to.","operationId":"docs_content_api_v1_devenv_docs__category___name__get","parameters":[{"name":"category","in":"path","required":true,"schema":{"type":"string","title":"Category"}},{"name":"name","in":"path","required":true,"schema":{"type":"string","title":"Name"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/devenv/env-info":{"get":{"tags":["devenv"],"summary":"dcec 환경 정보(environment.md SSOT 전문)","description":"dcec 개발 환경 문서(docs/environment.md) 전문 — 환경정보 탭·에이전트 근거(요구 5).\n\nGitea SSOT(docs/environment.md)를 배포 서브셋(_DOCS_BASE)에서 서빙. 로컬머신/OS/도구/\nNAS/SSOT 계층/캐시 위치 등 상세. 하드코딩 없이 실 SSOT 반영(빈약한 수동 envctx 대체).","operationId":"env_info_api_v1_devenv_env_info_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/devenv/mcp":{"get":{"tags":["devenv"],"summary":"Mcp Servers","description":"등록된 MCP 서버 목록.","operationId":"mcp_servers_api_v1_devenv_mcp_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/devenv/bootstrap.ps1":{"get":{"tags":["devenv"],"summary":"Bootstrap Redirect","description":"신규 머신 부트스트랩 다운로드 — Gitea raw(SSOT)로 307 리다이렉트.\n\n사이트가 다운로드 URL을 제공: GET /api/v1/.../bootstrap.ps1 → Gitea raw.\n`irm http://<nas>:8900/.../bootstrap.ps1 | iex` 로 first-contact 실행 가능.","operationId":"bootstrap_redirect_api_v1_devenv_bootstrap_ps1_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/devenv/skills":{"get":{"tags":["devenv"],"summary":"Skills List","description":"스킬 목록 — live(skills_machine_map, 머신별 재현 스킬) + 정적 카테고리.\n\nD37: 결과 확인=DCEC 페이지. MVP-3 skills-lock 재현 결과(npx 공통 스킬 설치)를\nNAS SSOT(skills_machine_map)에서 live 로 읽어 페이지에 노출. live 실패 시 정적 폴백.\n필터: installed AND npx_skill AND scope='common' AND sr.deleted_at IS NULL\n(deleted_at: 2026-06-09 오염 중복 정리분 제외 — apply/reconcile is_active SSOT와 정합).","operationId":"skills_list_api_v1_devenv_skills_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/devenv/agents":{"get":{"tags":["devenv"],"summary":"Agent Teams","description":"에이전트 팀 구성.","operationId":"agent_teams_api_v1_devenv_agents_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/devenv/sessions":{"get":{"tags":["devenv"],"summary":"Recent Sessions","description":"최근 Claude Code 세션 이력.","operationId":"recent_sessions_api_v1_devenv_sessions_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/devenv/workers":{"get":{"tags":["devenv"],"summary":"Agent Workers","description":"등록된 LLM 워커 세션 목록.","operationId":"agent_workers_api_v1_devenv_workers_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/devenv/workers/tasks":{"get":{"tags":["devenv"],"summary":"Agent Task List","description":"워커 작업 목록.","operationId":"agent_task_list_api_v1_devenv_workers_tasks_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"type":"string","default":"","title":"Status"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/devenv/tasks/delegate":{"post":{"tags":["devenv"],"summary":"Delegate Task Bridge","description":"Hub MCP delegate_task → agent_tasks PG 브릿지.\n\nHub에서 delegate_task 호출 시 이 엔드포인트를 통해\nDCEC agent_tasks 테이블에도 기록한다.","operationId":"delegate_task_bridge_api_v1_devenv_tasks_delegate_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DelegateTaskRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/devenv/tasks/{task_id}":{"patch":{"tags":["devenv"],"summary":"Update Task Status","description":"작업 상태 업데이트 (running/completed/failed).","operationId":"update_task_status_api_v1_devenv_tasks__task_id__patch","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","title":"Task Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateTaskRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/env/info":{"get":{"tags":["env"],"summary":"환경정보 DB SSOT (목적·NAS·네트워크·서비스·머신)","description":"dcec 환경정보를 항목별로 집계 — DB(env_*) SSOT. 변동값은 updated_at 병기.\n\n항목: purpose(DCEC 목적·운영방향) / nas / network / services / machines.\n파일(environment.md) 아닌 DB 조회 → 실측 현행값. pool 부재 시 available=False.","operationId":"env_info_api_v1_env_info_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/env/changes":{"get":{"tags":["env"],"summary":"환경 변경이력 (역순)","description":"env_change_log 변경이력 — changed_at 역순(최신 먼저). limit 1~200 클램프.\n\n변동값 현행화 이력(before→after) 추적. 아코디언 아닌 리스트 렌더용.","operationId":"env_changes_api_v1_env_changes_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":50,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/nav/tree":{"get":{"tags":["nav"],"summary":"nav 트리 조회(활성 카테고리·경로) — 사이드바 렌더 소스","description":"렌더용 트리(활성만). base.html 과 동일 소스.","operationId":"get_tree_api_v1_nav_tree_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/nav/snapshot":{"get":{"tags":["nav"],"summary":"nav 전체 스냅샷(비활성 포함) — 라우팅 관리 콘솔용","description":"관리 UI 전체 스냅샷(비활성 포함).","operationId":"get_snapshot_api_v1_nav_snapshot_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/nav/code-routes":{"get":{"tags":["nav"],"summary":"코드 SSOT 예약 경로 목록 — dynamic 경로 충돌 검사 참고","description":"코드 SSOT 예약 경로(신규 dynamic 경로 충돌 회피 참고).","operationId":"get_code_routes_api_v1_nav_code_routes_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/nav/health":{"get":{"tags":["nav"],"summary":"각 nav 경로 실시간 관제(HTTP status·서빙 여부)","description":"각 nav 경로 실시간 관제 — in-process GET 으로 status/응답시간(ms) 수집.","operationId":"get_health_api_v1_nav_health_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/nav/categories":{"put":{"tags":["nav"],"summary":"nav 카테고리 생성/수정(admin)","operationId":"upsert_category_api_v1_nav_categories_put","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CategoryBody"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"post":{"tags":["nav"],"summary":"nav 카테고리 생성/수정(admin)","operationId":"upsert_category_api_v1_nav_categories_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CategoryBody"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/nav/categories/{key}":{"delete":{"tags":["nav"],"summary":"nav 카테고리 삭제(admin, builtin·비어있지않음 보호)","operationId":"delete_category_api_v1_nav_categories__key__delete","parameters":[{"name":"key","in":"path","required":true,"schema":{"type":"string","title":"Key"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/nav/routes":{"put":{"tags":["nav"],"summary":"nav 경로 생성/수정(admin) — dynamic 은 코드경로 충돌검사+라이브 등록","operationId":"upsert_route_api_v1_nav_routes_put","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RouteBody"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"post":{"tags":["nav"],"summary":"nav 경로 생성/수정(admin) — dynamic 은 코드경로 충돌검사+라이브 등록","operationId":"upsert_route_api_v1_nav_routes_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RouteBody"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/nav/routes/{route_key}":{"delete":{"tags":["nav"],"summary":"nav 경로 삭제(admin, builtin·하위보유 보호)","operationId":"delete_route_api_v1_nav_routes__route_key__delete","parameters":[{"name":"route_key","in":"path","required":true,"schema":{"type":"string","title":"Route Key"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/nav/reorder":{"post":{"tags":["nav"],"summary":"nav 카테고리/경로 순서 재정렬(admin)","operationId":"reorder_api_v1_nav_reorder_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReorderBody"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/a2a/send":{"post":{"tags":["a2a"],"summary":"Send Message","operationId":"send_message_api_v1_a2a_send_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SendMessageRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/a2a/recv":{"get":{"tags":["a2a"],"summary":"Receive Messages","operationId":"receive_messages_api_v1_a2a_recv_get","parameters":[{"name":"machine_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"title":"Machine Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}},{"name":"consumer_service","in":"query","required":false,"schema":{"anyOf":[{"type":"string","minLength":1},{"type":"null"}],"title":"Consumer Service"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/a2a/thread":{"get":{"tags":["a2a"],"summary":"Get Thread","description":"Conversation-like view over queued/delivered machine messages.","operationId":"get_thread_api_v1_a2a_thread_get","parameters":[{"name":"source_machine_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"title":"Source Machine Id"}},{"name":"target_machine_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"title":"Target Machine Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/a2a/direct-status":{"get":{"tags":["a2a"],"summary":"Get Direct Status","description":"Low-level direct delivery readiness for one source->target pair.","operationId":"get_direct_status_api_v1_a2a_direct_status_get","parameters":[{"name":"source_machine_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"title":"Source Machine Id"}},{"name":"target_machine_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"title":"Target Machine Id"}},{"name":"bootstrap","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Bootstrap"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/tasks":{"get":{"tags":["tasks"],"summary":"Task List","description":"태스크 목록 (agent_tasks + task_queue 통합).","operationId":"task_list_api_v1_tasks_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"type":"string","default":"","title":"Status"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":50,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/tasks/stats":{"get":{"tags":["tasks"],"summary":"Task Stats","description":"태스크 통계.","operationId":"task_stats_api_v1_tasks_stats_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/tasks/targets":{"get":{"tags":["tasks"],"summary":"Task Targets","description":"태스크 위임 대상 세션 목록.","operationId":"task_targets_api_v1_tasks_targets_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/tasks/{task_id}":{"get":{"tags":["tasks"],"summary":"Task Detail","description":"단일 태스크 상세.","operationId":"task_detail_api_v1_tasks__task_id__get","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","title":"Task Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"patch":{"tags":["tasks"],"summary":"Update Task","description":"공통 태스크 상태 업데이트 엔드포인트.","operationId":"update_task_api_v1_tasks__task_id__patch","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","title":"Task Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateTaskRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/tasks/delegate":{"post":{"tags":["tasks"],"summary":"Delegate Task","description":"공통 태스크 위임 엔드포인트.","operationId":"delegate_task_api_v1_tasks_delegate_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DelegateTaskRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/tasks/{task_id}/events":{"get":{"tags":["tasks"],"summary":"Task Events","description":"plan_events for a task — collab phase audit trail (tunaFlow uplift).","operationId":"task_events_api_v1_tasks__task_id__events_get","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","title":"Task Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":50,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/peers":{"get":{"tags":["peers"],"summary":"Peer List","description":"현재 접속 클라이언트/LLM 목록 (peer_heartbeats 우선 + session_activity 보강).","operationId":"peer_list_api_v1_peers_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/peers/computers":{"get":{"tags":["peers"],"summary":"Computer List","description":"Aggregated computer/host presence for fast online/offline recognition.","operationId":"computer_list_api_v1_peers_computers_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/peers/heartbeats":{"get":{"tags":["peers"],"summary":"Peer Heartbeats","description":"최근 peer heartbeat 목록 (테이블 없으면 빈 배열).","operationId":"peer_heartbeats_api_v1_peers_heartbeats_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/peers/heartbeat":{"post":{"tags":["peers"],"summary":"Post Heartbeat","description":"Upsert the latest participant heartbeat.","operationId":"post_heartbeat_api_v1_peers_heartbeat_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/HeartbeatRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/peers/{machine_id}/{service}":{"delete":{"tags":["peers"],"summary":"Delete Peer","description":"Explicit unregister — soft-delete (status='offline', stopped_at=NOW).\n\nIdempotent: missing row returns 200 rowcount=0.\nAuth: body.machine_id 가 path machine_id 와 일치해야 (self-verify).","operationId":"delete_peer_api_v1_peers__machine_id___service__delete","parameters":[{"name":"machine_id","in":"path","required":true,"schema":{"type":"string","title":"Machine Id"}},{"name":"service","in":"path","required":true,"schema":{"type":"string","title":"Service"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UnregisterRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/telegram/status":{"get":{"tags":["telegram"],"summary":"Telegram Status","operationId":"telegram_status_api_v1_telegram_status_get","parameters":[{"name":"project_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Key"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/telegram/bindings":{"get":{"tags":["telegram"],"summary":"Telegram Bindings","operationId":"telegram_bindings_api_v1_telegram_bindings_get","parameters":[{"name":"project_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Key"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/telegram/relays":{"get":{"tags":["telegram"],"summary":"Telegram Relays","operationId":"telegram_relays_api_v1_telegram_relays_get","parameters":[{"name":"project_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Key"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/telegram/command":{"post":{"tags":["telegram"],"summary":"Telegram Command","operationId":"telegram_command_api_v1_telegram_command_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TelegramCommandRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/telegram/flush-relays":{"post":{"tags":["telegram"],"summary":"Telegram Flush Relays","operationId":"telegram_flush_relays_api_v1_telegram_flush_relays_post","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/webhook/telegram":{"post":{"tags":["telegram-webhook"],"summary":"Telegram Webhook","operationId":"telegram_webhook_webhook_telegram_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/audit/sessions":{"post":{"tags":["audit"],"summary":"Create Session","description":"새 감사 세션 생성.","operationId":"create_session_api_v1_audit_sessions_post","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateAuditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"get":{"tags":["audit"],"summary":"List Sessions","operationId":"list_sessions_api_v1_audit_sessions_get","parameters":[{"name":"state","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":50,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/audit/sessions/{audit_id}":{"get":{"tags":["audit"],"summary":"Get Session","operationId":"get_session_api_v1_audit_sessions__audit_id__get","parameters":[{"name":"audit_id","in":"path","required":true,"schema":{"type":"string","title":"Audit Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/audit/sessions/{audit_id}/rounds":{"get":{"tags":["audit"],"summary":"Get Rounds","operationId":"get_rounds_api_v1_audit_sessions__audit_id__rounds_get","parameters":[{"name":"audit_id","in":"path","required":true,"schema":{"type":"string","title":"Audit Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/audit/review":{"post":{"tags":["audit"],"summary":"Submit Review","description":"Claude가 리뷰 완료 후 결과를 허브에 기록하고 상태 전이.","operationId":"submit_review_api_v1_audit_review_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SubmitReviewRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/audit/revision":{"post":{"tags":["audit"],"summary":"Submit Revision","description":"Codex가 수정 완료 후 재감사 준비 상태로 전이.","operationId":"submit_revision_api_v1_audit_revision_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SubmitRevisionRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/api-keys/{prefix}/value":{"get":{"tags":["settings"],"summary":"API Key 전체 값 조회(개발 대시보드, 공개읽기, 요청마다)","description":"개발 편의 — key_prefix 의 전체 raw 값을 요청마다 반환. 1회 노출 아님.\n\n**공개읽기(admin 게이트 없음)**: API Key 값은 부트스트랩 루트라 admin 키로 게이트하면\n'값 보려면 값 필요' 순환(deadlock, 무한반복). 무로그인 1-admin 개발 대시보드 +\n키/크리덴셜 목록이 이미 공개읽기(OPEN_GET)인 tier 와 동일. 다운스트림 크리덴셜 '값'은 admin 유지.\nlegacy(raw 미저장) 키는 value=null + stored=false(회전 후 조회 가능). 인증은 key_hash.","operationId":"get_api_key_value_api_v1_settings_api_keys__prefix__value_get","parameters":[{"name":"prefix","in":"path","required":true,"schema":{"type":"string","title":"Prefix"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/whoami":{"get":{"tags":["settings"],"summary":"입력한 x-api-key 의 역할/prefix 확인 (UI 키 입력 피드백)","description":"제공된 x-api-key 의 검증 결과(역할·prefix·admin 여부). 키 없음/무효면 401.\n\nUI 가 '어떤 권한의 키가 입력되었는지' 표시하고 재입력을 지원하기 위한 조회.","operationId":"whoami_api_v1_settings_whoami_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/settings/api-keys/bootstrap":{"post":{"tags":["settings"],"summary":"Bootstrap Api Keys","description":"최초 1회 — admin + bridge 키 동시 발급. 이미 활성 키 존재 시 409.","operationId":"bootstrap_api_keys_api_v1_settings_api_keys_bootstrap_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/settings/api-keys":{"get":{"tags":["settings"],"summary":"List Api Keys","description":"API Key 목록 (공개 읽기 — 1인 관리자 대시보드). ?all=1 → 폐기/만료 이력(발급 대장).\n\n비밀(해시/raw) 미포함. 발급/회전/폐기 변경 조치는 admin 전용.","operationId":"list_api_keys_api_v1_settings_api_keys_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"tags":["settings"],"summary":"Create Api Key","description":"새 API Key 발급 (admin 전용). Body: role/label/expires_in_days(0=무기한).","operationId":"create_api_key_api_v1_settings_api_keys_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/settings/api-keys/events":{"get":{"tags":["settings"],"summary":"List Api Key Events","description":"키 발급/회전/폐기 감사 이력 (공개 읽기 — 최근 이벤트).","operationId":"list_api_key_events_api_v1_settings_api_keys_events_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/settings/api-keys/{prefix}":{"put":{"tags":["settings"],"summary":"Update Api Key","description":"키 권한/목적/유효기간 수정 (admin 전용). Body: role/label/expires_in_days.","operationId":"update_api_key_api_v1_settings_api_keys__prefix__put","parameters":[{"name":"prefix","in":"path","required":true,"schema":{"type":"string","title":"Prefix"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"delete":{"tags":["settings"],"summary":"Revoke Api Key","description":"API Key 비활성화 (admin 전용).","operationId":"revoke_api_key_api_v1_settings_api_keys__prefix__delete","parameters":[{"name":"prefix","in":"path","required":true,"schema":{"type":"string","title":"Prefix"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/api-keys/{prefix}/rotate":{"post":{"tags":["settings"],"summary":"Rotate Api Key","description":"구 키 revoke + 동일 role 신규 키 발급 (admin 전용).","operationId":"rotate_api_key_api_v1_settings_api_keys__prefix__rotate_post","parameters":[{"name":"prefix","in":"path","required":true,"schema":{"type":"string","title":"Prefix"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/credentials":{"get":{"tags":["settings"],"summary":"List Credentials","description":"활성 credential 목록 (공개 읽기 — 민감값 마스킹, 1인 관리자 대시보드). 수정/삭제는 admin 전용.","operationId":"list_credentials_api_v1_settings_credentials_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"tags":["settings"],"summary":"Upsert Credential","description":"credential 생성/수정 (admin 전용). Body: service/credential_type/key_name/key_value.","operationId":"upsert_credential_api_v1_settings_credentials_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/settings/credentials/{cred_id}/value":{"get":{"tags":["settings"],"summary":"credential 실제 value 지연 조회(admin)","description":"단건 실제 value(마스킹 해제) — admin 전용. 목록은 마스킹, 클릭 시에만 서버에서 실값 조회.","operationId":"get_credential_value_api_v1_settings_credentials__cred_id__value_get","parameters":[{"name":"cred_id","in":"path","required":true,"schema":{"type":"integer","title":"Cred Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/credentials/{cred_id}":{"delete":{"tags":["settings"],"summary":"Deactivate Credential","description":"credential 비활성화 (admin 전용).","operationId":"deactivate_credential_api_v1_settings_credentials__cred_id__delete","parameters":[{"name":"cred_id","in":"path","required":true,"schema":{"type":"integer","title":"Cred Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/categories":{"get":{"tags":["settings"],"summary":"List Categories","description":"nav 카테고리 레지스트리(라우팅 SSOT) + 역할 템플릿 — 역할 권한 UI가 참조(공개 읽기).","operationId":"list_categories_api_v1_settings_categories_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/settings/roles":{"get":{"tags":["settings"],"summary":"List Roles","description":"역할 목록 + granular 권한 (공개 읽기).","operationId":"list_roles_api_v1_settings_roles_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"tags":["settings"],"summary":"Create Role","description":"커스텀 역할 생성 (admin 전용). Body: role_name/description/can_*.","operationId":"create_role_api_v1_settings_roles_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/settings/roles/{name}":{"put":{"tags":["settings"],"summary":"Update Role","description":"커스텀 역할 권한/설명 수정 (admin 전용). builtin 불가.","operationId":"update_role_api_v1_settings_roles__name__put","parameters":[{"name":"name","in":"path","required":true,"schema":{"type":"string","title":"Name"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"delete":{"tags":["settings"],"summary":"Delete Role","description":"커스텀 역할 삭제 (admin 전용). builtin/사용중 불가.","operationId":"delete_role_api_v1_settings_roles__name__delete","parameters":[{"name":"name","in":"path","required":true,"schema":{"type":"string","title":"Name"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/api-usage":{"get":{"tags":["settings"],"summary":"Api Usage","description":"API 사용량 집계(공개 읽기) — 많이/적게 사용된 엔드포인트 + 카테고리.","operationId":"api_usage_api_v1_settings_api_usage_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/settings/api-versions":{"get":{"tags":["settings"],"summary":"List Api Versions","description":"등록된 플랫폼 API 버전 목록 + 버전별 엔드포인트 수(openapi 자동집계, 공개 읽기).","operationId":"list_api_versions_api_v1_settings_api_versions_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"tags":["settings"],"summary":"Create Api Version","description":"새 API 버전 등록(admin).","operationId":"create_api_version_api_v1_settings_api_versions_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/settings/api-versions/{version}":{"put":{"tags":["settings"],"summary":"Update Api Version","description":"버전 상태/폐기예정(sunset)/설명 수정(admin). clear_sunset=true → sunset 해제.","operationId":"update_api_version_api_v1_settings_api_versions__version__put","parameters":[{"name":"version","in":"path","required":true,"schema":{"type":"string","title":"Version"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/api-versions/{version}/changelog":{"get":{"tags":["settings"],"summary":"Api Version Changelog","description":"버전별 변경 이력(changelog, 공개 읽기).","operationId":"api_version_changelog_api_v1_settings_api_versions__version__changelog_get","parameters":[{"name":"version","in":"path","required":true,"schema":{"type":"string","title":"Version"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/api-versions/policy":{"get":{"tags":["settings"],"summary":"Api Version Policy","description":"API 버전 관리 기준(SSOT) — 화면·문서가 이 값을 그대로 표시한다.","operationId":"api_version_policy_api_v1_settings_api_versions_policy_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/settings/api-versions/{version}/pending":{"get":{"tags":["settings"],"summary":"Api Pending Changes","description":"아직 마이너가 확정되지 않은(미배포) 변경 목록.","operationId":"api_pending_changes_api_v1_settings_api_versions__version__pending_get","parameters":[{"name":"version","in":"path","required":true,"schema":{"type":"string","title":"Version"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/api-versions/{version}/release":{"post":{"tags":["settings"],"summary":"Api Release Minor","description":"미배포 변경을 한 마이너로 확정(admin) — 배포 1회 = 마이너 1개.","operationId":"api_release_minor_api_v1_settings_api_versions__version__release_post","parameters":[{"name":"version","in":"path","required":true,"schema":{"type":"string","title":"Version"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/api-versions/{version}/minors":{"get":{"tags":["settings"],"summary":"Api Minor Versions","description":"major 아래 마이너 릴리스 목록(공개 읽기).\n\nmajor(v1)=호환성 경계/라이프사이클, minor(v1.1…)=하위호환 변경 묶음.\n`next` 는 다음에 나갈 마이너 번호(변경 기록 시 자동 배정되는 값).","operationId":"api_minor_versions_api_v1_settings_api_versions__version__minors_get","parameters":[{"name":"version","in":"path","required":true,"schema":{"type":"string","title":"Version"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/api-versions/{version}/changes":{"post":{"tags":["settings"],"summary":"Add Api Version Change","description":"changelog 항목 추가(admin) — added/removed/changed/deprecated.\n\nbody.minor_version 미지정 시 다음 마이너로 자동 배정된다.","operationId":"add_api_version_change_api_v1_settings_api_versions__version__changes_post","parameters":[{"name":"version","in":"path","required":true,"schema":{"type":"string","title":"Version"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/access-denials":{"get":{"tags":["settings"],"summary":"List Access Denials","description":"RBAC 접근 거부 감사 이력 (공개 읽기).","operationId":"list_access_denials_api_v1_settings_access_denials_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/settings/api-change-requests":{"get":{"tags":["settings"],"summary":"List Api Change Requests","description":"API 변경 요청 목록(공개 읽기). ?status=open|accepted|rejected|done 필터.","operationId":"list_api_change_requests_api_v1_settings_api_change_requests_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"tags":["settings"],"summary":"Create Api Change Request","description":"API 변경 요청 접수(admin). request_type: new|improve|replace|deprecate.","operationId":"create_api_change_request_api_v1_settings_api_change_requests_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/settings/api-change-requests/{req_id}/decide":{"put":{"tags":["settings"],"summary":"Decide Api Change Request","description":"요청 판단(admin): decision=accept|reject (+note). open 상태만 전이.","operationId":"decide_api_change_request_api_v1_settings_api_change_requests__req_id__decide_put","parameters":[{"name":"req_id","in":"path","required":true,"schema":{"type":"integer","title":"Req Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/settings/api-change-requests/{req_id}/complete":{"post":{"tags":["settings"],"summary":"Complete Api Change Request","description":"수용된 요청 반영 완료(admin): accepted→done + 버전 changelog 자동 기록/연결.","operationId":"complete_api_change_request_api_v1_settings_api_change_requests__req_id__complete_post","parameters":[{"name":"req_id","in":"path","required":true,"schema":{"type":"integer","title":"Req Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/contracts":{"get":{"tags":["contracts"],"summary":"List Contracts","operationId":"list_contracts_api_v1_contracts_get","parameters":[{"name":"protocol","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Protocol"}},{"name":"contract_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contract Id"}},{"name":"include_deprecated","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Include Deprecated"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"post":{"tags":["contracts"],"summary":"Create Contract","operationId":"create_contract_api_v1_contracts_post","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateContractRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/contracts/{contract_id}/versions":{"get":{"tags":["contracts"],"summary":"List Versions","operationId":"list_versions_api_v1_contracts__contract_id__versions_get","parameters":[{"name":"contract_id","in":"path","required":true,"schema":{"type":"string","title":"Contract Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/contracts/{contract_id}/versions/{version}":{"get":{"tags":["contracts"],"summary":"Get Version","operationId":"get_version_api_v1_contracts__contract_id__versions__version__get","parameters":[{"name":"contract_id","in":"path","required":true,"schema":{"type":"string","title":"Contract Id"}},{"name":"version","in":"path","required":true,"schema":{"type":"string","title":"Version"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/contracts/{contract_id}/active":{"get":{"tags":["contracts"],"summary":"Get Active","operationId":"get_active_api_v1_contracts__contract_id__active_get","parameters":[{"name":"contract_id","in":"path","required":true,"schema":{"type":"string","title":"Contract Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/contracts/{contract_id}/versions/{version}/deprecate":{"post":{"tags":["contracts"],"summary":"Deprecate Version","operationId":"deprecate_version_api_v1_contracts__contract_id__versions__version__deprecate_post","parameters":[{"name":"contract_id","in":"path","required":true,"schema":{"type":"string","title":"Contract Id"}},{"name":"version","in":"path","required":true,"schema":{"type":"string","title":"Version"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeprecateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/contracts/attestations":{"post":{"tags":["contracts"],"summary":"Record Attestation","operationId":"record_attestation_api_v1_contracts_attestations_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AttestationRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/contracts/audit":{"get":{"tags":["contracts"],"summary":"List Audit","operationId":"list_audit_api_v1_contracts_audit_get","parameters":[{"name":"contract_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contract Id"}},{"name":"machine_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Machine Id"}},{"name":"event_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Event Type"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":1,"default":100,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/contract-bindings":{"get":{"tags":["contract-bindings"],"summary":"List Bindings","operationId":"list_bindings_api_v1_contract_bindings_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/contract-bindings/{runtime_id}":{"patch":{"tags":["contract-bindings"],"summary":"Upsert Binding","operationId":"upsert_binding_api_v1_contract_bindings__runtime_id__patch","parameters":[{"name":"runtime_id","in":"path","required":true,"schema":{"type":"string","title":"Runtime Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpsertBindingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/collab/messages":{"post":{"tags":["collab"],"summary":"Create Collab Message","description":"Create or append a collab message.\n\n1. Upsert thread (new if thread_id missing, update phase otherwise).\n2. Insert message row.\n3. Record plan_events action='dispatch'.\n4. Best-effort a2a/send (non-blocking).","operationId":"create_collab_message_api_v1_collab_messages_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CollabMessageRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CollabMessageResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/collab/threads/{thread_id}":{"get":{"tags":["collab"],"summary":"Get Collab Thread","operationId":"get_collab_thread_api_v1_collab_threads__thread_id__get","parameters":[{"name":"thread_id","in":"path","required":true,"schema":{"type":"string","title":"Thread Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Collab Thread Api V1 Collab Threads  Thread Id  Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/orchestrate/promote-to-task":{"post":{"tags":["orchestrate"],"summary":"Api Promote To Task","description":"5신호 게이트 통과 시 thread → task 승격.","operationId":"api_promote_to_task_api_v1_orchestrate_promote_to_task_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PromoteRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/PromoteResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/orchestrate/abort":{"post":{"tags":["orchestrate"],"summary":"Api Abort","description":"kill_switch trip — orchestrator 긴급 정지.","operationId":"api_abort_api_v1_orchestrate_abort_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AbortRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"additionalProperties":true,"type":"object","title":"Response Api Abort Api V1 Orchestrate Abort Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/orchestrate/kill-switch/reset":{"post":{"tags":["orchestrate"],"summary":"Api Kill Switch Reset","description":"kill_switch 수동 reset → state='open'.","operationId":"api_kill_switch_reset_api_v1_orchestrate_kill_switch_reset_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ResetRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"additionalProperties":true,"type":"object","title":"Response Api Kill Switch Reset Api V1 Orchestrate Kill Switch Reset Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/orchestrate/status":{"get":{"tags":["orchestrate"],"summary":"Api Status","description":"orchestrator 전반 상태.","operationId":"api_status_api_v1_orchestrate_status_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/StatusResponse"}}}}}}},"/api/v1/orchestrate/promote-to-deployment":{"post":{"tags":["orchestrate"],"summary":"Api Promote To Deployment","description":"수동 trigger — agent_tasks 묶음 → release_packet 생성.\n\nauto_promote_loop와 같은 경로를 명시 호출로 사용. project_key 미지정 시\ntask의 project_key 사용. completed + auto_promoted 검증은 호출자 책임.","operationId":"api_promote_to_deployment_api_v1_orchestrate_promote_to_deployment_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PromoteToDeploymentRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/PromoteToDeploymentResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/orchestrate/pending-acks":{"get":{"tags":["orchestrate"],"summary":"Api Pending Acks","description":"ack_window 미만료 + state in (pending,dry_run_passed) packet 목록.","operationId":"api_pending_acks_api_v1_orchestrate_pending_acks_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"additionalProperties":true,"type":"object","title":"Response Api Pending Acks Api V1 Orchestrate Pending Acks Get"}}}}}}},"/api/v1/local_hub/changes":{"post":{"tags":["peers-cockpit"],"summary":"Post Local Hub Change","description":"로컬 허브가 보고한 변경을 변경 원장(dcec_changes)에 남긴다.\n\n상태 이벤트(`/local_hub/lifecycle`)와 **다른 축**이다. 그쪽은 관제(상태)로 조회하고,\n이쪽이 변경 이력이 답해야 하는 값이다. hub_id 를 함께 받아 허브별 관제가 가능하게 한다\n(현재는 머신당 허브 1개라 machine_id 로도 특정되지만, 다수가 되면 이 인자가 유일한 구분이다).","operationId":"post_local_hub_change_api_v1_local_hub_changes_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LocalHubChangeIngestRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/local_hub/lifecycle":{"post":{"tags":["peers-cockpit"],"summary":"Post Local Hub Lifecycle","description":"Best-effort local_hub lifecycle mirror into NAS dcec_changes.","operationId":"post_local_hub_lifecycle_api_v1_local_hub_lifecycle_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LocalHubLifecycleIngestRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/local_hub/status":{"get":{"tags":["peers-cockpit"],"summary":"Get Local Hub Status","description":"로컬 허브 상태 목록 (관제 조회, NAS 최신 요약).","operationId":"get_local_hub_status_api_v1_local_hub_status_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"tags":["peers-cockpit"],"summary":"Post Local Hub Status","description":"로컬 허브 5역할 상태 요약 수신 (허브 데몬이 주기 push → 관제).","operationId":"post_local_hub_status_api_v1_local_hub_status_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LocalHubStatusRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/local_hub/processes/snapshot":{"post":{"tags":["peers-cockpit"],"summary":"Post Process Snapshot","description":"로컬 프로세스 스냅샷 수신 — 머신별 **최신 상태로 치환**(이력 아님).\n\n판정(owner/supervised/orphan/protected)은 로컬이 내린 결과를 그대로 저장한다.\n여기서 다시 판정하지 않는다 — 두 곳이 판정하면 반드시 어긋난다.","operationId":"post_process_snapshot_api_v1_local_hub_processes_snapshot_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProcessSnapshotRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/local_hub/processes":{"get":{"tags":["peers-cockpit"],"summary":"Get Local Hub Processes","description":"머신(선택적으로 에이전트)별 프로세스 목록 + 스냅샷 신선도.\n\n`sampled_at` 을 함께 돌려준다 — 로컬 워치독이 멈추면 화면이 **오래된 데이터임을 밝혀야**\n한다(\"없음\"과 \"못 쟀음\"은 다르다).","operationId":"get_local_hub_processes_api_v1_local_hub_processes_get","parameters":[{"name":"machine_id","in":"query","required":true,"schema":{"type":"string","title":"Machine Id"}},{"name":"service","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Service"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/local_hub/processes/reap":{"post":{"tags":["peers-cockpit"],"summary":"Post Process Reap","description":"수동 회수 발행 — 되돌릴 수 없다. 보호 대상은 **서버에서도 거부**(UI 차단과 이중 방어).\n\n실제 종료는 로컬 워커가 `verified_kill` 로 수행한다. 여기서는 명령만 싣는다.","operationId":"post_process_reap_api_v1_local_hub_processes_reap_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProcessReapRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/agents/known":{"get":{"tags":["peers-cockpit"],"summary":"Get Known Agents","description":"5종+ Agent SSOT 응답 (config/dcec_agents.json read-only).","operationId":"get_known_agents_api_v1_agents_known_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/peers/{machine_id}/local_hub":{"get":{"tags":["peers-cockpit"],"summary":"Peer Local Hub Summary","description":"⑥ 책임 합산 view — 1 GET으로 PeerCard widget data 일괄 로드.","operationId":"peer_local_hub_summary_api_v1_peers__machine_id__local_hub_get","parameters":[{"name":"machine_id","in":"path","required":true,"schema":{"type":"string","title":"Machine Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/peers/{machine_id}/resource_snapshot":{"get":{"tags":["peers-cockpit"],"summary":"Get Resource Snapshot","operationId":"get_resource_snapshot_api_v1_peers__machine_id__resource_snapshot_get","parameters":[{"name":"machine_id","in":"path","required":true,"schema":{"type":"string","title":"Machine Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":1,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"post":{"tags":["peers-cockpit"],"summary":"Post Resource Snapshot","operationId":"post_resource_snapshot_api_v1_peers__machine_id__resource_snapshot_post","parameters":[{"name":"machine_id","in":"path","required":true,"schema":{"type":"string","title":"Machine Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ResourceSnapshotRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/peers/{machine_id}/sync_state":{"get":{"tags":["peers-cockpit"],"summary":"Get Sync State","description":"최근 sync 결과 (dcec_changes resp=3 APPLY). machine_id 는 host 정규화(sync 기록과 정합).\n\nW000124 fix: 기존 `async with pool.acquire() as conn, contextlib.suppress(...)` 는\nsync CM(suppress) 을 async with 에 혼용해 __aenter__ 부재로 500 → try/except 로 분리.","operationId":"get_sync_state_api_v1_peers__machine_id__sync_state_get","parameters":[{"name":"machine_id","in":"path","required":true,"schema":{"type":"string","title":"Machine Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/peers/{machine_id}/sync":{"post":{"tags":["peers-cockpit"],"summary":"Trigger Sync","description":"수동/자동 동기화 — 해당 허브의 peer(연결/끊긴 agent) 상태값(freshness)을 재평가·정합 후\n\nDCEC NAS SSOT 에 기록. W000124: stub 해제(실동작). 안전(서버-side 상태 정합, self 무관).\n  1. 같은 host 의 peer_heartbeats 최신행 freshness 재평가 (age>임계 → offline 정합)\n  2. local_hub_status.updated_at 갱신\n  3. dcec_changes(resp=3, action=APPLY) 기록 → GET /sync_state 실효화","operationId":"trigger_sync_api_v1_peers__machine_id__sync_post","parameters":[{"name":"machine_id","in":"path","required":true,"schema":{"type":"string","title":"Machine Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/peers/{machine_id}/update":{"post":{"tags":["peers-cockpit"],"summary":"Trigger Update","description":"수동/자동 업데이트 — 대상 로컬허브를 최신 버전으로 갱신 요청(복수 허브 관제 제어).\n\nW000124: stub 해제(실 배선). worker self-restart(pg_notify('worker_control')) 선례 재사용.\n  1. pg_notify('hub_control', {machine_id, action:'update', ...}) 발행 → 허브측 LISTEN 소비\n  2. dcec_changes(resp=6, action=APPLY) 기록 → 업데이트 요청 이력·추적\n실 git pull + 재시작은 허브측 소비자(bin/dcec_supervisor.py hub_control LISTEN)가 수행.","operationId":"trigger_update_api_v1_peers__machine_id__update_post","parameters":[{"name":"machine_id","in":"path","required":true,"schema":{"type":"string","title":"Machine Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/HubUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/peers/{machine_id}/env_sync":{"post":{"tags":["peers-cockpit"],"summary":"Trigger Env Sync","description":"개발환경 동기화 — 대상 로컬 머신이 개발환경 collector 재수집→NAS 반영(사용자 수동 트리거). W000124.\n\ntrigger_update 패턴 재사용: pg_notify('hub_control', {action:'env_sync'}) → 워커 _run_env_sync 소비\n(dcec_env_collector 실행). dcec_changes(resp=6, APPLY) 이력 기록.","operationId":"trigger_env_sync_api_v1_peers__machine_id__env_sync_post","parameters":[{"name":"machine_id","in":"path","required":true,"schema":{"type":"string","title":"Machine Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch":{"post":{"tags":["peers-cockpit"],"summary":"Post Dispatch","description":"⑤ KEY — dispatch 진입점. 안 B(W000124): 실행 SSOT = agent_tasks 단일.\n\n대상 워커 세션마다 agent_tasks 를 batch 발행(task_packet.meta.dispatch_id=dispatch_id).\nDB 트리거(trg_agent_tasks_enqueue)가 NOTIFY → 워커 claim → LLM 실행 → complete(result_json).\ndispatch 관제는 agent_tasks 를 dispatch_id 로 취합(별도 a2a 회신 불요).\ndispatch_history 는 batch 헤더(발행 이력)로만 유지.","operationId":"post_dispatch_api_v1_dispatch_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DispatchRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch/targets":{"get":{"tags":["peers-cockpit"],"summary":"Get Dispatch Targets","description":"dispatch 대상 후보 = 등록 워커 세션 + 지금 접속된 피어. A안(W000124).\n\n- kind='worker'(claimable): agent_tasks를 claim·실행하는 워커 세션 → 실제 결과 반환.\n- kind='peer'(감지): 지금 접속된 에이전트(peer_heartbeats online)이나 워커 미기동 →\n  claim 주체 없음. dispatch는 되나 그 세션 워커가 떠야 실행(jobs에 worker 오프라인 경고).\nlive = last_seen/heartbeat 근래(<120s).","operationId":"get_dispatch_targets_api_v1_dispatch_targets_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/dispatch/roles":{"get":{"tags":["peers-cockpit"],"summary":"Get Dispatch Roles","description":"dispatch role 선택 목록(동작 가능한 정의된 역할만). W000124.\n\n사용자 자유입력 대신 선택 — 선택한 role 의 instruction 이 실행 prompt 에 반영돼 실제 동작.","operationId":"get_dispatch_roles_api_v1_dispatch_roles_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/dispatch/history":{"get":{"tags":["peers-cockpit"],"summary":"Get Dispatch History","operationId":"get_dispatch_history_api_v1_dispatch_history_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":20,"title":"Limit"}},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch/jobs":{"get":{"tags":["peers-cockpit"],"summary":"Get Dispatch Jobs","description":"진행 중 dispatch 잡 = agent_tasks(task_packet.meta.dispatch_id) 중 미완료. 안 B(W000124).\n\n실행 SSOT=agent_tasks. 대상 워커 세션/서비스/state(queued/dispatched) 가시화.\nstale 방지: 최근 3일 + 미완료만(완료·실패는 이력/세션 대화에서).","operationId":"get_dispatch_jobs_api_v1_dispatch_jobs_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":30,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch/hubs":{"get":{"tags":["peers-cockpit"],"summary":"Get Dispatch Hubs","description":"로컬 허브 목록(현재 연결 + 과거 연결됐던 전부) + 에이전트별 현행/최종 잡. W000124.\n\ndcec는 복수 허브 관리 서비스 → 연결됐던 허브를 host 기준으로 모두 나열(선택·삭제 가능).\n소스 union: local_hub_status(허브 데몬) + agent_sessions(worker/channel) + peer_heartbeats.\nconnected = 최근 신호(<120s) 있으면. 6개월+ 미접속은 자동 purge.","operationId":"get_dispatch_hubs_api_v1_dispatch_hubs_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/dispatch/hub/delete":{"post":{"tags":["peers-cockpit"],"summary":"Post Hub Delete","description":"로컬 허브 수동 삭제(관리) — 그 host 의 허브/세션/피어 + 의존 데이터 제거. W000124.\n\n끊긴/불필요 허브를 사용자가 목록에서 제거. host = 정규화 호스트명(예: 'dreamx').\nFK 순서: 그 host 세션의 agent_tasks·channel_inbox 먼저 → agent_sessions → peer_heartbeats → local_hub_status.","operationId":"post_hub_delete_api_v1_dispatch_hub_delete_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/HubDeleteRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch/hub_job":{"get":{"tags":["peers-cockpit"],"summary":"Get Dispatch Hub Job","description":"에이전트 현행/최종 잡 관제 상세 — dev_activity 타임라인(request→action/result). W000124.","operationId":"get_dispatch_hub_job_api_v1_dispatch_hub_job_get","parameters":[{"name":"machine_id","in":"query","required":false,"schema":{"type":"string","default":"","title":"Machine Id"}},{"name":"service","in":"query","required":false,"schema":{"type":"string","default":"","title":"Service"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch/hub_comm":{"post":{"tags":["peers-cockpit"],"summary":"Post Hub Comm","description":"헤드리스 에이전트 통신 — 연속 대화 메모리(세션 resume 유지). W000124.\n\n채널(host:service)의 직전 완료 통신의 claude_session 을 resume 대상으로 삼아 대화 컨텍스트를\n이어간다. 첫 통신은 워커 세션(fresh)으로 → 워커가 claude 세션 생성·session_id 반환·저장,\n다음 통신부터 그 세션 resume. App(kind=app)/워커 미기동은 통신 불가(관제만).","operationId":"post_hub_comm_api_v1_dispatch_hub_comm_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/HubCommRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch/worker/restart":{"post":{"tags":["peers-cockpit"],"summary":"Post Worker Restart","description":"dispatch → 워커 재기동 신호(worker_control NOTIFY). 워커가 LISTEN 하다 self-restart. W000124.\n\nNAS→로컬 프로세스 직접 제어 불가 → pg_notify 로 신호만 보내고, 워커가 자기 프로세스를\n새 코드로 재실행(os spawn+exit). 온라인 CLI 워커가 있어야 수신(오프라인=400).","operationId":"post_worker_restart_api_v1_dispatch_worker_restart_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkerRestartRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch/channel/register":{"post":{"tags":["peers-cockpit"],"summary":"Post Channel Register","description":"채널 서버(로컬)가 자기 CLAUDE_CODE_SESSION_ID로 등록·하트비트. dispatch 통신 대상 소스.\n\n라우팅 일관성 핵심: 채널이 폴하는 session_id 와 dispatch가 타겟하는 session_id 를 일치시킨다\n(session_activity 의 상이한 id 의존 제거). agent_sessions(transport='channel')로 등록.","operationId":"post_channel_register_api_v1_dispatch_channel_register_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChannelRegisterRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch/channel/sessions":{"get":{"tags":["peers-cockpit"],"summary":"Get Channel Sessions","description":"dispatch 통신 대상 = 채널 등록된 live 세션(transport='channel'). 머신·복수 세션 공통.","operationId":"get_channel_sessions_api_v1_dispatch_channel_sessions_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/v1/dispatch/channel/send":{"post":{"tags":["peers-cockpit"],"summary":"Post Channel Send","description":"dispatch UI → 특정 live 세션에 메시지 적재(pending). 채널 서버가 폴링해 세션에 주입.","operationId":"post_channel_send_api_v1_dispatch_channel_send_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChannelSendRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch/channel/inbox":{"get":{"tags":["peers-cockpit"],"summary":"Get Channel Inbox","description":"채널 서버(로컬)가 폴링 — 그 세션의 pending 메시지 반환 + delivered 표시.\n\n세션 주입 대상만(status='pending', id>since). 반환 즉시 delivered 로 마킹(중복 주입 방지).","operationId":"get_channel_inbox_api_v1_dispatch_channel_inbox_get","parameters":[{"name":"session_id","in":"query","required":false,"schema":{"type":"string","default":"","title":"Session Id"}},{"name":"since","in":"query","required":false,"schema":{"type":"integer","default":0,"title":"Since"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch/channel/reply":{"post":{"tags":["peers-cockpit"],"summary":"Post Channel Reply","description":"세션(reply 툴) → 응답 저장 → dispatch UI 가 thread 로 조회.","operationId":"post_channel_reply_api_v1_dispatch_channel_reply_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChannelReplyRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch/channel/thread":{"get":{"tags":["peers-cockpit"],"summary":"Get Channel Thread","description":"dispatch UI 대화창 — 그 세션의 채널 대화(요청→응답) 시계열.","operationId":"get_channel_thread_api_v1_dispatch_channel_thread_get","parameters":[{"name":"session_id","in":"query","required":false,"schema":{"type":"string","default":"","title":"Session Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":30,"title":"Limit"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dispatch/thread":{"get":{"tags":["peers-cockpit"],"summary":"Get Dispatch Thread","description":"dispatch 관제(대화) — dispatch_id(batch) 또는 session_id(그 세션 잡 히스토리). 안 B(W000124).\n\nsession_id: jobs 클릭 관제 — 그 세션의 최근 잡(요청+결과), tasks 발행(dispatch_id 없음)도 열림.\ndispatch_id: batch(1 dispatch=N task) 취합. 회신 = agent_tasks 결과.","operationId":"get_dispatch_thread_api_v1_dispatch_thread_get","parameters":[{"name":"dispatch_id","in":"query","required":false,"schema":{"type":"string","default":"","title":"Dispatch Id"}},{"name":"session_id","in":"query","required":false,"schema":{"type":"string","default":"","title":"Session Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dcec/changes":{"get":{"tags":["peers-cockpit"],"summary":"Get Dcec Changes","description":"변경 이력 — **무엇이 바뀌었는가**를 답한다.\n\n기본적으로 **상태 이벤트를 제외**한다. `POST /local_hub/lifecycle` 이 세션 시작·heartbeat·\nturn_ended 를 같은 표에 mirror 하는데(actor=`local_hub_lifecycle`), 그것은 변경이 아니라\n상태값이다. 대량으로 들어와 실제 변경(sync APPLY resp=3 · update resp=6 등)을 덮었고,\n화면에는 `claude:agent_turn_ended` 만 20줄 남았다(2026-08-18 사용자 지적).\n상태 이력이 필요하면 `include_state=true` 로 명시해 부른다 — 섞어서 보여주는 것은 두 값을\n**대조할 목적일 때만** 의미가 있다.","operationId":"get_dcec_changes_api_v1_dcec_changes_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":50,"title":"Limit"}},{"name":"machine_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Machine Id"}},{"name":"responsibility","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Responsibility"}},{"name":"include_state","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Include State"}},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","default":0,"title":"Offset"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dcec/changes/analysis":{"get":{"tags":["peers-cockpit"],"summary":"Get Changes Analysis","description":"변경 이력 온디맨드 분석 — 이슈 관제·보고용. 조회 시 집계 + 규칙기반 인사이트 생성.\n\nW000124: 4관점(안정성/이상·활동요약·추세/변화·최근실패). 저장 없는 실시간 규칙 분석.\n필터는 NULL-허용 파라미터화(S608 회피).","operationId":"get_changes_analysis_api_v1_dcec_changes_analysis_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","default":7,"title":"Days"}},{"name":"machine_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Machine Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dcec/incidents":{"get":{"tags":["peers-cockpit"],"summary":"Get Incidents","description":"C2 incident — dcec_incidents(실 기록) + dcec_changes 실패건(success=false) 자동 파생 union.\n\nW000124: 유입 0 이던 incidents 를 changes 실패에서 파생해 실효화. 파생은 open/all 에서만 표출.\n필터는 NULL-허용 파라미터화(S608 회피).","operationId":"get_incidents_api_v1_dcec_incidents_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"type":"string","default":"open","title":"Status"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","default":50,"title":"Limit"}},{"name":"machine_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Machine Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"post":{"tags":["peers-cockpit"],"summary":"Post Incident","operationId":"post_incident_api_v1_dcec_incidents_post","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IncidentRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dcec/prevention_rules":{"get":{"tags":["peers-cockpit"],"summary":"Get Prevention Rules","description":"C2 예방 규칙 — dcec_prevention_rules(실 규칙) + 반복 실패 패턴 후보 파생.\n\nW000124: 유입 0 이던 예방규칙을 changes 반복 실패(동일 machine+reason ≥3회)에서 후보 파생.\n후보는 status=candidate 로 all/candidate 조회 시 표출(auto_apply=false).","operationId":"get_prevention_rules_api_v1_dcec_prevention_rules_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"type":"string","default":"active","title":"Status"}},{"name":"machine_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Machine Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/dcec/rollback":{"post":{"tags":["peers-cockpit"],"summary":"Post Rollback","description":"C2 auto-recovery — change_id의 before_json 으로 target_table 복원.\n\n본 사이클 stub — Phase 8 with_snapshot_and_rollback decorator 와 paired.\n실 적용은 target_table-specific 처리 별 cycle.","operationId":"post_rollback_api_v1_dcec_rollback_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RollbackRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/devices/enroll":{"post":{"tags":["devices"],"summary":"Enroll Device","description":"①a 자동 등록 — 목록에 올리고 **승인 대기**로 둔다. 리스는 승인 후에만 나간다.","operationId":"enroll_device_api_v1_devices_enroll_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EnrollRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/devices/lease":{"post":{"tags":["devices"],"summary":"Request Lease","description":"리스 발급/갱신. 미승인이면 `lease=null` + 사유를 돌려준다(오류가 아니다).\n\n오류(4xx)로 만들지 않는 이유: 승인 대기는 **정상 상태**다. 허브는 이 응답을 받고\n로컬 기록을 계속하며 전송만 보류한다(②a). 4xx 로 만들면 허브 로그가 오류로 덮인다.","operationId":"request_lease_api_v1_devices_lease_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LeaseRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/devices/{machine_id}/approve":{"post":{"tags":["devices"],"summary":"Approve Device","operationId":"approve_device_api_v1_devices__machine_id__approve_post","parameters":[{"name":"machine_id","in":"path","required":true,"schema":{"type":"string","title":"Machine Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApprovalRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/devices/{machine_id}/reject":{"post":{"tags":["devices"],"summary":"Reject Device","operationId":"reject_device_api_v1_devices__machine_id__reject_post","parameters":[{"name":"machine_id","in":"path","required":true,"schema":{"type":"string","title":"Machine Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApprovalRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/devices/{machine_id}/revoke":{"post":{"tags":["devices"],"summary":"Revoke Device","description":"승인 취소 — 활성 리스도 **즉시** 무효화된다(다음 갱신까지 기다리지 않는다).","operationId":"revoke_device_api_v1_devices__machine_id__revoke_post","parameters":[{"name":"machine_id","in":"path","required":true,"schema":{"type":"string","title":"Machine Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApprovalRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/v1/devices":{"get":{"tags":["devices"],"summary":"List Devices","description":"관제 화면용 — 기기 목록 + 승인 상태 + 리스 만료/갱신 이력.","operationId":"list_devices_api_v1_devices_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/llm/login-status":{"get":{"tags":["llm-oauth"],"summary":"Get Llm Login Status","description":"Return per-provider OAuth/Auth state for the LLM settings tab.","operationId":"get_llm_login_status_api_settings_llm_login_status_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/llm/agents/reconcile":{"post":{"tags":["llm-oauth"],"summary":"Reconcile Agents","description":"POST /api/settings/llm/agents/reconcile — 현시점 provider 상태로 agent_registry 현행화.\n\n드리프트 검사(provider 요금제·인증형식 변경 대응) + upsert. 자동(주기) + 수동(버튼)\n양쪽에서 호출. 반환 = {checked_at, applied, drift_count, report}.","operationId":"reconcile_agents_api_settings_llm_agents_reconcile_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/llm/oauth/google/authorize":{"get":{"tags":["llm-oauth"],"summary":"Google Oauth Authorize","description":"GET /api/settings/llm/oauth/google/authorize — Google OAuth PKCE 시작.\n\n경로가 /api/settings/llm/* 아래 = auth 미들웨어 OPEN_PREFIXES 통과(UI same-origin).\n\nclient_id(env_credentials) → PKCE state/verifier → oauth_pkce_state INSERT →\nauthorize_url 반환. 콜백 = NAS 웹훅(dcec.crossman.synology.me). UI 버튼이 URL 오픈.","operationId":"google_oauth_authorize_api_settings_llm_oauth_google_authorize_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/llm/oauth/openai/authorize":{"get":{"tags":["llm-oauth"],"summary":"Openai Oauth Authorize","description":"GET /api/settings/llm/oauth/openai/authorize — OpenAI OAuth는 loopback(:1455) 로컬 플로우.\n\nNAS 컨테이너는 사용자 머신의 localhost:1455 콜백을 띄울 수 없으므로 로컬에서\n수행해야 한다(Codex CLI 로그인과 동일). UI는 본 안내를 표시.","operationId":"openai_oauth_authorize_api_settings_llm_oauth_openai_authorize_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/llm/oauth/github/device/start":{"post":{"tags":["llm-oauth"],"summary":"Github Device Start","description":"POST /api/settings/llm/oauth/github/device/start — GitHub device flow 시작.\n\n경로가 /api/settings/llm/* 아래 = auth 미들웨어 통과(UI same-origin).\nuser_code/verification_uri를 UI에 표시 → 사용자 브라우저 인증 → poll로 토큰 수령.","operationId":"github_device_start_api_settings_llm_oauth_github_device_start_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/llm/oauth/github/device/poll":{"post":{"tags":["llm-oauth"],"summary":"Github Device Poll","description":"POST /api/settings/llm/oauth/github/device/poll — device_code로 토큰 교환.\n\nbody {device_code}. 성공 시 oauth_tokens(service='github') 저장 → login-status connected.","operationId":"github_device_poll_api_settings_llm_oauth_github_device_poll_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/llm/oauth/codex/import":{"post":{"tags":["llm-oauth"],"summary":"Import Codex Oauth","description":"POST /api/settings/llm/oauth/codex/import — 로컬 ~/.codex/auth.json 토큰 push 저장.\n\ndcec 플랫폼(NAS 컨테이너)은 로컬 파일 미접근 → 로컬 push 스크립트가 이 엔드포인트로\naccess/refresh/id_token+account_id 전달. oauth_tokens(service='openai_codex') 저장.\nbody: {access_token, refresh_token, id_token?, account_id, expires_at?}","operationId":"import_codex_oauth_api_settings_llm_oauth_codex_import_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/llm/oauth/codex/refresh":{"post":{"tags":["llm-oauth"],"summary":"Refresh Codex Oauth","description":"POST /api/settings/llm/oauth/codex/refresh — 저장된 refresh_token 으로 서버측 재발급.\n\n웹 UI/로컬 python 없이 재연결(만료 배지/버튼이 호출). refresh_token 이 만료·거부되면\nneeds_relogin=True 로 로컬 재로그인 안내(계정 권한 재인증 필요). 성공 시 oauth_tokens 갱신.","operationId":"refresh_codex_oauth_api_settings_llm_oauth_codex_refresh_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/llm/oauth/codex/device/start":{"post":{"tags":["llm-oauth"],"summary":"Codex device-code 인증 시작 — 제공사(OpenAI) deviceauth(콜백 불요)","description":"OpenAI deviceauth/usercode 요청 → user_code + 인증 URL 반환. 403/401=device login 미허용.","operationId":"codex_device_start_api_settings_llm_oauth_codex_device_start_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/llm/oauth/codex/device/poll":{"post":{"tags":["llm-oauth"],"summary":"Codex device-code 폴링 → 토큰 교환·저장","description":"deviceauth/token 폴(403·404=pending) → authorization_code 교환 → oauth_tokens 저장.","operationId":"codex_device_poll_api_settings_llm_oauth_codex_device_poll_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/llm/oauth/github/copilot-usage":{"get":{"tags":["llm-oauth"],"summary":"Github Copilot Usage","description":"GET /api/settings/llm/oauth/github/copilot-usage — Copilot plan/quota.\n\noauth_tokens(service='github') access_token으로 copilot_internal/user 호출.\n공식 개인 usage API는 없어 비공식 엔드포인트 사용(라이브 검증됨). 카드 하단 표시용.","operationId":"github_copilot_usage_api_settings_llm_oauth_github_copilot_usage_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/llm/agents/local-status":{"post":{"tags":["llm-oauth"],"summary":"Push Local Agent Status","description":"POST /api/settings/llm/agents/local-status — 로컬 CLI 에이전트 인증 상태 반영.\n\nCLI 에이전트(codex_cli 등) 인증은 로컬 파일에 있어 NAS가 직접 못 봄. 로컬 probe\n(bin/dcec_local_agent_auth.py)가 push한 status를 agent_registry에 upsert.\nbody = {machine_id, agents:[{agent_id, status, auth_method}]}.","operationId":"push_local_agent_status_api_settings_llm_agents_local_status_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/api/settings/dcec/default-provider":{"get":{"tags":["llm-oauth"],"summary":"Get Default Provider","description":"GET /api/settings/dcec/default-provider — current DCEC system default Provider.","operationId":"get_default_provider_api_settings_dcec_default_provider_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"tags":["llm-oauth"],"summary":"Post Default Provider","description":"POST /api/settings/dcec/default-provider — set DCEC system default Provider.\n\nBody: {\"provider_id\": \"openai\"|\"google\"|\"github\"|\"anthropic\"}\nStores into env_credentials row (service='dcec_meta', credential_type='setting',\nkey_name='default_provider'). Upsert via INSERT ... ON CONFLICT.","operationId":"post_default_provider_api_settings_dcec_default_provider_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DefaultProviderRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/settings/llm/routing":{"get":{"tags":["llm-oauth"],"summary":"Get Provider Routing","description":"GET /api/settings/llm/routing — provider 우선순위/폴백 체인 + 연결상태.\n\nchain 미설정 시 default_provider 단일로 폴백 표기.","operationId":"get_provider_routing_api_settings_llm_routing_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"tags":["llm-oauth"],"summary":"Post Provider Routing","description":"POST /api/settings/llm/routing — provider 우선순위/폴백 체인 저장.\n\nBody: {\"chain\": [\"github\",\"google\",\"openai\"]}. _PROVIDERS_BASE 검증 후 JSON 업서트.","operationId":"post_provider_routing_api_settings_llm_routing_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProviderChainRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/settings/llm/providers/{provider}/api-key":{"post":{"tags":["llm-oauth"],"summary":"Post Provider Api Key","description":"POST /api/settings/llm/providers/{provider}/api-key — API key 저장.\n\n평문 저장(기존 env_credentials client_id/secret 관례와 일관). 저장 위치:\nenv_credentials(service=provider, credential_type='api_key', key_name='api_key').\n_load_credential 가 이 행을 읽어 _fetch_*_models 가 Bearer 로 사용 → 저장 즉시 fetch 작동.","operationId":"post_provider_api_key_api_settings_llm_providers__provider__api_key_post","parameters":[{"name":"provider","in":"path","required":true,"schema":{"type":"string","title":"Provider"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiKeyRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/settings/llm/models":{"get":{"tags":["llm-oauth"],"summary":"Get Llm Models","description":"GET /api/settings/llm/models[?provider=X] — list models from DB.","operationId":"get_llm_models_api_settings_llm_models_get","parameters":[{"name":"provider","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Provider"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/settings/llm/providers/{provider_id}/default-model":{"post":{"tags":["llm-oauth"],"summary":"Set Default Model","description":"POST /api/settings/llm/providers/{id}/default-model — provider별 기본 모델 지정.\n\nenv_credentials(service=provider, credential_type='setting', key_name='default_model') upsert.\n사용자가 select에서 모델 선택 시 호출 → 영속화. get_llm_models가 default_model로 반환해 pre-select.","operationId":"set_default_model_api_settings_llm_providers__provider_id__default_model_post","parameters":[{"name":"provider_id","in":"path","required":true,"schema":{"type":"string","title":"Provider Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DefaultModelRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/settings/llm/providers/{provider_id}/refresh-models":{"post":{"tags":["llm-oauth"],"summary":"Post Refresh Models","description":"POST /api/settings/llm/providers/{id}/refresh-models — refresh catalog into DB.\n\nFor now: static catalog UPSERT. Future: real API fetch where token valid.","operationId":"post_refresh_models_api_settings_llm_providers__provider_id__refresh_models_post","parameters":[{"name":"provider_id","in":"path","required":true,"schema":{"type":"string","title":"Provider Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/api/settings/llm/models/refresh-all":{"post":{"tags":["llm-oauth"],"summary":"Post Refresh All Models","description":"POST /api/settings/llm/models/refresh-all — refresh all 4 providers.","operationId":"post_refresh_all_models_api_settings_llm_models_refresh_all_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/oauth/google/oauth2callback":{"get":{"tags":["oauth-callback"],"summary":"Google Oauth Callback","description":"GET /oauth/google/oauth2callback — Google OAuth PKCE redirect 수신 + 토큰 교환.\n\nredirect_uri(=이 경로)는 /api/settings 밖이라 root 라우터로 마운트 + 미들웨어 OPEN_PREFIXES 등록.\nstate로 oauth_pkce_state 조회 → code+verifier 교환 → oauth_tokens(service='google') 저장 → /settings 리다이렉트.","operationId":"google_oauth_callback_oauth_google_oauth2callback_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/":{"get":{"tags":["pages"],"summary":"Dashboard","operationId":"dashboard__get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/docker":{"get":{"tags":["pages"],"summary":"Docker List","operationId":"docker_list_docker_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/docker/{container_id}":{"get":{"tags":["pages"],"summary":"Docker Detail","operationId":"docker_detail_docker__container_id__get","parameters":[{"name":"container_id","in":"path","required":true,"schema":{"type":"string","title":"Container Id"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/health":{"get":{"tags":["pages"],"summary":"Health Page","operationId":"health_page_health_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/npm":{"get":{"tags":["pages"],"summary":"Npm Page","operationId":"npm_page_npm_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/domains":{"get":{"tags":["pages"],"summary":"Domains Page","description":"서브도메인·SSL 관제. 정본은 DSM 라우팅(수집) + 실측 TLS — npm 이 아니다(W000197).","operationId":"domains_page_domains_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/domains/guide":{"get":{"tags":["pages"],"summary":"Domains Guide Page","description":"서브도메인 등록 절차. **관제 화면에서 분리**했다 — `/domains` 는 \"지금 괜찮은가\"에\n답하는 화면이고 절차문은 그 질문과 무관하다(PLATFORM_UIUX_GUIDE §0-1, §3.2).\n내용은 `/api/v1/domains/guide` 가 실측으로 채우므로 이 템플릿은 문장을 갖지 않는다.","operationId":"domains_guide_page_domains_guide_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/gitea":{"get":{"tags":["pages"],"summary":"Gitea Page","operationId":"gitea_page_gitea_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/client":{"get":{"tags":["pages"],"summary":"Client Page","operationId":"client_page_client_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/contracts":{"get":{"tags":["pages"],"summary":"Contracts Page","description":"Contract Control Plane 대시보드 (Phase 7 AC7.2).","operationId":"contracts_page_contracts_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/insights/collect":{"get":{"tags":["pages"],"summary":"Insights Collect","operationId":"insights_collect_insights_collect_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/insights/collect/detail":{"get":{"tags":["pages"],"summary":"Insights Collect Detail","description":"수집 레코드 세부 — 별도 페이지(?source=&i=&q=). 목록과 파일 분리.","operationId":"insights_collect_detail_insights_collect_detail_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/insights/analyze":{"get":{"tags":["pages"],"summary":"Insights Analyze","operationId":"insights_analyze_insights_analyze_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/insights/analyze/detail":{"get":{"tags":["pages"],"summary":"Insights Analyze Detail","description":"분석 세부 — 별도 페이지(리스트에서 day+source 쿼리로 진입).","operationId":"insights_analyze_detail_insights_analyze_detail_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/insights/improve":{"get":{"tags":["pages"],"summary":"Insights Improve","operationId":"insights_improve_insights_improve_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/insights/improve/detail":{"get":{"tags":["pages"],"summary":"Insights Improve Detail","description":"개선 세부 — 별도 페이지(리스트에서 id 쿼리로 진입). 에이전트 실행/결과 비교.","operationId":"insights_improve_detail_insights_improve_detail_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/devenv":{"get":{"tags":["pages"],"summary":"Devenv Page","operationId":"devenv_page_devenv_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/claude-code":{"get":{"tags":["pages"],"summary":"Claude Code Page","operationId":"claude_code_page_claude_code_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/codex":{"get":{"tags":["pages"],"summary":"Codex Page","operationId":"codex_page_codex_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/development":{"get":{"tags":["pages"],"summary":"Development Page","operationId":"development_page_development_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/development/claude-code":{"get":{"tags":["pages"],"summary":"Development Claude Code Page","operationId":"development_claude_code_page_development_claude_code_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/development/codex":{"get":{"tags":["pages"],"summary":"Development Codex Page","operationId":"development_codex_page_development_codex_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/development/gitea":{"get":{"tags":["pages"],"summary":"Development Gitea Page","operationId":"development_gitea_page_development_gitea_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/development/deployment":{"get":{"tags":["pages"],"summary":"Development Deployment Page","operationId":"development_deployment_page_development_deployment_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/development/tasks":{"get":{"tags":["pages"],"summary":"Tasks Page","operationId":"tasks_page_development_tasks_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/development/tasks/detail":{"get":{"tags":["pages"],"summary":"Tasks Detail Page","description":"태스크 세부 — 별도 페이지(?id=&f=). 목록과 파일 분리 (가이드 규칙1, P2-6).","operationId":"tasks_detail_page_development_tasks_detail_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/development/collab":{"get":{"tags":["pages"],"summary":"Collab Page","description":"Collab Workspace — tunaFlow uplift Phase B Step 7 (Plan/Dev/Review/Trace).","operationId":"collab_page_development_collab_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/tasks":{"get":{"tags":["pages"],"summary":"Tasks Legacy Page","operationId":"tasks_legacy_page_tasks_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/peers":{"get":{"tags":["pages"],"summary":"Peers Page","operationId":"peers_page_peers_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/peers-cockpit":{"get":{"tags":["pages"],"summary":"Peers Cockpit Page","description":"dcec-peers-cockpit standalone 페이지 (P1-6: app.py 인라인 정의 이관).","operationId":"peers_cockpit_page_peers_cockpit_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/dispatch":{"get":{"tags":["pages"],"summary":"Dispatch Page","description":"Dispatch — 로컬 허브 잡/통신(a2a) 전달 전용 페이지(peers god-page에서 분리, W000124).\n\n상태 중요 페이지: no-cache 헤더로 항상 최신 JS(비동기 폴링 코드) 로드 — 배포 후 stale JS로\n새 상태·기능이 안 잡히는 문제 방지(데이터 변동은 페이지 내 8초 폴링이 반영, 코드 변동은 no-cache로 즉시).","operationId":"dispatch_page_dispatch_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/development/agents":{"get":{"tags":["pages"],"summary":"Agents Main Page","description":"Phase 5 — AgentMainPanel 메인 페이지 (P1-6: app.py 인라인 정의 이관).","operationId":"agents_main_page_development_agents_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/deployment":{"get":{"tags":["pages"],"summary":"Deployment Page","operationId":"deployment_page_deployment_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/settings":{"get":{"tags":["pages"],"summary":"Settings Page","operationId":"settings_page_settings_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/settings/llm":{"get":{"tags":["pages"],"summary":"Settings Llm Page","operationId":"settings_llm_page_settings_llm_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/settings/apikey":{"get":{"tags":["pages"],"summary":"Settings Apikey Page","operationId":"settings_apikey_page_settings_apikey_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/settings/devices":{"get":{"tags":["pages"],"summary":"Settings Devices Page","description":"기기 승인 + 신원 리스(W000153). 접속 클라이언트(client.html)와 **분리**한다 —\n그쪽은 상태 조회, 이쪽은 권한 부여로 관심사가 다르다(god-page 금지).","operationId":"settings_devices_page_settings_devices_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/settings/api":{"get":{"tags":["pages"],"summary":"Settings Api Page","operationId":"settings_api_page_settings_api_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/settings/env":{"get":{"tags":["pages"],"summary":"Settings Env Page","operationId":"settings_env_page_settings_env_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/settings/env/{item}":{"get":{"tags":["pages"],"summary":"Settings Env Item Page","operationId":"settings_env_item_page_settings_env__item__get","parameters":[{"name":"item","in":"path","required":true,"schema":{"type":"string","title":"Item"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/settings/routing":{"get":{"tags":["pages"],"summary":"Settings Routing Page","operationId":"settings_routing_page_settings_routing_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/settings/system":{"get":{"tags":["pages"],"summary":"Settings System Page","operationId":"settings_system_page_settings_system_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/settings/api-docs":{"get":{"tags":["pages"],"summary":"Settings Api Docs Page","operationId":"settings_api_docs_page_settings_api_docs_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}}},"components":{"schemas":{"AbortRequest":{"properties":{"tripped_by":{"type":"string","title":"Tripped By","default":"user"},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"}},"type":"object","title":"AbortRequest"},"ApiKeyRequest":{"properties":{"api_key":{"type":"string","title":"Api Key"}},"type":"object","required":["api_key"],"title":"ApiKeyRequest","description":"Body for POST /llm/providers/{provider}/api-key."},"ApprovalRequest":{"properties":{"actor":{"type":"string","title":"Actor","description":"승인자(관제 사용자)","default":""},"reason":{"type":"string","title":"Reason","default":""}},"type":"object","title":"ApprovalRequest"},"AttestationRequest":{"properties":{"machine_id":{"type":"string","title":"Machine Id"},"runtime_id":{"type":"string","title":"Runtime Id"},"applied_contracts":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Applied Contracts"},"actor":{"type":"string","title":"Actor","default":"contract-agent"}},"type":"object","required":["machine_id","runtime_id","applied_contracts"],"title":"AttestationRequest"},"CategoryBody":{"properties":{"key":{"type":"string","title":"Key"},"label":{"type":"string","title":"Label"},"icon":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Icon"},"order_idx":{"type":"integer","title":"Order Idx","default":0},"render_mode":{"type":"string","title":"Render Mode","default":"group"},"path":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Path"},"active_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Active Key"},"enabled":{"type":"boolean","title":"Enabled","default":true}},"type":"object","required":["key","label"],"title":"CategoryBody"},"ChannelRegisterRequest":{"properties":{"session_id":{"type":"string","title":"Session Id"},"machine_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Machine Id"},"label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Label"},"service":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Service","default":"claude"}},"type":"object","required":["session_id"],"title":"ChannelRegisterRequest"},"ChannelReplyRequest":{"properties":{"msg_id":{"type":"integer","title":"Msg Id"},"text":{"type":"string","title":"Text"}},"type":"object","required":["msg_id","text"],"title":"ChannelReplyRequest"},"ChannelSendRequest":{"properties":{"session_id":{"type":"string","title":"Session Id"},"machine_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Machine Id"},"prompt":{"type":"string","title":"Prompt"},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source"}},"type":"object","required":["session_id","prompt"],"title":"ChannelSendRequest"},"CollabMessageRequest":{"properties":{"phase":{"type":"string","title":"Phase","description":"research|plan|annotate|implement"},"actor":{"type":"string","minLength":1,"title":"Actor"},"role":{"type":"string","title":"Role","description":"proposal|annotate|reply|evidence|vote"},"content":{"type":"string","minLength":1,"title":"Content"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"project_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Key"},"thread_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Thread Id"},"a2a_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"A2A Ref"},"task_packet":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Task Packet"}},"type":"object","required":["phase","actor","role","content"],"title":"CollabMessageRequest"},"CollabMessageResponse":{"properties":{"thread_id":{"type":"string","title":"Thread Id"},"message_id":{"type":"string","title":"Message Id"},"a2a_message_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"A2A Message Id"},"plan_event":{"type":"boolean","title":"Plan Event","default":true}},"type":"object","required":["thread_id","message_id"],"title":"CollabMessageResponse"},"ContextMeta":{"properties":{"recent_context":{"items":{"type":"string"},"type":"array","title":"Recent Context"},"compressed_memory":{"items":{"type":"string"},"type":"array","title":"Compressed Memory"},"findings":{"items":{"type":"string"},"type":"array","title":"Findings"},"artifacts":{"items":{"type":"string"},"type":"array","title":"Artifacts"},"skills":{"items":{"type":"string"},"type":"array","title":"Skills"},"cross_session":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cross Session"},"source_collab_thread_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Collab Thread Id"},"promoted_from_task_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Promoted From Task Id"},"project_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Key"},"auto_promoted":{"type":"boolean","title":"Auto Promoted","default":false},"rollback_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Rollback Ref"}},"type":"object","title":"ContextMeta","description":"tunaFlow ContextPack-inspired metadata (adapted to DCEC headless backend).\n\nv2.1 (2026-05-04): adds 5 optional fields for collab→task→deploy pipeline.\nAll v2.1 fields are optional → v1/v2 packets remain valid."},"CreateAuditRequest":{"properties":{"audit_type":{"type":"string","enum":["code","doc","plan"],"title":"Audit Type"},"initiator":{"type":"string","title":"Initiator"},"reviewer":{"type":"string","title":"Reviewer"},"max_rounds":{"type":"integer","maximum":10.0,"minimum":1.0,"title":"Max Rounds","default":3},"file_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"File Ref"},"context":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Context"}},"type":"object","required":["audit_type","initiator","reviewer"],"title":"CreateAuditRequest"},"CreateContractRequest":{"properties":{"contract_id":{"type":"string","title":"Contract Id"},"version":{"type":"string","title":"Version"},"schema_jsonb":{"additionalProperties":true,"type":"object","title":"Schema Jsonb"},"protocol":{"type":"string","title":"Protocol","description":"runtime/a2a/transport/task/channel/rpai/other"},"enforcement_mode":{"type":"string","title":"Enforcement Mode","description":"soft | hard","default":"soft"},"created_by":{"type":"string","title":"Created By"},"predecessor_version":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Predecessor Version"},"effective_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Effective At"},"deprecation_deadline":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Deprecation Deadline"}},"type":"object","required":["contract_id","version","schema_jsonb","protocol","created_by"],"title":"CreateContractRequest"},"DefaultModelRequest":{"properties":{"model_id":{"type":"string","title":"Model Id"}},"type":"object","required":["model_id"],"title":"DefaultModelRequest","description":"Body for POST /llm/providers/{id}/default-model."},"DefaultProviderRequest":{"properties":{"provider_id":{"type":"string","title":"Provider Id"}},"type":"object","required":["provider_id"],"title":"DefaultProviderRequest","description":"Body for POST /api/dcec/default-provider."},"DelegateTaskRequest":{"properties":{"target_session_id":{"type":"string","title":"Target Session Id","default":"codex-default"},"prompt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Prompt"},"contract_version":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contract Version"},"task_packet":{"anyOf":[{"$ref":"#/components/schemas/StructuredTaskPacket"},{"type":"null"}]},"delegation_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Delegation Id"},"from_terminal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"From Terminal"}},"type":"object","title":"DelegateTaskRequest","description":"Hub MCP delegate_task → DCEC agent_tasks 브릿지."},"DeploymentExecuteRequest":{"properties":{"candidate_id":{"type":"string","minLength":1,"title":"Candidate Id"},"dry_run":{"type":"boolean","title":"Dry Run","default":true},"requested_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Requested By"}},"type":"object","required":["candidate_id"],"title":"DeploymentExecuteRequest"},"DeploymentRecordRequest":{"properties":{"candidate_id":{"type":"string","minLength":1,"title":"Candidate Id"},"target_id":{"type":"string","minLength":1,"title":"Target Id"},"verification_result":{"type":"string","minLength":1,"title":"Verification Result"},"evidence_summary":{"type":"string","minLength":1,"title":"Evidence Summary"},"record_ref":{"type":"string","minLength":1,"title":"Record Ref"},"verified_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Verified By"},"live_commit":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Live Commit"},"notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Notes"}},"type":"object","required":["candidate_id","target_id","verification_result","evidence_summary","record_ref"],"title":"DeploymentRecordRequest"},"DeploymentRollbackRequest":{"properties":{"target_id":{"type":"string","minLength":1,"title":"Target Id"},"dry_run":{"type":"boolean","title":"Dry Run","default":true},"requested_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Requested By"}},"type":"object","required":["target_id"],"title":"DeploymentRollbackRequest"},"DeprecateRequest":{"properties":{"deadline":{"type":"string","format":"date-time","title":"Deadline"},"actor":{"type":"string","title":"Actor"}},"type":"object","required":["deadline","actor"],"title":"DeprecateRequest"},"DevelopmentBroadcastRequest":{"properties":{"source_machine_id":{"type":"string","minLength":1,"title":"Source Machine Id"},"project_key":{"type":"string","minLength":1,"title":"Project Key"},"content":{"type":"string","minLength":1,"title":"Content"},"topic":{"type":"string","title":"Topic","default":"general"},"sender_service":{"type":"string","title":"Sender Service","default":"dcec-web"},"target_machine_ids":{"items":{"type":"string"},"type":"array","title":"Target Machine Ids"},"metadata":{"additionalProperties":true,"type":"object","title":"Metadata"},"delivery_mode":{"type":"string","title":"Delivery Mode","default":"direct"},"fallback_mode":{"type":"string","title":"Fallback Mode","default":"queue"},"expect_reply":{"type":"boolean","title":"Expect Reply","default":true}},"type":"object","required":["source_machine_id","project_key","content"],"title":"DevelopmentBroadcastRequest"},"DevelopmentMainRoomRequest":{"properties":{"source_machine_id":{"type":"string","minLength":1,"title":"Source Machine Id"},"content":{"type":"string","minLength":1,"title":"Content"},"topic":{"type":"string","title":"Topic","default":"general"},"sender_service":{"type":"string","title":"Sender Service","default":"dcec-web"},"target_machine_ids":{"items":{"type":"string"},"type":"array","title":"Target Machine Ids"},"metadata":{"additionalProperties":true,"type":"object","title":"Metadata"},"delivery_mode":{"type":"string","title":"Delivery Mode","default":"direct"},"fallback_mode":{"type":"string","title":"Fallback Mode","default":"queue"},"expect_reply":{"type":"boolean","title":"Expect Reply","default":true}},"type":"object","required":["source_machine_id","content"],"title":"DevelopmentMainRoomRequest"},"DispatchRequest":{"properties":{"source":{"type":"string","title":"Source"},"target_sessions":{"items":{"type":"string"},"type":"array","title":"Target Sessions","default":[]},"target_agents":{"items":{"type":"string"},"type":"array","title":"Target Agents","default":[]},"prompt":{"type":"string","title":"Prompt"},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role"},"project_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Key"}},"type":"object","required":["source","prompt"],"title":"DispatchRequest"},"EnrollRequest":{"properties":{"machine_id":{"type":"string","title":"Machine Id","description":"머신 축(hostname 대문자)"},"agent_axis_id":{"type":"string","title":"Agent Axis Id","description":"에이전트 축({host}-{service})","default":""},"hub_id":{"type":"string","title":"Hub Id","description":"hub_{host} — 파생값","default":""},"evidence":{"additionalProperties":true,"type":"object","title":"Evidence","description":"os/ip/python 등 승인 판단 재료"}},"type":"object","required":["machine_id"],"title":"EnrollRequest","description":"등록 요청 — 기기가 자기 신원을 **주장**한다(승인은 별도)."},"HTTPValidationError":{"properties":{"detail":{"items":{"$ref":"#/components/schemas/ValidationError"},"type":"array","title":"Detail"}},"type":"object","title":"HTTPValidationError"},"HeartbeatRequest":{"properties":{"machine_id":{"type":"string","minLength":1,"title":"Machine Id"},"service":{"type":"string","title":"Service","default":"unknown"},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id"},"status":{"type":"string","title":"Status","default":"online"},"protocol":{"type":"string","title":"Protocol","default":"a2a"},"capabilities":{"additionalProperties":true,"type":"object","title":"Capabilities"},"metadata":{"additionalProperties":true,"type":"object","title":"Metadata"}},"type":"object","required":["machine_id"],"title":"HeartbeatRequest","description":"Minimal presence payload for participant liveness."},"HubCommRequest":{"properties":{"machine_id":{"type":"string","title":"Machine Id"},"service":{"type":"string","title":"Service"},"prompt":{"type":"string","title":"Prompt"},"skill":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Skill"}},"type":"object","required":["machine_id","service","prompt"],"title":"HubCommRequest"},"HubDeleteRequest":{"properties":{"host":{"type":"string","title":"Host"}},"type":"object","required":["host"],"title":"HubDeleteRequest"},"HubUpdateRequest":{"properties":{"target_version":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Version"},"requested_by":{"type":"string","title":"Requested By","default":"cockpit"}},"type":"object","title":"HubUpdateRequest"},"IncidentRequest":{"properties":{"machine_id":{"type":"string","title":"Machine Id"},"agent":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent"},"responsibility":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Responsibility"},"problem":{"type":"string","title":"Problem"},"root_cause":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Root Cause"},"severity":{"type":"string","title":"Severity","default":"medium"},"related_change_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Related Change Id"},"auto_recovered":{"type":"boolean","title":"Auto Recovered","default":false},"safe_mode_triggered":{"type":"boolean","title":"Safe Mode Triggered","default":false}},"type":"object","required":["machine_id","problem"],"title":"IncidentRequest"},"LeaseRequest":{"properties":{"machine_id":{"type":"string","title":"Machine Id"},"agent_axis_id":{"type":"string","title":"Agent Axis Id","default":""},"hub_id":{"type":"string","title":"Hub Id","default":""}},"type":"object","required":["machine_id"],"title":"LeaseRequest"},"LocalHubChangeIngestRequest":{"properties":{"machine_id":{"type":"string","title":"Machine Id"},"hub_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Hub Id"},"kind":{"type":"string","title":"Kind"},"target":{"type":"string","title":"Target"},"before":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Before"},"after":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"After"},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"},"actor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actor"},"responsibility":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Responsibility"},"success":{"type":"boolean","title":"Success","default":true}},"type":"object","required":["machine_id","kind","target"],"title":"LocalHubChangeIngestRequest","description":"로컬 허브가 **자기 변경**을 보고하는 형식.\n\n상태값(lifecycle)과 분리된 축이다 — 이쪽은 \"무엇이 바뀌었나\"에만 답한다(사용자 지시\n2026-08-18: \"변경 이력 항목은 로컬 허브 변경내용을 기록하는 것으로 구현해\")."},"LocalHubLifecycleIngestRequest":{"properties":{"machine_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Machine Id"},"event_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Event Id"},"ts":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Ts"},"terminal_id":{"type":"string","title":"Terminal Id"},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id"},"service":{"type":"string","title":"Service"},"event":{"type":"string","title":"Event"},"source":{"type":"string","title":"Source"},"pid":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Pid"},"cwd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cwd"},"transcript_path":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Transcript Path"},"thread_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Thread Id"},"turn_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Turn Id"},"evidence":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Evidence"},"metadata":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Metadata"}},"type":"object","required":["terminal_id","service","event","source"],"title":"LocalHubLifecycleIngestRequest"},"LocalHubStatusRequest":{"properties":{"machine_id":{"type":"string","title":"Machine Id"},"hub_version":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Hub Version"},"roles":{"additionalProperties":true,"type":"object","title":"Roles"},"machine":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Machine"}},"type":"object","required":["machine_id"],"title":"LocalHubStatusRequest"},"ProcessReapRequest":{"properties":{"machine_id":{"type":"string","title":"Machine Id"},"pids":{"items":{"type":"integer"},"type":"array","title":"Pids"},"scope":{"type":"string","title":"Scope","default":"partial"},"service":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Service"},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"},"kind":{"type":"string","title":"Kind","default":"service"}},"type":"object","required":["machine_id"],"title":"ProcessReapRequest"},"ProcessSnapshotItem":{"properties":{"pid":{"type":"integer","title":"Pid"},"script":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Script"},"cmd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cmd"},"service":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Service"},"owner_kind":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Kind"},"owner_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Ref"},"supervised":{"type":"boolean","title":"Supervised","default":false},"orphan":{"type":"boolean","title":"Orphan","default":false},"protected":{"type":"boolean","title":"Protected","default":false},"protect_reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Protect Reason"},"age_sec":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Age Sec"},"rss_mb":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Rss Mb"}},"type":"object","required":["pid"],"title":"ProcessSnapshotItem"},"ProcessSnapshotRequest":{"properties":{"machine_id":{"type":"string","title":"Machine Id"},"processes":{"items":{"$ref":"#/components/schemas/ProcessSnapshotItem"},"type":"array","title":"Processes"}},"type":"object","required":["machine_id"],"title":"ProcessSnapshotRequest"},"PromoteRequest":{"properties":{"thread_id":{"type":"string","minLength":1,"title":"Thread Id"},"rollback_ref":{"type":"string","minLength":1,"title":"Rollback Ref"},"decision_basis":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Decision Basis"},"auto_promoted":{"type":"boolean","title":"Auto Promoted","default":false},"actor":{"type":"string","title":"Actor","default":"user"},"force":{"type":"boolean","title":"Force","default":false}},"type":"object","required":["thread_id","rollback_ref"],"title":"PromoteRequest"},"PromoteResponse":{"properties":{"task_id":{"type":"string","title":"Task Id"},"redirect":{"type":"string","title":"Redirect"}},"type":"object","required":["task_id","redirect"],"title":"PromoteResponse"},"PromoteToDeploymentRequest":{"properties":{"task_ids":{"items":{"type":"string"},"type":"array","minItems":1,"title":"Task Ids","description":"completed agent_tasks"},"project_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Key"},"promoted_by":{"type":"string","title":"Promoted By","default":"user-manual"}},"type":"object","required":["task_ids"],"title":"PromoteToDeploymentRequest"},"PromoteToDeploymentResponse":{"properties":{"packet_ids":{"items":{"type":"string"},"type":"array","title":"Packet Ids"},"state":{"type":"string","title":"State"}},"type":"object","required":["packet_ids","state"],"title":"PromoteToDeploymentResponse"},"ProtocolEnvelope":{"properties":{"f":{"type":"string","minLength":1,"title":"F"},"t":{"type":"string","minLength":1,"title":"T"},"op":{"type":"string","maxLength":2,"minLength":2,"title":"Op"},"d":{"title":"D"}},"type":"object","required":["f","t","op","d"],"title":"ProtocolEnvelope","description":"Low-token pre-send protocol shared by both endpoints."},"ProviderChainRequest":{"properties":{"chain":{"items":{"type":"string"},"type":"array","title":"Chain"}},"type":"object","required":["chain"],"title":"ProviderChainRequest","description":"Body for POST /api/settings/llm/routing — 우선순위 provider id 배열."},"ReleasePacketRequest":{"properties":{"target_id":{"type":"string","minLength":1,"title":"Target Id"},"candidate_label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Candidate Label"},"purpose":{"type":"string","minLength":1,"title":"Purpose"},"change_summary":{"type":"string","minLength":1,"title":"Change Summary"},"record_ref":{"type":"string","minLength":1,"title":"Record Ref"},"execution_request":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Execution Request"},"verification_plan":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Verification Plan"},"requested_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Requested By"}},"type":"object","required":["target_id","purpose","change_summary","record_ref"],"title":"ReleasePacketRequest"},"ReorderBody":{"properties":{"kind":{"type":"string","title":"Kind"},"ordered_keys":{"items":{"type":"string"},"type":"array","title":"Ordered Keys"}},"type":"object","required":["kind","ordered_keys"],"title":"ReorderBody"},"ResetRequest":{"properties":{"reset_by":{"type":"string","title":"Reset By","default":"user"}},"type":"object","title":"ResetRequest"},"ResourceSnapshotRequest":{"properties":{"cpu_pct":{"type":"number","title":"Cpu Pct"},"ram_mb":{"type":"integer","title":"Ram Mb"},"ram_pct":{"type":"number","title":"Ram Pct"},"disk_pct":{"type":"number","title":"Disk Pct"},"ram_total_mb":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Ram Total Mb"},"disk_free_gb":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Disk Free Gb"},"disk_total_gb":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Disk Total Gb"},"net_sent_kbps":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Net Sent Kbps"},"net_recv_kbps":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Net Recv Kbps"},"processes_json":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Processes Json","default":[]},"health_state":{"type":"string","title":"Health State","default":"ok"},"snapshot_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Snapshot At"}},"type":"object","required":["cpu_pct","ram_mb","ram_pct","disk_pct"],"title":"ResourceSnapshotRequest"},"RollbackRequest":{"properties":{"target_change_id":{"type":"string","title":"Target Change Id"},"actor":{"type":"string","title":"Actor"},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"}},"type":"object","required":["target_change_id","actor"],"title":"RollbackRequest"},"RouteBody":{"properties":{"route_key":{"type":"string","title":"Route Key"},"category_key":{"type":"string","title":"Category Key"},"label":{"type":"string","title":"Label"},"parent_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Parent Key"},"path":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Path"},"active_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Active Key"},"icon":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Icon"},"order_idx":{"type":"integer","title":"Order Idx","default":0},"handler_type":{"type":"string","title":"Handler Type","default":"code"},"is_external":{"type":"boolean","title":"Is External","default":false},"content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content"},"enabled":{"type":"boolean","title":"Enabled","default":true}},"type":"object","required":["route_key","category_key","label"],"title":"RouteBody"},"SendMessageRequest":{"properties":{"source_machine_id":{"type":"string","title":"Source Machine Id"},"target_machine_id":{"type":"string","title":"Target Machine Id"},"content":{"type":"string","minLength":1,"title":"Content"},"topic":{"type":"string","title":"Topic","default":"general"},"project_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Key"},"sender_service":{"type":"string","title":"Sender Service","default":"unknown"},"metadata":{"additionalProperties":true,"type":"object","title":"Metadata"},"protocol":{"anyOf":[{"$ref":"#/components/schemas/ProtocolEnvelope"},{"type":"null"}]},"delivery_mode":{"type":"string","title":"Delivery Mode","default":"queue"},"fallback_mode":{"type":"string","title":"Fallback Mode","default":"none"},"expect_reply":{"type":"boolean","title":"Expect Reply","default":false}},"type":"object","required":["source_machine_id","target_machine_id","content"],"title":"SendMessageRequest","description":"Minimal transport payload for machine_id-based messaging."},"StatusResponse":{"properties":{"kill_switch":{"additionalProperties":true,"type":"object","title":"Kill Switch"}},"type":"object","required":["kill_switch"],"title":"StatusResponse"},"StructuredTaskPacket":{"properties":{"purpose":{"type":"string","title":"Purpose"},"usage_context":{"type":"string","title":"Usage Context"},"user_intent":{"type":"string","title":"User Intent"},"research_summary":{"type":"string","title":"Research Summary"},"analysis_summary":{"type":"string","title":"Analysis Summary"},"record_ref":{"type":"string","title":"Record Ref"},"execution_request":{"type":"string","title":"Execution Request"},"confirmed_facts":{"items":{"type":"string"},"type":"array","title":"Confirmed Facts"},"unverified_items":{"items":{"type":"string"},"type":"array","title":"Unverified Items"},"phase":{"anyOf":[{"type":"string","enum":["research","plan","annotate","implement"]},{"type":"null"}],"title":"Phase"},"meta":{"anyOf":[{"$ref":"#/components/schemas/ContextMeta"},{"type":"null"}]},"prompt_budget_tokens":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Prompt Budget Tokens"},"engine_hint":{"anyOf":[{"type":"string","enum":["claude","codex","auto"]},{"type":"null"}],"title":"Engine Hint"},"model_hint":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Model Hint"}},"type":"object","required":["purpose","usage_context","user_intent","research_summary","analysis_summary","record_ref","execution_request"],"title":"StructuredTaskPacket","description":"Minimum packet required before a DCEC-controlled task can be dispatched.\n\nv2 (2026-04-28): adds phase / meta / prompt_budget_tokens / engine_hint\n(tunaFlow uplift). All v2 fields are optional → v1 packets remain valid."},"SubmitReviewRequest":{"properties":{"audit_id":{"type":"string","title":"Audit Id"},"content":{"type":"string","title":"Content"},"review_result":{"additionalProperties":true,"type":"object","title":"Review Result"},"round":{"type":"integer","title":"Round"}},"type":"object","required":["audit_id","content","review_result","round"],"title":"SubmitReviewRequest","description":"audit.review 결과를 허브에 기록."},"SubmitRevisionRequest":{"properties":{"audit_id":{"type":"string","title":"Audit Id"},"revised_content":{"type":"string","title":"Revised Content"}},"type":"object","required":["audit_id","revised_content"],"title":"SubmitRevisionRequest","description":"audit.revision (Codex 수정 완료) 기록."},"TelegramCommandRequest":{"properties":{"source_machine_id":{"type":"string","minLength":1,"title":"Source Machine Id","default":"dcec-web-console"},"project_key":{"type":"string","minLength":1,"title":"Project Key"},"chat_id":{"type":"integer","title":"Chat Id"},"content":{"type":"string","minLength":1,"title":"Content"},"topic":{"type":"string","title":"Topic","default":"general"},"sender_service":{"type":"string","title":"Sender Service","default":"dcec-web"},"target_machine_ids":{"items":{"type":"string"},"type":"array","title":"Target Machine Ids"},"metadata":{"additionalProperties":true,"type":"object","title":"Metadata"},"delivery_mode":{"type":"string","title":"Delivery Mode","default":"direct"},"fallback_mode":{"type":"string","title":"Fallback Mode","default":"queue"},"expect_reply":{"type":"boolean","title":"Expect Reply","default":true},"relay_results":{"type":"boolean","title":"Relay Results","default":true}},"type":"object","required":["project_key","chat_id","content"],"title":"TelegramCommandRequest"},"UnregisterRequest":{"properties":{"machine_id":{"type":"string","minLength":1,"title":"Machine Id"}},"type":"object","required":["machine_id"],"title":"UnregisterRequest","description":"Body for DELETE /peers/{machine_id}/{service} — self-verify."},"UpdateTaskRequest":{"properties":{"status":{"type":"string","enum":["running","completed","failed"],"title":"Status"},"error_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error Text"}},"type":"object","required":["status"],"title":"UpdateTaskRequest","description":"작업 상태 업데이트 요청."},"UpsertBindingRequest":{"properties":{"required":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Required"},"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name"},"peer_service":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Peer Service"}},"type":"object","required":["required"],"title":"UpsertBindingRequest"},"ValidationError":{"properties":{"loc":{"items":{"anyOf":[{"type":"string"},{"type":"integer"}]},"type":"array","title":"Location"},"msg":{"type":"string","title":"Message"},"type":{"type":"string","title":"Error Type"},"input":{"title":"Input"},"ctx":{"type":"object","title":"Context"}},"type":"object","required":["loc","msg","type"],"title":"ValidationError"},"WorkerRestartRequest":{"properties":{"machine_id":{"type":"string","title":"Machine Id"},"service":{"type":"string","title":"Service"}},"type":"object","required":["machine_id","service"],"title":"WorkerRestartRequest"}}}}