A SaaS company uses a single Azure AI Search index containing documents from multiple customer tenants. Each document in the index has a 'tenantId' field. A Copilot Studio agent is deployed for each tenant, and each agent must only return search results belonging to its own tenant. Which Azure AI Search feature should the developer use to enforce this per-tenant data isolation at query time?
Select an answer to reveal the explanation.
Short Explanation and Infographic
An OData filter is like putting a WHERE clause on your search—it's fast, happens at the index level before results are returned, and costs almost nothing in compute. It's the right tool when you have a shared index with a discriminator field like tenantId.
Full explanation below image
Full Explanation
Azure AI Search supports OData filter expressions that can be applied to any query. These filters are evaluated server-side before results are returned, making them highly efficient for data isolation. When a Copilot Studio agent's knowledge source is configured to query Azure AI Search, the developer can inject a filter parameter such as $filter=tenantId eq 'contoso' so only documents belonging to the correct tenant are included in the search results.
Option A is correct because OData filter expressions are the standard, supported mechanism for query-time data isolation in Azure AI Search. The tenantId field is a filterable field in the index, and the filter is applied at the Azure AI Search service level before any results are returned to the agent. This is efficient, secure (the filter runs server-side), and does not require separate infrastructure per tenant.
Option B is wrong in the context of this question. While creating separate indexes per tenant is architecturally valid for strict isolation and is a recognized pattern for small tenant counts, the scenario explicitly uses a single shared index and asks how to enforce isolation at query time. Separate indexes do not answer the query-time isolation question and are operationally expensive for large numbers of tenants.
Option C is wrong because semantic ranking is a relevance mechanism, not a security/isolation mechanism. Boosting documents matching a tenant's name in the query string is unreliable—it might surface some correct documents but would never reliably exclude all documents from other tenants. A tenant named 'Contoso' could accidentally surface 'ContosoSupplier' documents.
Option D is wrong because Azure AI Search does not have a native 'row-level security' feature similar to SQL row-level security. There is no built-in mechanism to automatically filter results based on an authenticated user's tenant at the index configuration level. OData filters at query time are the supported approach for this pattern.
Exam tip: OData filters in Azure AI Search are the correct tool for query-time field-value restrictions. Know the syntax pattern: $filter=fieldName eq 'value'. For filterable fields, this is applied before results are returned and cannot be bypassed by the caller when injected server-side. The 'required' use of filterable fields is a common multi-tenant architecture pattern in Azure AI Search.