Option B — User-level (email-based) access
Per-user row isolation using the authenticated user's email address. Users in the same Cognito group can see different rows of the same table.
- How it works: Cognito groups → IAM roles → Lake Formation data cell filters with
owner_email = '${session:UserEmail}'. - Best for: scenarios where each user should only see their own records (for example sales reps see only their own leads).
- Requires: the
sts:TagSessionpermission on every IAM role, and theemailscope on the Cognito app client.
Complete Set up Amazon Cognito first, including the email scope and read attribute on the app client.
Step 1: Prepare Lake Formation​
- In the Lake Formation Console go to Data lake locations → Register location. Register the S3 paths where your data resides (e.g.
s3://my-athena-data-bucket/) and select the IAM role Lake Formation should use to access the data (or use the service-linked role). - Under Administrative roles and tasks → Data lake administrators, add your admin IAM user or role.
Step 2: Create an email-based data cell filter​
Data cell filters give you row-level (and column-level) security.
- Go to Data filters → Create new filter.
- Configure the filter for each table that holds per-user data:
Filter name: email_row_filter
Target database: my_analytics_db
Target table: transactions
Row filter expression: owner_email = '${session:UserEmail}'
The ${session:UserEmail} variable is resolved to the authenticated user's email address at query time, so one filter serves every user.
Step 3: Grant SELECT through the filter​
- Go to Data lake permissions → Grant.
- Select IAM users and roles → choose the IAM role for the Cognito group.
- Under LF-Tags or catalog resources, select the database and table.
- Under Data filters, select the cell filter you created.
- Grant SELECT.
Step 4: Add sts:TagSession to every IAM role​
Every IAM role mapped to a Cognito group must include the sts:TagSession permission. This lets the UserEmail session tag propagate through the assume-role chain to Lake Formation.
Add this statement to each role's permissions policy:
{
"Sid": "AllowTagSession",
"Effect": "Allow",
"Action": "sts:TagSession",
"Resource": "*"
}
Without sts:TagSession, the ${session:UserEmail} variable in Lake Formation data cell filters will not resolve, and queries will silently return zero rows instead of failing with an error.
Step 5: Confirm the Cognito email scope​
Make sure your Cognito App Client (from Cognito setup, Step 2) has:
emailin AllowedOAuthScopesemailin ReadAttributes
This ensures the ID token contains the email claim, which is used as the session tag value.
Verify​
Sign in as two users in the same group. Each should see only the rows whose owner_email matches their own address. If either sees zero rows, re-check sts:TagSession and the email scope.