Using Shieldly with Terraform
Shieldly doesn't have a native Terraform provider — instead, extract the IAM policy JSON your plan is about to create or change and run it through the same @shieldly/cli used everywhere else. This works with any Terraform version and any backend.
IAM resources this covers
Terraform stores each of these resources' policy document as a JSON string in plan/state output — exactly the input analyze-iam expects:
| Resource type | Attribute | What it is |
|---|---|---|
| aws_iam_policy | policy | Standalone managed policy |
| aws_iam_role_policy | policy | Inline policy on a role |
| aws_iam_user_policy | policy | Inline policy on a user |
| aws_iam_group_policy | policy | Inline policy on a group |
Extract the policy JSON from a plan
terraform plan -out=tfplan
terraform show -json tfplan > plan.json
# Pull every IAM policy document about to be created/changed into its own file
jq -r '
.resource_changes[]
| select(.type == "aws_iam_policy" or .type == "aws_iam_role_policy"
or .type == "aws_iam_user_policy" or .type == "aws_iam_group_policy")
| .change.after.policy
' plan.json | nl -ba | while read -r n policy; do
echo "$policy" > "policy-$n.json"
doneRequires jq (preinstalled on GitHub Actions and GitLab CI runners).
Scan every extracted policy
for f in policy-*.json; do
npx @shieldly/cli analyze-iam "$f" || exit 1
doneanalyze-iam exits non-zero on its own when a scan finds a Critical or High severity issue — the loop above fails the pipeline on the first one, before terraform apply runs.
Full CI example (GitHub Actions)
- name: Terraform plan
run: |
terraform init
terraform plan -out=tfplan
terraform show -json tfplan > plan.json
- name: Extract + scan IAM policies
env:
SHIELDLY_API_KEY: ${{ secrets.SHIELDLY_API_KEY }}
run: |
jq -r '
.resource_changes[]
| select(.type == "aws_iam_policy" or .type == "aws_iam_role_policy"
or .type == "aws_iam_user_policy" or .type == "aws_iam_group_policy")
| .change.after.policy
' plan.json | nl -ba | while read -r n policy; do
echo "$policy" > "policy-$n.json"
npx @shieldly/cli analyze-iam "policy-$n.json" || exit 1
doneSame recipe works in GitLab CI or Jenkins — see Using Shieldly with GitLab CI and Using Shieldly with Jenkins for the pipeline syntax.
Privacy
Shieldly does not log your policy input. Cache keys are one-way SHA-256 hashes.