AWS Security Hub · Lambda
Lambda.1: A Lambda resource policy allows public invocation
Written and reviewed by Emnode · Last reviewed
What does AWS Security Hub Lambda.1 check?
Lambda.1 fails when a Lambda function's resource-based policy allows public access: a Principal "*" permission to invoke the function without a restricting condition.
Why does Lambda.1 matter?
A publicly invocable function lets anyone on the internet trigger your code, potentially incurring cost, abusing downstream resources the function can reach, or probing for logic flaws. Functions should be invoked only by the specific services, accounts, or API Gateways you intend.
How do I fix Lambda.1?
- Review the function policy (get-policy) and remove statements granting invoke to Principal "*".
- Re-add permissions scoped to the exact source: a specific service principal plus SourceArn/SourceAccount conditions.
- For HTTP access, front the function with API Gateway or a Function URL that enforces IAM/auth.
Remediation script · bash
# Close the highest-blast-radius mode first: confirm and remove the root access key.
# (Deletion is done as the root user via the console; an IAM identity cannot do it.)
aws iam get-account-summary --query 'SummaryMap.AccountAccessKeysPresent'
# Expect 0 after deletion.
# Close a public EKS endpoint (only after confirming a private path exists).
aws eks update-cluster-config --name svc-orders \
--resources-vpc-config endpointPublicAccess=false,endpointPrivateAccess=true
# Disable legacy ACLs on a bucket and let policy govern access.
aws s3api put-bucket-ownership-controls --bucket my-legacy-assets \
--ownership-controls 'Rules=[{ObjectOwnership=BucketOwnerEnforced}]'
# Migrate a Transfer Family server off plain FTP to SFTP only.
aws transfer update-server --server-id s-0a1b2c3d4e5f --protocols SFTP Full walkthrough (console steps, edge cases and verification) in the lesson Disable insecure access modes and protocols.
Is Lambda.1 a false positive?
A genuinely public endpoint (a Function URL with `AuthType: NONE` fronting a webhook receiver, a public form handler, or an AWS Marketplace/partner integration that is designed to be invoked anonymously) needs `Principal "*"`, so the control fails by design even though the function is meant to be open. The control also can't credit you for a restriction it can't parse: it ignores any condition that uses wildcards or policy variables, so a policy scoped only by something like `aws:PrincipalOrgID` may still read as public to it. Where the open access is the intended state, suppress the finding with a documented exception (record the auth/throttling layer that protects it) rather than tightening a principal the design requires; where a fixed-value condition would express your real intent, rewrite the condition to fixed values so the check can pass honestly.