api7 / api7/aisix

/v1/completions emits an empty applied_guardrails while its chain does run

Open Beginner friendly
#1,030 0 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Dominant language
Rust
Stars
157
Forks
32
Avg merge
1h 25m
Merged PRs (30d)
145

Description

Found by the independent pre-merge audit of #1028.

/v1/completions resolves a guardrail chain (crates/aisix-proxy/src/completions.rs, state.guardrail_index.resolve(&guardrail_ctx)) and runs both the non-segment check and the segment pass over the prompt — but never snapshots resolved_chain.applied(), and emit_usage_event never sets applied_guardrails. The emitted event leaves the field empty.

Every sibling handler fills it: chat, messages, responses, embeddings, rerank, images, images/edits, audio, videos, and — since AISIX-Cloud#1330 — /mcp. #379 added the field precisely so a /logs reader can see which guardrails governed a request, not just whether one refused it.

The failure is silent in the usual way: nothing errors, the guardrails still run and still enforce, and the row simply claims no guardrail governed the call. It is also now internally inconsistent — after #1028, a masked /v1/completions request carries guardrail_enforced_hits naming the policy that rewrote it while applied_guardrails says none was attached. A reader would file that contradiction as a bug.

Fix

Mirror what embeddings does, three lines:

let resolved_chain = state.guardrail_index.resolve(&guardrail_ctx);
let applied_guardrails = resolved_chain.applied().to_vec();   // add

thread it onto CompletionDispatchSuccess beside redactions / monitor_hits, and set applied_guardrails: applied_guardrails.to_vec() in emit_usage_event. embeddings.rs and rerank.rs are the templates, including their applied_guardrails_recorded_on_usage_event tests.

Not folded into #1028 because every changed line there traces to the enforced-hit drain; this is a sibling field with its own issue number (#379).

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start in crates/aisix-proxy/src/completions.rs, tracing the resolved guardrail chain through CompletionDispatchSuccess and emit_usage_event. Compare embeddings.rs and rerank.rs, including their applied_guardrails_recorded_on_usage_event tests; done means the completion usage event records the applied chain and the corresponding test passes.

Written by the indexing model from the issue text.

Assessment

Tech stack
rust
Domain
backend-api-design, observability
Issue type
Bug
Difficulty
2/5
Estimated time
1-3 hours
Activity status
Active
Clarity
Clearly specified
Newbie friendliness
88/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.