누적된 잠금·승인·증거 체인이 구현과 완료를 반복 차단해 작업 비용을 키웠다. 보안·데이터 손상·명시적 외부 의존성만 차단 조건으로 남기고 로드맵과 스킬의 기본 흐름을 단순화한다.
192 lines
20 KiB
Markdown
192 lines
20 KiB
Markdown
---
|
|
test_env: dev
|
|
test_profile: edge-smoke
|
|
domain: edge
|
|
verification_type: smoke
|
|
last_rule_updated_at: 2026-08-15
|
|
---
|
|
|
|
# edge-smoke dev 테스트
|
|
|
|
## 읽기 조건
|
|
|
|
- `apps/edge/**` 변경 또는 edge registry, transport, service, console, OpenAI-compatible/A2A 입력 표면 dev 검증 판단이 필요한 경우
|
|
|
|
## 적용 범위
|
|
|
|
- `apps/edge/cmd/edge/**`
|
|
- `apps/edge/internal/bootstrap/**`
|
|
- `apps/edge/internal/transport/**`
|
|
- `apps/edge/internal/service/**`
|
|
- `apps/edge/internal/events/**`
|
|
- `apps/edge/internal/input/**`
|
|
- `apps/edge/internal/openai/**`
|
|
- `apps/edge/internal/opsconsole/**`
|
|
- `apps/edge/internal/node/**`
|
|
|
|
## 분류
|
|
|
|
- domain: edge
|
|
- verification_type: smoke
|
|
- scope: edge 실행 그룹, node registry, input surface baseline
|
|
|
|
## 환경
|
|
|
|
- host: local checkout. dev runtime, external CLI, shared port evidence가 필요하면 원격 runner를 사용한다.
|
|
- port: compose Edge-Node TCP transport `19003`; dev artifact/bootstrap HTTP 후보 `18082`, dev Edge OpenAI-compatible HTTP 후보 `18083`, dev Edge metrics 후보 `19101`.
|
|
- runtime: Go `1.24`
|
|
- package manager: Go modules / Makefile
|
|
- docker: unit/smoke quick check는 Docker를 요구하지 않는다. compose dev 검증은 `docker compose --env-file .env.dev.example ...`로 수행한다.
|
|
- external service: dev artifact/base URL 후보 `http://toki-labs.com:18082`, compose Edge runtime 주소 후보 `toki-labs.com:19003`, dev-runtime provider pool native Edge 주소 후보 `toki-labs.com:18084`
|
|
- model endpoint: dev OpenAI-compatible base URL 후보 `http://toki-labs.com:18083/v1`
|
|
- credential: token/secret 원문은 문서에 기록하지 않는다.
|
|
|
|
## dev-runtime provider pool 인벤토리
|
|
|
|
dev-runtime provider pool과 4-node 연결 상태를 점검할 때는 `agent-test/inventory-dev.yaml`의 machine-readable 값을 우선하고, 원격 runner `ssh toki@toki-labs.com`의 `/Users/toki/agent-work/iop-dev` checkout을 기준으로 한다.
|
|
|
|
Claude Anthropic-compatible 단일 요청 Agent 실행을 검증할 때는 Claude가 보낸 실제 Edge `/v1/messages` ingress POST 수를 계수한다. PASS 기준은 정확히 1회이며, 같은 endpoint·사용자 요청·Claude 세션 또는 logical request id 하나는 이를 대체하지 않는다. Harness는 supervised child에만 `CLAUDE_CODE_MAX_RETRIES=0`과 `CLAUDE_CODE_DISABLE_TERMINAL_TITLE=1`을 고정해 SDK retry와 별도 session-title Messages 요청을 제거하고 parent/user Claude 설정은 변경하지 않는다. IOP 내부 Plan/Work/Review provider 응답은 선택적 문자열 `message.reasoning_content`를 검증 후 폐기하며 stage 결과, artifact, caller 응답, 관측 로그에 보존하지 않는다. Gemini `extra_content.google.thought_signature`는 Plan/Review의 정확한 비공개 구조에서만 허용한다. terminal text signature는 폐기하고 Review tool-call signature는 같은 요청의 다음 Gemini assistant tool-call message에만 그대로 되돌려 보내며 Work, artifact, 결과, 로그에는 남기지 않는다. plan/work/review를 caller나 외부 test harness가 각각 호출하거나 Claude-facing `tool_use`/tool result continuation으로 이어 간 과거 다중 요청 실험은 protocol bridge와 model/provider 연결 evidence로만 보존하고 단일 요청 acceptance로 재사용하지 않는다. 이 경로의 stage와 workspace tool loop는 IOP Edge와 operator가 승인한 IOP Node가 소유하며 Agent-Ops dispatcher와 Pi를 실행 경로 또는 test harness로 사용하지 않는다. 현재 구현은 `darwin|linux` Node catalog와 exact host matching만 지원하고 Windows는 fail-closed다; 선택된 dev runner의 OS는 실행 evidence일 뿐 caller-visible 기능 selector가 아니다.
|
|
|
|
- Edge config: `build/dev-runtime/edge.yaml`
|
|
- Edge id: `edge-toki-labs-dev`
|
|
- Control Plane HTTP: `http://127.0.0.1:18001`
|
|
- bootstrap HTTP: `http://toki-labs.com:18082`
|
|
- Edge OpenAI-compatible base URL: `http://toki-labs.com:18083/v1`
|
|
- Edge-Node TCP transport: `toki-labs.com:18084`
|
|
- active model aliases: `ornith:35b`(GX10/OneXPlayer, raw capacity `7`), `ornith-fast`(RTX5090), `qwen3.6:35b`(mac-mlx-vllm). RTX5090은 `ornith:35b` 후보가 아니며 `laguna-s:2.1`은 stopped rollback 자산이라 active provider capacity가 없다.
|
|
- host Pi dispatcher profile: `agent-test/inventory-agent.yaml`의 `environments.dev.agents.pi` 기준. 현재 기본 provider/model/thinking level은 `iop` / `glm-5.2` / `high`이고, dispatcher local-model route는 `iop/ornith:35b` / `high`다. 두 모델 모두 IOP Edge `http://toki-labs.com:18083/v1`을 사용하며 Pi local direct providers는 제거된 상태다. credential 원문 대신 같은 inventory의 SOPS `token_ref`만 기준으로 삼는다.
|
|
- provider/model separation: GX10 Ornith는 `qwen3_xml`/`qwen3`, mac Qwen은 `qwen`/`qwen3`, Lemonade Ornith는 저장된 runtime profile을 사용한다. stopped Laguna의 `poolside_v1` profile이나 dev-corp `gemma4` profile을 이들 active provider에 섞지 않는다.
|
|
|
|
노드 후보:
|
|
|
|
- mac CLI + MLX provider node: `mac-codex-node` / `mac-codex`
|
|
- SSH/user: `ssh toki@toki-labs.com`
|
|
- 목적: `cli` adapter, `codex app-server` + `mac-mlx-vllm` provider resource
|
|
- workspace: `/Users/toki/agent-work/iop-workspace/nomadcode`
|
|
- MLX vLLM provider: `mac-mlx-vllm`
|
|
- provider endpoint: `http://127.0.0.1:8002/v1`
|
|
- served model: `mlx-community/Qwen3.6-35B-A3B-4bit`
|
|
- capacity baseline: `2`
|
|
- priority baseline: `2`
|
|
- workdir: `/Users/toki/agent-work/iop-mlx-vllm`
|
|
- runtime baseline: `vllm-mlx`, `--max-num-seqs 2`, `--max-kv-size 262144`, `--max-request-tokens 262144`, `--use-paged-cache --paged-cache-block-size 64 --max-cache-blocks 4096`, `--enable-auto-tool-choice --tool-call-parser qwen --reasoning-parser qwen3`, `--default-chat-template-kwargs {"enable_thinking": true}`
|
|
- KV policy: per-call window bound `262144`, one full context-size setting
|
|
- long-context admission baseline: `total_context_tokens=262144`, `long_context_capacity=1` (KV budget `262144` fits one full 262144-window request; long slot count is not the normal capacity `2`)
|
|
- GX10 vLLM node: `gx10-vllm-node` / `gx10-vllm`
|
|
- SSH/user: `ssh toki@192.168.0.91`
|
|
- provider endpoint: `http://192.168.0.91:8001/v1`
|
|
- served model: `ornith:35b`
|
|
- capacity baseline: `4`
|
|
- priority baseline: `1`
|
|
- runtime baseline: image `vllm/vllm-openai:nightly-aarch64`, model `deepreinforce-ai/Ornith-1.0-35B-FP8` revision `1ab57ce0b44950e498a88756f40ad1ed4d0f30ca`, `--served-model-name ornith:35b`, `--max-model-len 262144`, `--max-num-seqs 4`, `--gpu-memory-utilization 0.50`, `--enable-prefix-caching`, `--enable-auto-tool-choice --tool-call-parser qwen3_xml`, `--reasoning-parser qwen3`, `--trust-remote-code`, `--language-model-only`, `--override-generation-config '{"temperature":0.6,"top_p":0.95,"top_k":20}'`
|
|
- long-context admission baseline: conservative `total_context_tokens=1048576`, `long_context_capacity=4`; current startup reports GPU KV cache `1173993` tokens and full-context concurrency `4.48x`.
|
|
- runtime ownership: active container는 `iop-vllm-ornith35b-fp8`; stopped `iop-vllm-laguna-s21`은 명시적 rollback 전용이며 provider capacity에 포함하지 않는다.
|
|
- reasoning baseline: `chat_template_kwargs.enable_thinking`으로 model-native reasoning을 제어하고 `qwen3_xml`/`qwen3` parser를 사용한다.
|
|
- workspace: `/home/toki/iop-gx10-vllm`
|
|
- OneXPlayer Lemonade node: `onexplayer-lemonade-node` / `onexplayer-lemonade`
|
|
- SSH/user: `ssh r0bin@192.168.0.59`
|
|
- 접속 기준: 현재 작업 호스트에서 직접 SSH
|
|
- Node provider endpoint: `http://127.0.0.1:8001/v1` (OneX host-local llama backend)
|
|
- Lemonade lifecycle endpoint: `http://192.168.0.59:13305/v1`
|
|
- served model: `ornith:35b` (`--alias`); backend model은 `Ornith-1.0-35B-GGUF-llamacpp-tp1-Q5_K_M`
|
|
- capacity baseline: `3`
|
|
- priority baseline: `2`
|
|
- load baseline: checkpoint `LordNeel/Ornith-1.0-35B-GGUF-llamacpp-tp1:Q5_K_M`, backend `vulkan`, ctx size `524288`, `llamacpp_args="--spec-type none --alias ornith:35b -cb -fa on -b 4096 -ub 1024 --kv-unified --temp 0.6 --top-p 0.95 --top-k 20"`, `save_options=true`
|
|
- long-context admission baseline: `total_context_tokens=524288`, `long_context_capacity=2`; 고정 `-np` 없이 `/slots`가 자동 slot 4개와 각 `n_ctx=262144`를 보고하고 Edge normal capacity는 `3`으로 제한한다.
|
|
- workspace: `C:/Users/r0bin/iop-field`
|
|
- RTX5090 Lemonade node: `rtx5090-lemonade-node` / `rtx5090-lemonade`
|
|
- SSH/user: `ssh iop-dev-rtx5090`
|
|
- 접속 기준: 현재 작업 호스트의 local SSH config alias와 public-key batch 인증
|
|
- provider endpoint: `http://192.168.0.111:13305/v1`
|
|
- served model: `Ornith-1.0-35B-GGUF-llamacpp-tp1-Q5_K_M`
|
|
- capacity baseline: `1`
|
|
- priority baseline: `0`
|
|
- load baseline: backend `cuda`, Q5 GGUF, Q8 KV, ctx size `262144`, `llamacpp_args="--chat-template-kwargs '{\"preserve_thinking\":true}' --kv-unified --min-p 0.00 --repeat-penalty 1.0 --spec-type none --temp 0.6 --top-k 20 --top-p 0.95 -b 512 -cb -ctk q8_0 -ctv q8_0 -fa on -np 1 -ub 256"`, Lemonade `host=0.0.0.0`
|
|
- long-context admission baseline: `total_context_tokens=262144`, `long_context_capacity=1`
|
|
- process baseline: IOP 관련 Windows 부팅 자동 실행은 비활성이고, 수동 `remote-llm-toggle.ps1`이 Lemonade Server, Ornith, IOP Node를 순차 UP/DOWN한다. Startup shortcut, Run entry, Task Scheduler, Windows service는 IOP dev 배포가 생성·재생성하지 않는다.
|
|
- workspace: `C:/Users/r0bin/iop-field`
|
|
|
|
GX10은 Ornith FP8 vLLM을 사용하고 OneXPlayer와 RTX5090 Lemonade는 Ornith Q5 GGUF를 사용한다. stopped Laguna 컨테이너와 `poolside_v1` profile은 rollback 전용이며 active provider에 섞지 않는다.
|
|
|
|
OneXPlayer Lemonade Node는 원격 runner나 Edge host에서 다시 SSH하거나 proxy process로 띄우지 않는다. 현재 작업 호스트에서 OneXPlayer Windows host에 `ssh r0bin@192.168.0.59`로 직접 접속한 뒤 generated PowerShell bootstrap을 실행한다.
|
|
|
|
RTX5090 Lemonade Node도 원격 runner나 Edge host를 경유하지 않는다. 현재 작업 호스트에서 `ssh iop-dev-rtx5090`으로 public-key batch 접속한다. Windows 부팅 owner는 없으며 `RemoteLLM_mode.ahk`의 유일한 `Run`은 수동 `remote-llm-toggle.ps1` 호출이다. 기본 Toggle은 operator 동작에만 쓰고 자동 검증은 `-Action Status|Up|Down`을 명시한다. UP 완료는 Lemonade `0.0.0.0:13305`, 정확한 Ornith profile, llama slot `1`/`n_ctx=262144`, Node의 Edge 연결을 모두 확인하고, DOWN 완료는 Node/Lemonade/llama process와 port가 모두 사라진 상태로 판정한다.
|
|
|
|
mac-mlx-vllm provider는 mac-codex-node 소속 resource로, Edge host와 같은 macOS host에서 vllm-mlx process로 실행한다. vllm-mlx API는 외부에 직접 노출하지 않고 `127.0.0.1:8002`에 bind하며, Edge OpenAI-compatible adapter가 local bearer header로 호출한다. 운영 파일은 `/Users/toki/agent-work/iop-mlx-vllm/vllm-mlx.pid`, `logs/vllm-mlx.stdout.log`, `logs/vllm-mlx.stderr.log`를 기준으로 한다. Docker와 macOS 여유 메모리를 고려해 capacity는 `2`를 기본선으로 유지한다.
|
|
|
|
GX10/OneXPlayer/RTX5090 Ornith sampling은 `temperature=0.6`, `top_p=0.95`, `top_k=20` 기준을 유지한다. GX10은 `qwen3_xml`/`qwen3` parser와 `chat_template_kwargs.enable_thinking`을 사용하고, Edge/Pi smoke는 `high` reasoning과 `off` zero-reasoning 및 tool-call을 각각 검증한다.
|
|
|
|
## 명령
|
|
|
|
- setup:
|
|
- lint:
|
|
- unit: `go test ./apps/edge/...`
|
|
- smoke: `./scripts/e2e-smoke.sh`는 기본 포트 임시 설정을 쓰는 보조 smoke이므로 dev 포트 override 필요 여부를 먼저 확인한다.
|
|
- e2e: `make test-e2e`는 보조 smoke이며 full-cycle 실제 구동을 대체하지 않는다.
|
|
- model: dev OpenAI-compatible profile을 띄운 경우 `iop-edge smoke openai --base-url http://127.0.0.1:18083`
|
|
- full-cycle: repo 내부 edge-node 진단, `iop-edge smoke openai`, OpenAI-compatible 입력 표면 수동 검증
|
|
|
|
## 최소 검증
|
|
|
|
- 변경한 edge 패키지 또는 `go test ./apps/edge/...`를 실행한다.
|
|
- registry, service, transport, console, HTTP/A2A 입력 표면을 바꾼 경우 edge-node 메시지 2회 왕복과 command 응답을 확인한다.
|
|
- OpenAI-compatible 경계를 바꾼 경우 dev `18083` 기준 `iop-edge smoke openai` 또는 동등한 `/healthz`, `/v1/models`, `/v1/responses` 확인으로 edge service와 node adapter 경로 수렴을 확인한다.
|
|
- runtime `edge.yaml`에서 `openai.enabled=true`이면 `openai.provider_id`가 현재 CLI/provider identity와 일치하는지 `config check`로 검증한다. 이 값이 빠진 candidate는 배포하지 않는다.
|
|
- OpenAI-compatible tool-call 경계(`apps/edge/internal/openai/**`의 text tool-call 합성/validation)를 바꾼 경우 dev `18083` `/v1/chat/completions`에 Pi/Cline형 `tools[]` 요청을 non-stream/stream 각각 최소 1회 보내 raw text tool-call boundary smoke를 수행한다. token은 원격 환경 변수에서 주입하고 원문을 명령/로그/보고에 남기지 않는다.
|
|
- dev provider-pool tool-call drift를 확인할 때는 active model group별 provider만 섞는다. `ornith:35b` group은 `gx10-vllm`/`onexplayer-lemonade` direct와 Edge alias를 검증하고, RTX5090은 `ornith-fast`에서만 검증한다. Qwen group은 `mac-mlx-vllm` direct와 Edge `qwen3.6:35b`를 사용하며 stopped Laguna는 active drift 표본에 포함하지 않는다.
|
|
- bootstrap/artifact 경계를 바꾼 경우 dev artifact/base URL 후보 `18082`가 local/test `18080` field baseline을 덮어쓰지 않는지 확인한다.
|
|
|
|
## 보조 검증
|
|
|
|
- `./scripts/e2e-smoke.sh`는 edge-node 최소 생존 확인에 사용한다.
|
|
- `./scripts/e2e-openai-ollama.sh`는 OpenAI-compatible Ollama 입력 표면 보조 확인에 사용한다.
|
|
|
|
## 판정 기준
|
|
|
|
- node 등록, `/nodes`, console 메시지 전송, 기대 payload를 포함한 `[node-*-message]` 출력, 같은 run의 complete event가 확인된다.
|
|
- node 로컬 `[node-message]` payload 라인 목록과 edge `[node-*-message]` payload 라인 목록이 run별로 내용/순서까지 동일해야 한다.
|
|
- edge complete는 같은 run의 마지막 `[node-*-message]` 이후에만 정상이다.
|
|
- OpenAI-compatible smoke에서 `/healthz`, `/v1/models`, `/v1/responses`가 기대 상태로 응답한다.
|
|
- raw text tool-call boundary smoke: Pi/Cline형 `tools[]` 요청에서 응답 body와 SSE delta 어디에도 `<tool_call>`, `{{`, `<|mask_end|>` 원문이 성공 content로 남지 않는다. 요청 `tools[]`에 있는 valid raw text tool-call은 `message.tool_calls`(또는 stream `delta.tool_calls`)와 `finish_reason: "tool_calls"`로 정규화되고, unknown tool hallucination이나 malformed 블록은 성공 content가 아니라 non-stream `tool_validation_error`(HTTP 502) 또는 SSE `tool_validation_error` 이벤트로 끝난다. non-stream/strict buffered stream은 bounded retry 후 차단을 확인한다. 세부 payload와 계약은 `docs/edge-local-dev-guide.md`의 Raw text tool-call boundary smoke와 `agent-contract/outer/openai-compatible-api.md`를 따른다.
|
|
- raw boundary smoke evidence는 tracked 문서가 아니라 ignored run 위치(`agent-test/runs/**`)나 code-review output path에 저장하고, 저장물에도 token 원문을 남기지 않는다.
|
|
- provider-pool dispatch는 `in_flight >= capacity`인 provider를 후보에서 제외하고, 남은 후보 중 가장 낮은 `in_flight` 레벨을 먼저 선택한다. 같은 `in_flight` 레벨 안에서는 낮은 priority 값과 rotation으로 분산한다.
|
|
- dev-runtime managed capacity smoke는 같은 principal token으로 authenticated route alias를 먼저 조회한다. explicit `resource_selector`는 정확히 그 provider 하나만, `default` selector는 route profile/upstream과 model group이 모두 일치하는 healthy provider만 eligible pool로 본다. 현재 `ornith:35b`는 GX10 `4` + OneXPlayer `3`, `ornith-fast`는 RTX5090 `1`이며 다른 provider capacity를 더하지 않는다. Chat/Responses를 alias별로 실행하고 eligible total `capacity + 1` 요청에서 provider별 exact peak와 queue를 확인한다.
|
|
- managed smoke는 실제 emitted request JSON의 Unicode rune 수와 `runes/4 + runes/16` estimate를 계산하고 `long_context_threshold_tokens`와 대조한다. normal qualification은 `capacity`, 별도 long-context 시나리오는 `long_context_capacity`를 사용한다. 장문 반복/liveness payload로 normal capacity를 증명하거나 normal 요청으로 long slot을 증명하지 않는다. stopped Laguna는 capacity가 없고, unprojected Qwen `qwen3.6:35b`만 기존 model-group capacity `2` 기준을 유지한다.
|
|
- capacity smoke 완료 후 대상 provider의 `in_flight=0`, `queued=0` 회복을 확인한다.
|
|
- long-context admission 시나리오(normal 10-way, mixed long/normal, all-long-slot-full)와 최종 회복 근거는 `agent-test/dev/long-context-admission-smoke.md`와 `scripts/e2e-long-context-admission-smoke.sh`를 사용한다.
|
|
- `/v1/responses`와 `/v1/chat/completions`는 각각 짧은 입력에서 700~1200 token 수준의 구조화된 응답을 유도하고 provider-native thinking을 제한하며 50~100ms 간격으로 status를 polling한다. 각 요청의 HTTP 200, endpoint-native success terminal 정확히 1개, `[DONE]` 정확히 1개, selected provider의 eligible capacity 미초과, exact peak와 queue, 최종 0 회복을 별도 증거로 남긴다.
|
|
- 2026-08-15 `ornith:35b` default pool Chat 검증은 8/8 HTTP 200과 정상 terminal, GX10 `peak in_flight=4`, OneXPlayer `peak in_flight=3`, 합산 peak `7`, queue peak `2`, RTX peak `0`, final `0/0`으로 통과했다. 별도 Responses 검증은 5/5 HTTP 200과 각 `response.completed`는 확인됐지만 `[DONE]` terminal이 누락되어 fail-closed로 미통과 상태다. 이 미통과를 Responses capacity 완료 근거로 사용하지 않는다.
|
|
- managed smoke invocation마다 ignored `agent-test/runs/**` 아래 mode `0700` unique directory와 immutable run id를 생성한다. manifest가 소유하고 현재 run/dispatch 이후 생성된 request/result/status만 판정하며 stale/missing/foreign-run body는 실패한다. tracked/review evidence에는 sanitized summary의 run id, script hash, alias, selected provider, endpoint, computed shape/class, terminal count, peak/queue/final counter, outcome만 허용하고 token/header, route/slot id, prompt, response body와 출력은 기록하지 않는다.
|
|
- Qwen provider-pool smoke는 thinking/reasoning 텍스트가 포함될 수 있다. 추론 출력 자체를 실패로 보지 말고 HTTP 성공, model alias, final marker 포함 여부, provider node log/run count 증가로 판정한다. 응답 전체가 특정 token과 정확히 같은지 비교하는 strict exact-match는 이 profile의 기본 판정으로 쓰지 않는다.
|
|
- Qwen provider를 agent/tool-call 용도로 검증할 때는 일반 chat smoke와 별도로 forced tool call, auto tool call, streaming `delta.tool_calls`, multi-turn tool result 후 최종 답변을 확인한다. raw native marker나 reasoning text가 assistant content로 새면 해당 model/runtime의 parser/template profile 미확정으로 보고한다.
|
|
- Qwen runtime에는 Qwen 전용 parser/template 검증값만 사용한다. dev-corp Gemma 계열의 `tool_call_parser=gemma4`, `reasoning_parser=gemma4`, Gemma4 chat template/profile을 Qwen provider에 복사하지 않는다.
|
|
- bootstrap 사용자 명령은 완성된 URL과 positional token 하나만 포함한다.
|
|
|
|
## 기준 출력 예시
|
|
|
|
```text
|
|
edge> /nodes
|
|
[edge] sent run_id=...
|
|
[node-*-message] IOP_EXPECTED_REPLY
|
|
[node-*-event] complete
|
|
```
|
|
|
|
## 차단 기준
|
|
|
|
- dev host 또는 Edge-Node TCP port 접근이 불가능하다.
|
|
- 외부 CLI profile 검증에 필요한 CLI 설치, 계정, provider 상태가 없다.
|
|
- dev artifact/model/metrics 포트가 기존 field baseline과 충돌한다.
|
|
- Node 등록 시 `openai_compat adapter instance key "<provider-id>" conflicts with provider id`가 발생한다. 이는 agent orchestration 차단이 아니라 Edge config mapper 또는 stale binary 문제다. provider/adapter 정의를 삭제하지 말고 candidate source identity와 `go test -race ./apps/edge/internal/node`를 확인한 뒤 Edge를 먼저 교체한다.
|
|
|
|
## 보고 항목
|
|
|
|
- 실행한 명령:
|
|
- 성공한 검증:
|
|
- 실패/차단된 검증:
|
|
- 생략 사유:
|
|
- 남은 위험:
|
|
|
|
## 금지 사항
|
|
|
|
- secret, token, 개인 endpoint 원문은 tracked 파일에 기록하지 않는다.
|
|
- field baseline 포트(`18080`, `18081`, `19090`, `19092`)를 dev 전용 포트로 재사용하지 않는다.
|