feat(llm-access): add standalone Codex image gateway#52
Conversation
There was a problem hiding this comment.
Code Review
This pull request introduces a new standalone Codex image gateway (llm-access-codex-image crate) along with corresponding frontend UI, database migrations, and deployment configurations to support image generation and edit requests. Feedback on the implementation highlights several performance and efficiency improvements: offloading blocking log file I/O and synchronous lock acquisition to a dedicated thread pool using tokio::task::spawn_blocking, reusing a default reqwest::Client to leverage connection pooling, parsing route.auth_json once per loop instead of multiple times, simplifying redundant string checks in the frontend, and keeping the log file handle open to avoid redundant system calls on every append.
Important
The consumer version of Gemini Code Assist on GitHub is being sunset. Starting June 18, 2026, new organization installations will be blocked, and all code review activity will officially cease on July 17, 2026.
For more details on the timeline and next steps, please review the Help Documentation.
acking-you
left a comment
There was a problem hiding this comment.
🔍 PR #52 详细评审 — 独立 Codex 图像网关
对本 PR(新增 llm-access-codex-image 独立图像网关 + store/migration/admin/frontend/部署脚本改动,约 2400 行新增)做了一次系统性评审:按 DB/SQL/迁移、请求分发与故障转移、并发与阻塞 I/O、请求校验与安全/脱敏、前端与 admin API、部署脚本/systemd/Caddy、测试覆盖 七个维度分别审查,每条结论再经独立的对抗式复核(重新读源码 + 校验锚点),以下 25 条均为复核通过后的发现。
严重度分布: 🟡 medium ×12 · 🔵 low ×10 · ⚪ nit ×3
已确认正确、无需改动
- SQL 列序与解码下标一致:
keys.rs各 SELECT 在codex_strict_session_rejection_enabled之后插入codex_image_generation_enabled,与decode.rs::decode_key_bundle的row.get(20)、credit_totalget(32)、rollup28..35全部对齐;INSERT 为 22 列 / 22 占位符 / 22 绑定一致;codex_account.rs两条 SELECT 的新列均落在序号 10/11,与decode_codex_admin_account_list_row匹配。无 off-by-one 问题。 - Caddy 路由顺序正确:
@codex_image的 handle 在更宽泛的/api/codex-gateway/*(@llm_access)之前,图像专用路径会被优先命中。 - 各处新增字段的
#[serde(default)]/ 默认值(前后端默认并发均为 3、上限均为 1024)保持了向后兼容与前后端一致。
需重点关注
/v1/images/edits以application/json转发而非 multipart — 仓库内既有的gpt2api_rs.rs对 edits 走的是 multipart,建议先核实backend-api/codex图像端点真实契约,否则 edit 请求可能整体失败。- 图像网关
connect_read_only跳过迁移,但 key SELECT 硬引用 0030 才新增的列 — 若在控制库尚未应用 0030 时独立部署,鉴权后所有请求 500;建议启动期快速失败 + 部署顺序文档化。 prepare/activate发布脚本 把 image-only 发布与共享neon.env耦合:prepare对所有目标强制要求 image 专属环境变量(打断既有 api-only/worker-only 发布);activate的 image 目标会覆盖文本服务共享的neon.env。- 图像流量在 per-key 维度既不计量也不限流(仅 per-account 并发上限),
remaining_billable闸门对图像实际不生效 — 需确认是否为有意设计。
评审说明:本次为以"在对应代码位置留下可执行建议"为目标的细评,含若干 low/nit 项(多为测试加固与可观测性),可按优先级择取。
|
You have reached your Codex usage limits. You can see your limits in the Codex usage dashboard. |
Summary
Adds a standalone Codex image gateway binary for
gpt-image-2generation/edit requests so image traffic can be routed, limited, and logged independently from the existing text/adminllm-accessservice.Root cause
Codex image requests share upstream Codex usage limits, but running them through the existing
llm-accessbinary would mix image request handling with text dispatch, token refresh, usage rollups, and worker-owned persistence paths. The new service keeps the image path read-only against the control plane and avoids writing usage rollups.What changed
llm-access-codex-image, listening on127.0.0.1:19082by default, with JSON-only validation for/v1/images/generationsand/v1/images/editsaliases.3.Test Plan
cargo test -p llm-access-codex -p llm-access-core -p llm-access-store -p llm-access -p llm-access-codex-image --jobs 4 --no-fail-fastcargo test -p static-flow-frontend --jobs 4 --no-fail-fastcargo test -p llm-access-codex-image --jobs 4 --no-fail-fastcargo clippy -p llm-access-codex -p llm-access-core -p llm-access-store -p llm-access-migrations -p llm-access -p llm-access-codex-image -p static-flow-frontend --jobs 4 -- -D warningsbash scripts/test_llm_access_cloud_bundle.shbash scripts/test_llm_access_cloud_release_scripts.shCARGO_TARGET_DIR=/mnt/wsl/data4tb/static-flow-data/cargo-target/static_flow bash scripts/build_frontend_selfhosted.shAdditional context
The image gateway intentionally does not refresh Codex tokens, persist auth failures, write DuckDB usage facts, or update key usage rollups. Existing
llm-accessrefresh/status workers remain the write path for Codex account state.