mlflow/mlflow · error · GuardrailViolation

Sanitization requires an action_llm_url but none was configu

Error message

Sanitization requires an action_llm_url but none was configured.

What it means

MLflow Gateway guardrail sanitization delegates the actual sanitization work to a secondary 'action LLM' endpoint. This GuardrailViolation is raised when the guardrail is configured to sanitize a payload but the guardrail instance has no action_llm_url (or action_endpoint_name) set, so there is nowhere to send the sanitization request.

Source

Thrown at mlflow/gateway/guardrails.py:228

        self,
        payload: dict[str, Any],
        rationale: str,
        auth_headers: dict[str, str] | None = None,
        usage_tracking: bool = False,
        payload_schema: dict[str, Any] | None = None,
    ) -> dict[str, Any]:
        """Send the full payload to the action endpoint LLM for rewriting.

        Posts a chat request to ``action_llm_url`` which is the fully
        resolved gateway invocations URL.

        When ``payload_schema`` is provided the sanitization request includes a
        ``response_format`` constraint so the action LLM returns a JSON object
        that matches the schema.  Pass ``None`` (the default) for passthrough or
        request-side payloads where no schema constraint is needed.
        """
        if not self.action_llm_url or not self.action_endpoint_name:
            raise GuardrailViolation(
                self.name,
                "Sanitization requires an action_llm_url but none was configured.",
            )

        url = self.action_llm_url
        path = f"gateway/{self.action_endpoint_name}/mlflow/invocations"
        body: dict[str, Any] = {
            "messages": [
                {
                    "role": "user",
                    "content": _SANITIZE_SYSTEM_PROMPT.format(
                        rationale=rationale,
                        payload_json=json.dumps(payload, indent=2),
                    ),
                },
            ],
        }
        if payload_schema is not None:

View on GitHub (pinned to 6a27f2decc)

Solutions

  1. Add action_llm_url and action_endpoint_name to the guardrail configuration pointing at a valid gateway LLM endpoint.
  2. If sanitization is not needed, change the guardrail action to 'validation' (block) or 'info' instead of 'sanitize'.
  3. Validate the guardrail config at load time before deploying the gateway.

Example fix

// before
"guardrails": [{"name": "pii", "action": "sanitize"}]
// after
"guardrails": [{"name": "pii", "action": "sanitize", "action_llm_url": "http://localhost:5000/api/2.0/gateway", "action_endpoint_name": "sanitizer-llm"}]
Defensive patterns

Strategy: validation

Validate before calling

if not guardrail.action_llm_url or not guardrail.action_endpoint_name:
    raise ValueError(f"Guardrail {guardrail.name}: sanitization requires action_llm_url and action_endpoint_name")

Type guard

def is_sanitization_ready(g) -> bool:
    return bool(getattr(g, 'action_llm_url', None)) and bool(getattr(g, 'action_endpoint_name', None))

Try / catch

try:
    payload = await guardrail.process_request(payload, ...)
except GuardrailViolation as e:
    logger.error("Guardrail %s misconfigured: %s", e.guardrail_name, e)
    raise

Prevention

When it happens

Trigger: A guardrail with action=sanitize (VALIDATION passes without needing it) processes a payload via _enforce -> _sanitize while the guardrail config lacks action_llm_url/action_endpoint_name.

Common situations: Gateway route config defines a guardrail but omits the action-LLM endpoint settings; the guardrail is only validated for detection, not for sanitization; config was migrated or hand-edited and the action LLM block was dropped.

Related errors


AI-assisted analysis of mlflow/mlflow@6a27f2decc (2026-08-29). Data as JSON: /api/errors/b6da38ccd0cf817d. Report an issue: GitHub.