Skip to Content
PlatformIntegration GuidesAWS (Manual Setup)

Setting up an AWS Integration

CloudQuery Platform authenticates with AWS through cross-account IAM roles using IAM Roles for Service Accounts (IRSA). This guide walks through the manual setup process. For an automated approach using CloudFormation, see the AWS Onboarding Wizard.

The AWS accounts involved are:

  • CloudQuery Account: The AWS account where CloudQuery Platform is deployed. This account hosts the IAM role that CloudQuery uses to assume roles in other accounts.
  • Your Account: The AWS account you want to sync resources from. You create a role here that allows the CloudQuery account’s role to assume it and read resources.

Prerequisites

  • A CloudQuery Platform account with admin access
  • AWS CLI installed and configured with credentials that have IAM administrative permissions
  • Your AWS account ID
  • EXTERNAL_ID — Generate this yourself (e.g., by running uuidgen). An external ID is recommended by AWS best practices to provide an additional verification layer when assuming roles in a third-party account. It can be any alphanumeric string between 2 and 1224 characters.

Add your generated EXTERNAL_ID as a secret in the Secrets section of your AWS integration configuration before proceeding.

IAM role and permissions

Use this approach to sync from one AWS account.

  1. Create the trust relationship for the cross-account role:

Replace <CLOUDQUERY_AWS_ACCOUNT_ID> with the CloudQuery AWS Account ID found in the side panel documentation on the integration UI page in CloudQuery Platform. Replace <TENANT_ID> with your tenant ID from the “Setup guide” section when configuring the integration. Replace <EXTERNAL_ID> with your generated external ID.

cat >third-party-trust.json <<EOF { "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "AWS": "arn:aws:iam::<CLOUDQUERY_AWS_ACCOUNT_ID>:role/syncs-<TENANT_ID>-role" }, "Action": "sts:AssumeRole", "Condition": { "StringEquals": { "sts:ExternalId": "<EXTERNAL_ID>" } } } ] } EOF
  1. Create the cross-account role and attach the ReadOnly policy:
aws iam create-role --role-name cross-account-readonly-role \ --assume-role-policy-document file://third-party-trust.json aws iam attach-role-policy \ --role-name cross-account-readonly-role \ --policy-arn="arn:aws:iam::aws:policy/ReadOnlyAccess"

The ReadOnlyAccess managed policy grants broad read permissions across all AWS services. If you need narrower permissions, create a custom policy that includes only the services you plan to sync.

Configuring the integration

After creating the IAM role in your AWS account, configure the integration in CloudQuery Platform.

  1. Navigate to Data PipelinesIntegrations in CloudQuery Platform.
  2. Click Create Integration and select AWS.

AWS YAML Configuration

  1. Update the YAML configuration with the role ARN and external ID. Use the appropriate format for your setup:
kind: source spec: name: aws path: cloudquery/aws registry: cloudquery version: "v33.20.0" tables: - aws_ec2_instances - aws_s3_buckets spec: accounts: - account_name: <YOUR_ACCOUNT_NAME> role_arn: "arn:aws:iam::<YOUR_ACCOUNT_ID>:role/cross-account-readonly-role" external_id: "${EXTERNAL_ID}"

Replace <YOUR_ACCOUNT_ID> with your AWS account ID. The role_arn should correspond to the cross-account-readonly-role created in the previous step. The external_id value must match the EXTERNAL_ID secret you configured in the Secrets section.

The tables list above is an example. Customize it to include the tables you need. See the AWS integration tables for the full list of available tables. Use ["*"] to sync all tables (this may increase sync time significantly).

  1. Click Test Connection to verify the setup.

What gets synced

The AWS integration can sync over 500 tables across all major AWS services. Some of the most commonly used tables include:

CategoryTablesDescription
Computeaws_ec2_instances, aws_lambda_functionsEC2 instances, Lambda functions
Storageaws_s3_buckets, aws_ebs_volumesS3 buckets, EBS volumes
Networkingaws_ec2_vpcs, aws_ec2_security_groups, aws_ec2_subnetsVPCs, security groups, subnets
Identityaws_iam_roles, aws_iam_users, aws_iam_policiesIAM roles, users, policies
Databasesaws_rds_instances, aws_rds_clustersRDS instances and clusters

See the full AWS table list for all available tables.

Verify the integration

After your first sync completes, open the SQL Console and run these queries to confirm data arrived:

-- Count synced EC2 instances SELECT count(*) FROM aws_ec2_instances
-- List synced AWS accounts and regions SELECT DISTINCT account_id, region FROM aws_ec2_instances
-- View S3 buckets across accounts SELECT account_id, name, region FROM aws_s3_buckets LIMIT 10

You can also browse your AWS resources in the Asset Inventory under the Compute, Storage, Networking, and other categories.

Troubleshooting

IssueCauseFix
AccessDenied when assuming roleTrust relationship misconfiguredVerify the Principal ARN in the trust policy matches the CloudQuery account role exactly. Check that <CLOUDQUERY_AWS_ACCOUNT_ID> and <TENANT_ID> are correct.
External ID mismatchEXTERNAL_ID in trust policy differs from the secretEnsure the EXTERNAL_ID value in the IAM trust policy matches the secret value in CloudQuery Platform exactly
InvalidIdentityTokenIRSA configuration issueVerify the CloudQuery Platform deployment has a valid OIDC provider. See AWS IRSA documentation.
No data after syncTables list is empty or incorrectCheck the tables field in the YAML configuration. Use ["*"] to sync everything, or specify individual table names from the AWS tables list.
Partial data (missing accounts)Member roles not deployedFor multi-account setups, verify the CloudFormation StackSet deployed roles to all target accounts. Run aws cloudformation describe-stacks to check.

Next steps

Last updated on