# Sovereign RAG: data sovereignty on AWS

> Explore data sovereignty in a Sydney-region RAG system: regional Bedrock inference, S3 Vectors, IAM controls and interactive AWS architecture explanations.

Source: https://krishparekhdev.com/blog/sovereign-rag
Published: 2026-10-12
Tags: ai, rag, aws, bedrock, data-sovereignty

---

A support assistant does more than store documents.
It sends questions, retrieved text and conversation history to services that process them.
Each step creates a data boundary worth checking.

Sovereign RAG explores a customer-support assistant with an AWS Sydney architecture.
The question is not only whether the answer is useful.
It is also where the data travels, who can access it, and which controls enforce those choices.

This article follows the [Sovereign RAG repository](https://github.com/Krish-Parekh/sovereign-rag), including its Terraform and answer code.
The diagrams come from that repository. The interactive examples do not call AWS.

## Why data sovereignty changes the design

Data residency concerns the location of data storage and processing.
Data sovereignty also concerns control over that data and the jurisdiction that applies to it.
A regional deployment contributes to that goal. It does not establish every governance or compliance requirement by itself.

For RAG, the data includes source documents, embeddings, questions, retrieved passages, responses and logs.
Keeping an S3 bucket in Sydney does not prove that every model request stays there.
The inference path needs its own checks.

[AWS documents cross-region inference](https://docs.aws.amazon.com/bedrock/latest/userguide/cross-region-inference.html) as a separate routing choice.
An inference profile can send a request to another destination region.
A source endpoint in Sydney alone therefore does not establish a Sydney processing boundary.

## Start with the complete data path

![Sovereign RAG architecture with AWS services inside ap-southeast-2 and separate ingestion and retrieval flows](https://krishparekhdev.com/images/blog/sovereign-architecture.webp)

Repository diagram: document ingestion and answer generation both need regional controls.

The project targets `ap-southeast-2` for its cloud resources.
Its Terraform variable checks that exact region.
The AWS provider uses that variable.
The application also configures regional Bedrock clients.

The inference permissions reference the Sydney foundation-model ARN for `qwen.qwen3-32b-v1:0`.
The embedding permissions reference the regional Titan V2 model ARN.
Relevant IAM statements also require `aws:RequestedRegion` to match the configured region.

These are concrete controls in the repository, rather than a regional label on a diagram.
They scope the permissions that these policies grant.
They are not an organization-wide denial of every other region or proof of the deployed account's full policy state.

## Inspect the regional controls

Select a layer below to inspect its control and remaining boundary.
Then compare a regional model call with a hypothetical cross-region profile.
The comparison explains a design decision. It does not change the actual project configuration.

[Interactive example: SovereigntyExplorer. See the source page for controls. The surrounding text explains the example.]

## Ingestion: keep documents and embeddings in the regional path

The preparation script reads the sample WixQA corpus on the operator's machine.
It uploads markdown and metadata to an [Amazon S3](https://aws.amazon.com/s3/) bucket.
That source preparation happens outside the AWS architecture boundary.

[Bedrock Knowledge Bases](https://docs.aws.amazon.com/bedrock/latest/userguide/knowledge-base.html) ingests the documents.
[Titan Text Embeddings V2](https://docs.aws.amazon.com/bedrock/latest/userguide/titan-embedding-models.html) converts document chunks into vectors.
[S3 Vectors](https://docs.aws.amazon.com/AmazonS3/latest/userguide/s3-vectors.html) stores those vectors for similarity search.

![WixQA corpus preparation on a laptop followed by S3, Knowledge Bases, Titan V2 and S3 Vectors in Sydney](https://krishparekhdev.com/images/blog/sovereign-ingest.webp)

Repository diagram: the laptop-to-S3 upload crosses the boundary. Embedding and indexing form the regional ingestion path.

The documents bucket blocks public access and denies insecure transport.
The knowledge-base role scopes document reads to the corpus path.
Its embedding and vector permissions use specific resources and region conditions.
Documents and vector records remain distinct assets that need access and deletion controls.

## Requests: identity, retrieval and inference

[Amazon Cognito](https://aws.amazon.com/cognito/) supplies the caller's identity.
[API Gateway](https://aws.amazon.com/api-gateway/) checks the token and requires an API key.
[AWS Lambda](https://aws.amazon.com/lambda/) then coordinates the answer flow.
The API key supplements authentication. It does not replace the Cognito identity.

![Question flow through Cognito, API Gateway, Lambda, input guardrail, retrieval, model generation and output guardrail](https://krishparekhdev.com/images/blog/sovereign-ask.webp)

Repository diagram: identity and data controls apply before and after model generation.

Lambda applies [Bedrock Guardrails](https://docs.aws.amazon.com/bedrock/latest/userguide/guardrails.html) to the incoming question.
It stores masked conversation turns in [DynamoDB](https://aws.amazon.com/dynamodb/).
It retrieves relevant sources with a role filter before sending them to Qwen3 32B through [Bedrock](https://aws.amazon.com/bedrock/).
An output guardrail checks the response before storage and return.

The model request contains retrieved source text and recent completed conversation turns.
These are part of the processing boundary, even when the original documents remain in S3.
The runtime uses the regional Bedrock endpoint and a direct model ID, rather than a configured cross-region inference profile.

## Sovereignty also needs access control

Customers can retrieve help articles.
Staff can also retrieve known issues and feature requests.
The backend reads the role from Cognito claims and sends an `article_type` filter with the retrieval request.

The model does not decide which role the caller holds.
A prompt instruction cannot replace the backend filter.
Try a known-issue question as each role below.

[Interactive example: SovereignRagExplorer. See the source page for controls. The surrounding text explains the example.]

The documents in this example are synthetic.
The widget demonstrates filtering, not an access boundary inside your browser.
The repository's server code supplies the actual role-based retrieval boundary.

## Logs and retention are part of the architecture

The application writes request metadata to [CloudWatch](https://aws.amazon.com/cloudwatch/), rather than logging the question and answer in its handler.
Terraform sets the Lambda log group's retention to 14 days.
The chat records use a 30-day expiry with DynamoDB TTL.
TTL expiry does not guarantee immediate deletion at the exact expiry time.

![Sovereign RAG AWS services grouped by identity, orchestration, retrieval, generation, storage and operations](https://krishparekhdev.com/images/blog/sovereign-stack.webp)

Repository diagram: every service has a role in the data lifecycle, including logs and infrastructure controls.

| Service | What it controls or supplies |
| --- | --- |
| [S3](https://aws.amazon.com/s3/) | Stores the document corpus. |
| [S3 Vectors](https://docs.aws.amazon.com/AmazonS3/latest/userguide/s3-vectors.html) | Stores the vector index. |
| [Bedrock Knowledge Bases](https://docs.aws.amazon.com/bedrock/latest/userguide/knowledge-base.html) | Ingests documents and retrieves source chunks. |
| [Titan V2](https://docs.aws.amazon.com/bedrock/latest/userguide/titan-embedding-models.html) | Produces embeddings for ingestion. |
| [Qwen3 on Bedrock](https://docs.aws.amazon.com/bedrock/latest/userguide/model-card-qwen-qwen3-32b.html) | Generates the answer from retrieved sources. |
| [Bedrock Guardrails](https://docs.aws.amazon.com/bedrock/latest/userguide/guardrails.html) | Applies input and output content controls. |
| [Cognito](https://aws.amazon.com/cognito/) | Supplies authenticated identities and staff group claims. |
| [API Gateway](https://aws.amazon.com/api-gateway/) | Provides the regional request endpoint. |
| [Lambda](https://aws.amazon.com/lambda/) | Coordinates masking, retrieval and generation. |
| [DynamoDB](https://aws.amazon.com/dynamodb/) | Stores conversation records with expiry. |
| [CloudWatch](https://aws.amazon.com/cloudwatch/) | Stores operational logs. |
| [IAM](https://aws.amazon.com/iam/) | Scopes workload permissions to resources and regions. |
| [Terraform](https://developer.hashicorp.com/terraform) | Defines the infrastructure and regional validation. |

## What this architecture establishes, and what it does not

The repository defines a regional storage and inference design with resource-scoped permissions.
It also defines identity, retrieval filtering, masking and retention settings.
These controls make the data path explicit and reviewable.

The API remains reachable over the network. This is not a fully private VPC-only system.
Operators must also check client machines, backups, account permissions, encryption requirements and service-specific data handling.
Changing models or inference profiles requires another review of processing destinations.

[AWS's data-protection guidance](https://docs.aws.amazon.com/bedrock/latest/userguide/data-protection.html) describes the shared responsibility for these choices.
The architecture does not certify compliance, or prove that every personal detail receives masking.
Source citations also need separate checks for whether they support the generated claims.

Inspect the [region validation](https://github.com/Krish-Parekh/sovereign-rag/blob/main/infra/variables.tf),
[model and API permissions](https://github.com/Krish-Parekh/sovereign-rag/blob/main/infra/api.tf),
[ingestion permissions](https://github.com/Krish-Parekh/sovereign-rag/blob/main/infra/knowledge.tf),
and [storage controls](https://github.com/Krish-Parekh/sovereign-rag/blob/main/infra/storage.tf).
For a different boundary, read [Wayfinder's A2A and long-term memory design](/blog/wayfinder).
