system: OPERATIONAL
← back to all hacks
INFRASTRUCTURE CRITICAL NEW

Vector-store metadata filters are an injection sink in Spring AI

Spring AI passed user-controlled filter strings and document IDs straight into each backend's native query language, turning RAG metadata filtering into classic SQL and query injection across five vector stores.

2026-07-16 // 6 min affects: spring-ai, pgvector, elasticsearch, opensearch, gemfire, cosmosdb

What is this?

Spring AI is the Spring framework’s official abstraction layer for building LLM features into Java applications, and it has become the de facto standard for retrieval-augmented generation (RAG) on the JVM. Its vector-store abstraction lets an application store embeddings and then query them with a metadata filter — a small expression such as “return only documents where tenant = X and year > 2024.” Between April and June 2026, Spring published a run of advisories showing that several of these vector-store integrations built the underlying database query by pasting user-controlled input directly into the backend’s native query language. The result is a textbook injection flaw, resurfacing inside the AI stack: the metadata filter, meant to narrow a search, becomes a channel for running arbitrary queries against the store.

Two advisories anchor the pattern. One, published on 27 April 2026, is a SQL injection in Spring AI’s Azure Cosmos DB vector store, reachable when an application passes user-supplied values as document IDs into the delete path. The second, published on 12 June 2026, covers the Elasticsearch, OpenSearch, and GemFire vector stores, where special characters in a filter string could force execution of arbitrary queries against those engines. Both are rated High.

How it works

The abstraction leaks in the same place each time: translating a portable metadata filter into a concrete query for one specific store. When that translation concatenates raw strings instead of using the backend’s parameter binding, any operator characters the user controls change the meaning of the query rather than being treated as data.

In the Cosmos DB case, the affected code path built a SQL statement for a delete operation from document IDs. An application that forwarded end-user input as those IDs handed the attacker a lever to break out of the intended WHERE clause and reach rows they should never touch. In the Elasticsearch, OpenSearch, and GemFire case, crafted characters inside the filter expression escaped the intended query structure and were interpreted by the target engine. The vulnerability is not in the vector database itself — Postgres/pgvector, Elasticsearch, OpenSearch, GemFire, and Cosmos DB all offer safe parameterized query paths — but in the glue code that assembled queries by string-building. We describe the mechanism, not any working payload.

The reason this matters for RAG specifically is that metadata filters are usually driven by request context: the tenant, the user, the document scope. That is exactly the untrusted, per-request input that classic injection thrives on, and RAG pipelines route it into a data store that holds every document the application has ingested.

Why it matters

A metadata filter injection collapses the isolation that RAG deployments lean on. If an attacker can rewrite the filter, they can potentially read documents belonging to other tenants, bypass access scoping, or — depending on the operation and the store — delete or alter stored vectors and their source records. In a multi-tenant enterprise Java application, that is a direct confidentiality and integrity failure in the layer that was supposed to keep customers’ data apart. The Cosmos DB issue reaches high confidentiality, integrity, and availability impact; the Elasticsearch/OpenSearch/GemFire issue is reachable without prior authentication in affected configurations.

The timing is not a coincidence. Java-side reporting around the UberConf 2026 gathering (14 July 2026) noted that Spring security advisories spiked more than seventeen-fold in April 2026 versus historical norms, largely because AI-assisted vulnerability scanners began finding bugs across the Spring dependency graph faster than ever — prompting what Broadcom described as the largest batch of Spring security updates in the framework’s history. The same reporting flags a separate expression-language injection in RAG pipeline code that reached remote code execution in a proof of concept, underlining that the RAG plumbing, not just the model, is now an active attack surface.

Defenses

  • Upgrade. Move to the fixed Spring AI releases — 1.0.6 / 1.1.5 for the Cosmos DB issue, and 1.0.9 / 1.1.8 for the Elasticsearch, OpenSearch, and GemFire issue. The maintainers state no other mitigation is required once patched.
  • Never build store queries by string concatenation. Use each backend’s parameterized query or prepared-statement API so that user-influenced values are always bound as data, never parsed as query syntax. This is the root-cause fix for the whole class.
  • Treat the metadata filter as untrusted input. Where filters or document IDs are derived from request context, validate them against an allowlist of expected fields, operators, and value types before they reach the store. Reject unexpected operator characters rather than trying to escape them.
  • Scope database credentials to least privilege. The RAG service’s store account should be limited to the collections and operations it genuinely needs, so a successful injection cannot reach unrelated data or destructive operations.
  • Enforce tenant isolation below the filter. Do not rely on an application-level filter string as the only boundary between tenants; back it with row-level security, per-tenant collections, or separate indices so a rewritten filter does not equal a cross-tenant read.
  • Log and monitor store queries. Capture the generated queries and alert on anomalies — unexpected operators, oversized filters, or delete operations with attacker-shaped IDs — to catch exploitation attempts and regressions.

Status

ItemValue
ClassInjection via vector-store metadata filters / document IDs in a RAG framework
Affected frameworkSpring AI 1.0.x and 1.1.x vector-store integrations
Stores implicatedAzure Cosmos DB; Elasticsearch, OpenSearch, GemFire (pattern is store-glue, not the databases)
ImpactCross-tenant read, and depending on operation, tampering or deletion of stored data
Fix versions1.0.6 / 1.1.5 (Cosmos DB); 1.0.9 / 1.1.8 (Elasticsearch / OpenSearch / GemFire)
Disclosed27 April 2026 and 12 June 2026 (vendor advisories); reported responsibly
ReferencesCVE-2026-40978, CVE-2026-47835

Key dates: 27 April 2026 — Cosmos DB vector-store SQL injection advisory (CVE-2026-40978), reported by SharlongWen. 12 June 2026 — Elasticsearch/OpenSearch/GemFire filter injection advisory (CVE-2026-47835), reported by Nitro Cao of Alibaba Cloud. 14 July 2026 — Java-ecosystem reporting on the April 2026 Spring advisory surge and the RAG-pipeline expression-language injection (referenced as CVE-2026-22738). Version numbers and credits are those stated in the vendor advisories.

Sources