# AWS (/docs/integrations/aws)



Trace connects to AWS using a cross-account IAM role with **read-only** permissions, so it can inventory what you've deployed and understand how your application is actually reachable. Nothing in your AWS account changes; Trace only reads.

<DashboardAction to="settings/integrations/cloud/aws" label="Connect an AWS account" description="Generate the external ID and CloudFormation template for the read-only role." />

How it works [#how-it-works]

1. From **Settings → Integrations → Cloud → AWS** in the dashboard, generate the onboarding artifacts. Trace produces an external ID unique to your organization and a CloudFormation template that creates a read-only role.
2. Deploy the CloudFormation stack in your AWS account. The template creates an IAM role scoped to the external ID, so only Trace can assume it.
3. Paste the role ARN back into the dashboard. Trace verifies access through AWS STS and starts the initial sync.
4. Trace inventories your account on a recurring basis: accounts, regions, key resource types, and the relationships between them. Public-facing resources are tagged so you can spot them at a glance.

Connecting more than one account [#connecting-more-than-one-account]

One Trace integration covers as many AWS accounts as you need, and every account uses the same template, role name, and external ID. To add an account, open the AWS integration page and choose **Add account**, deploy the same stack in the new account, then paste that account's role ARN. Each account shows up as its own row with its status, template version, and last verification.

If you connect more than one account, give each one a description of what runs in it, for example, Production API and databases.

You can disconnect accounts one at a time. Disconnecting the last connected account disconnects the integration as a whole; reconnecting later issues a new external ID, so the stacks need to be redeployed with it.

When a newer Trace template is available, **I've updated** checks every connected account. Accounts that are already on the new version are recorded as such, and the banner stays up until all of them are, naming the accounts that still need the update.

What Trace sees [#what-trace-sees]

Trace's IAM role grants **read-only** access. We can list and describe your cloud resources, and read secret values and stored data only if you turn those groups on. We cannot create, modify, or delete anything. The CloudFormation template is published with your onboarding artifacts so you can audit every permission before deploying.

Choosing what Trace can read [#choosing-what-trace-can-read]

The role is split into permission groups. Each group is one read-only managed policy you can switch on or off. On the AWS integration page, the Access row lists every group, checked to the recommended set. Uncheck a group to leave it out, or check a sensitive group to add it: the CloudFormation link and the Terraform and CDK snippets follow your choices. When you verify, Trace reads what the role actually grants, so the Access column shows what AWS reports.

<AwsPermissionGroupsTable />

Not included: creating, changing, or deleting anything.

To change an account's access later, choose **Change access** on its row. Trace lists the stack parameters to change and gives you the same change as one AWS CloudShell command; Terraform and CDK users get the updated configuration. After the update finishes, choose **Check access**.

When you disconnect, Trace retains your inventory for a fixed grace period (visible on the integration page) so you don't lose context if you reconnect, then deletes it.

Sensitive, off by default [#sensitive-off-by-default]

These groups read the contents of secrets and data, not only settings. With one on, Trace's pentest agent reads those values during a pentest, and what it reads is stored with the pentest's records.

<AwsPermissionGroupsTable sensitive />

Why connect AWS [#why-connect-aws]

Source code alone can't tell you what's *actually* reachable in your live environment. Cloud inventory closes that gap: Trace flags resources exposed to the internet (public services, open ports, reachable databases, open storage buckets, serverless function URLs, and exposed management endpoints) that never show up in source alone. During a penetration test, Trace uses your real topology (which services are public, which paths connect to them, where a data store actually sits) to confirm whether a weakness is genuinely reachable and exploitable, rather than only theoretically vulnerable. All cloud access during an engagement stays read-only and short-lived; Trace never modifies your cloud.

**GCP** is supported — see the [GCP integration](/docs/integrations/gcp). Support for **Azure** is on the roadmap; reach out to the Trace team if you'd like early access.
