From feb92f777f299dae385f01595c1f7805f4d6ac85 Mon Sep 17 00:00:00 2001 From: Andrea Amorosi Date: Thu, 3 Sep 2026 14:53:30 +0200 Subject: [PATCH 1/3] chore(ci): mirror source layer visibility Carry commercial layer policies with partition artifacts and grant public access only when the source version has an unconditional public permission. Verify target visibility after publishing and fail safely on malformed policies or unexpected public placeholders. Fixes #8421 --- .../workflows/layers_partition_balance.yml | 73 +++++++++-- .github/workflows/layers_partitions.yml | 117 +++++++++++++++++- 2 files changed, 173 insertions(+), 17 deletions(-) diff --git a/.github/workflows/layers_partition_balance.yml b/.github/workflows/layers_partition_balance.yml index abd23c42f08..76cc6a581fd 100644 --- a/.github/workflows/layers_partition_balance.yml +++ b/.github/workflows/layers_partition_balance.yml @@ -154,6 +154,7 @@ jobs: for (( VERSION=START_VERSION; VERSION<=END_VERSION; VERSION++ )); do NAME="${LAYER}-${ARCHITECTURE}" METADATA="source/${VERSION}.json" + POLICY="source/${VERSION}.policy.json" ZIP="source/${VERSION}.zip" aws --region us-east-1 lambda get-layer-version-by-arn \ @@ -162,6 +163,17 @@ jobs: LOCATION=$(jq -r '.Content.Location' "$METADATA") curl --fail --location --retry 3 --retry-delay 2 --output "$ZIP" "$LOCATION" + if ! aws --region us-east-1 lambda get-layer-version-policy \ + --layer-name "arn:aws:lambda:us-east-1:017000801446:layer:${NAME}" \ + --version-number "$VERSION" > "$POLICY" 2> policy-error.txt; then + if grep -q ResourceNotFoundException policy-error.txt; then + echo '{"Policy":null}' > "$POLICY" + else + cat policy-error.txt + exit 1 + fi + fi + EXPECTED_SHA=$(jq -r '.Content.CodeSha256' "$METADATA") ACTUAL_SHA=$(openssl dgst -sha256 -binary "$ZIP" | openssl enc -base64) if [[ "$ACTUAL_SHA" != "$EXPECTED_SHA" ]]; then @@ -250,15 +262,26 @@ jobs: mkdir -p target has_public_permission() { - jq -e ' + local result + + if jq -e ' (.Policy | if type == "string" then fromjson else . end) | any(.Statement[]?; - .Sid == "PublicLayer" - and .Effect == "Allow" - and ((.Action | if type == "array" then . else [.] end) | index("lambda:GetLayerVersion") != null) + .Effect == "Allow" + and ((.Action // [] | if type == "array" then . else [.] end) | any(. == "*" or . == "lambda:*" or . == "lambda:GetLayerVersion")) and (((.Principal | if type == "object" then .AWS // "" else . end) | if type == "array" then . else [.] end) | index("*") != null) + and ((.Condition // {}) | length == 0) ) - ' "$1" > /dev/null + ' "$1" > /dev/null; then + return 0 + else + result=$? + if (( result > 1 )); then + echo "Unable to evaluate layer policy $1 (jq exit ${result})" + exit 1 + fi + return 1 + fi } if ! aws --region "$REGION" lambda list-layer-versions \ @@ -276,6 +299,7 @@ jobs: for (( VERSION=START_VERSION; VERSION<=END_VERSION; VERSION++ )); do METADATA="source/${VERSION}.json" + SOURCE_POLICY="source/${VERSION}.policy.json" ZIP="source/${VERSION}.zip" TARGET_METADATA="target/${VERSION}.json" TARGET_ARN="arn:${PARTITION}:lambda:${REGION}:${AWS_ACCOUNT}:layer:${NAME}:${VERSION}" @@ -313,6 +337,12 @@ jobs: exit 1 fi + SOURCE_IS_PUBLIC=false + if has_public_permission "$SOURCE_POLICY"; then + SOURCE_IS_PUBLIC=true + fi + echo "Commercial source ${NAME}:${VERSION} public: ${SOURCE_IS_PUBLIC}" + if [[ "$VERSION_EXISTS" == "true" ]]; then echo "${NAME}:${VERSION} already exists in ${REGION} with the expected SHA" else @@ -323,13 +353,21 @@ jobs: fi fi + if [[ "$SOURCE_IS_PUBLIC" == "false" ]] && [[ "$HAS_PUBLIC_PERMISSION" == "true" ]]; then + echo "${NAME}:${VERSION} in ${REGION} is public but its commercial source is private" + exit 1 + fi + if [[ "$DRY_RUN" != "false" ]]; then if [[ "$VERSION_EXISTS" == "false" ]]; then echo "Would publish ${NAME}:${VERSION} to ${REGION}" CURRENT_POSITION=$VERSION - elif [[ "$HAS_PUBLIC_PERMISSION" == "false" ]]; then + elif [[ "$SOURCE_IS_PUBLIC" == "true" ]] && [[ "$HAS_PUBLIC_PERMISSION" == "false" ]]; then echo "Would add public permission to ${NAME}:${VERSION} in ${REGION}" fi + if [[ "$SOURCE_IS_PUBLIC" == "false" ]]; then + echo "Would keep ${NAME}:${VERSION} private in ${REGION}" + fi continue fi @@ -352,7 +390,7 @@ jobs: CURRENT_POSITION=$PUBLISHED_VERSION fi - if [[ "$HAS_PUBLIC_PERMISSION" == "false" ]]; then + if [[ "$SOURCE_IS_PUBLIC" == "true" ]] && [[ "$HAS_PUBLIC_PERMISSION" == "false" ]]; then if ! aws --region "$REGION" lambda add-layer-version-permission \ --layer-name "$NAME" \ --statement-id PublicLayer \ @@ -375,11 +413,24 @@ jobs: exit 1 fi - aws --region "$REGION" lambda get-layer-version-policy \ + if ! aws --region "$REGION" lambda get-layer-version-policy \ --layer-name "$NAME" \ - --version-number "$VERSION" > scratch/policy.json - if ! has_public_permission scratch/policy.json; then - echo "${NAME}:${VERSION} in ${REGION} is missing the expected public permission" + --version-number "$VERSION" > scratch/policy.json 2> scratch/policy-error.txt; then + if grep -q ResourceNotFoundException scratch/policy-error.txt; then + echo '{"Policy":null}' > scratch/policy.json + else + cat scratch/policy-error.txt + exit 1 + fi + fi + + TARGET_IS_PUBLIC=false + if has_public_permission scratch/policy.json; then + TARGET_IS_PUBLIC=true + fi + + if [[ "$TARGET_IS_PUBLIC" != "$SOURCE_IS_PUBLIC" ]]; then + echo "${NAME}:${VERSION} in ${REGION} does not match its commercial source visibility" exit 1 fi done diff --git a/.github/workflows/layers_partitions.yml b/.github/workflows/layers_partitions.yml index 65b80f30748..089466a1392 100644 --- a/.github/workflows/layers_partitions.yml +++ b/.github/workflows/layers_partitions.yml @@ -98,6 +98,21 @@ jobs: run: | aws --region us-east-1 lambda get-layer-version-by-arn --arn arn:aws:lambda:us-east-1:017000801446:layer:${{ matrix.layer }}-${{ matrix.arch }}:${{ inputs.version }} --query 'Content.Location' | xargs curl -L -o ${{ matrix.layer }}-${{ matrix.arch }}.zip aws --region us-east-1 lambda get-layer-version-by-arn --arn arn:aws:lambda:us-east-1:017000801446:layer:${{ matrix.layer }}-${{ matrix.arch }}:${{ inputs.version }} > ${{ matrix.layer }}-${{ matrix.arch }}.json + - name: Grab Policy + env: + LAYER_NAME: ${{ matrix.layer }}-${{ matrix.arch }} + VERSION: ${{ inputs.version }} + run: | + if ! aws --region us-east-1 lambda get-layer-version-policy \ + --layer-name "arn:aws:lambda:us-east-1:017000801446:layer:${LAYER_NAME}" \ + --version-number "$VERSION" > "${LAYER_NAME}.policy.json" 2> policy-error.txt; then + if grep -q ResourceNotFoundException policy-error.txt; then + echo '{"Policy":null}' > "${LAYER_NAME}.policy.json" + else + cat policy-error.txt + exit 1 + fi + fi - name: Store Zip uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 with: @@ -112,6 +127,13 @@ jobs: path: ${{ matrix.layer }}-${{ matrix.arch }}.json retention-days: 1 if-no-files-found: error + - name: Store Policy + uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 + with: + name: ${{ matrix.layer }}-${{ matrix.arch }}.policy.json + path: ${{ matrix.layer }}-${{ matrix.arch }}.policy.json + retention-days: 1 + if-no-files-found: error copy: name: Copy @@ -146,10 +168,35 @@ jobs: uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8.0.1 with: name: ${{ matrix.layer }}-${{ matrix.arch }}.json + - name: Download Policy + uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8.0.1 + with: + name: ${{ matrix.layer }}-${{ matrix.arch }}.policy.json - name: Verify Layer Signature run: | SHA=$(jq -r '.Content.CodeSha256' '${{ matrix.layer }}-${{ matrix.arch }}.json') test "$(openssl dgst -sha256 -binary ${{ matrix.layer }}-${{ matrix.arch }}.zip | openssl enc -base64)" == "$SHA" && echo "SHA OK: ${SHA}" || exit 1 + - id: source_policy + name: Source Layer Visibility + run: | + if jq -e ' + (.Policy | if type == "string" then fromjson else . end) + | any(.Statement[]?; + .Effect == "Allow" + and ((.Action // [] | if type == "array" then . else [.] end) | any(. == "*" or . == "lambda:*" or . == "lambda:GetLayerVersion")) + and (((.Principal | if type == "object" then .AWS // "" else . end) | if type == "array" then . else [.] end) | index("*") != null) + and ((.Condition // {}) | length == 0) + ) + ' '${{ matrix.layer }}-${{ matrix.arch }}.policy.json' > /dev/null; then + echo 'public=true' >> "$GITHUB_OUTPUT" + else + RESULT=$? + if (( RESULT > 1 )); then + echo "Unable to evaluate source layer policy (jq exit ${RESULT})" + exit 1 + fi + echo 'public=false' >> "$GITHUB_OUTPUT" + fi - id: transform run: | echo 'CONVERTED_REGION=${{ matrix.region }}' | tr 'a-z\-' 'A-Z_' >> "$GITHUB_OUTPUT" @@ -160,8 +207,28 @@ jobs: aws-region: ${{ matrix.region}} mask-aws-account-id: true audience: ${{ needs.setup.outputs.aud }} + - name: Validate target account + env: + AWS_ACCOUNT: ${{ secrets[format('AWS_ACCOUNT_{0}', steps.transform.outputs.CONVERTED_REGION)] }} + PARTITION: ${{ needs.setup.outputs.partition }} + REGION: ${{ matrix.region }} + run: | + if [[ ! "$AWS_ACCOUNT" =~ ^[0-9]{12}$ ]]; then + echo "AWS account secret for ${REGION} is missing or invalid" + exit 1 + fi + + CALLER_ACCOUNT=$(aws --region "$REGION" sts get-caller-identity --query Account --output text) + CALLER_ARN=$(aws --region "$REGION" sts get-caller-identity --query Arn --output text) + + if [[ "$CALLER_ACCOUNT" != "$AWS_ACCOUNT" ]] || [[ "$CALLER_ARN" != "arn:${PARTITION}:"* ]]; then + echo "Assumed role does not match the expected account and partition for ${REGION}" + exit 1 + fi - name: Create Layer id: create-layer + env: + SOURCE_IS_PUBLIC: ${{ steps.source_policy.outputs.public }} run: | jq '{"LayerName": "${{ matrix.layer }}-${{ matrix.arch }}", "Description": .Description, "CompatibleRuntimes": .CompatibleRuntimes, "CompatibleArchitectures": .CompatibleArchitectures, "LicenseInfo": .LicenseInfo} | with_entries(select(.value != null))' '${{ matrix.layer }}-${{ matrix.arch }}.json' > input.json @@ -173,15 +240,18 @@ jobs: echo "LAYER_VERSION=$LAYER_VERSION" >> "$GITHUB_OUTPUT" - aws --region ${{ matrix.region}} lambda add-layer-version-permission \ - --layer-name ${{ matrix.layer }}-${{ matrix.arch }} \ - --statement-id 'PublicLayer' \ - --action lambda:GetLayerVersion \ - --principal '*' \ - --version-number "$LAYER_VERSION" + if [[ "$SOURCE_IS_PUBLIC" == "true" ]]; then + aws --region ${{ matrix.region}} lambda add-layer-version-permission \ + --layer-name ${{ matrix.layer }}-${{ matrix.arch }} \ + --statement-id 'PublicLayer' \ + --action lambda:GetLayerVersion \ + --principal '*' \ + --version-number "$LAYER_VERSION" + fi - name: Verify Layer env: LAYER_VERSION: ${{ steps.create-layer.outputs.LAYER_VERSION }} + SOURCE_IS_PUBLIC: ${{ steps.source_policy.outputs.public }} run: | export layer_output='${{ matrix.layer }}-${{ matrix.arch }}-${{matrix.region}}.json' aws --region ${{ matrix.region}} lambda get-layer-version-by-arn --arn 'arn:${{ needs.setup.outputs.partition }}:lambda:${{ matrix.region}}:${{ secrets[format('AWS_ACCOUNT_{0}', steps.transform.outputs.CONVERTED_REGION)] }}:layer:${{ matrix.layer }}-${{ matrix.arch }}:${{ env.LAYER_VERSION }}' > $layer_output @@ -190,6 +260,41 @@ jobs: test "$REMOTE_SHA" == "$LOCAL_SHA" && echo "SHA OK: ${LOCAL_SHA}" || exit 1 jq -s -r '["Layer Arn", "Runtimes", "Version", "Description", "SHA256"], ([.[0], .[1]] | .[] | [.LayerArn, (.CompatibleRuntimes | join("/")), .Version, .Description, .Content.CodeSha256]) |@tsv' '${{ matrix.layer }}-${{ matrix.arch }}.json' $layer_output | column -t -s $'\t' + if ! aws --region ${{ matrix.region}} lambda get-layer-version-policy \ + --layer-name '${{ matrix.layer }}-${{ matrix.arch }}' \ + --version-number "$LAYER_VERSION" > target-policy.json 2> policy-error.txt; then + if grep -q ResourceNotFoundException policy-error.txt; then + echo '{"Policy":null}' > target-policy.json + else + cat policy-error.txt + exit 1 + fi + fi + + TARGET_IS_PUBLIC=false + if jq -e ' + (.Policy | if type == "string" then fromjson else . end) + | any(.Statement[]?; + .Effect == "Allow" + and ((.Action // [] | if type == "array" then . else [.] end) | any(. == "*" or . == "lambda:*" or . == "lambda:GetLayerVersion")) + and (((.Principal | if type == "object" then .AWS // "" else . end) | if type == "array" then . else [.] end) | index("*") != null) + and ((.Condition // {}) | length == 0) + ) + ' target-policy.json > /dev/null; then + TARGET_IS_PUBLIC=true + else + RESULT=$? + if (( RESULT > 1 )); then + echo "Unable to evaluate target layer policy (jq exit ${RESULT})" + exit 1 + fi + fi + + if [[ "$TARGET_IS_PUBLIC" != "$SOURCE_IS_PUBLIC" ]]; then + echo "Published layer visibility does not match its commercial source" + exit 1 + fi + - name: Store Metadata - ${{ matrix.region }} uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 with: From 604889bc8bc5de22082ee9d401864f12f26594bb Mon Sep 17 00:00:00 2001 From: Andrea Amorosi Date: Thu, 3 Sep 2026 15:02:23 +0200 Subject: [PATCH 2/3] chore(ci): enforce partition layer version parity Log commercial source visibility and fail when Lambda assigns a partition version that differs from the requested commercial version. This prevents applying version-indexed permissions to a misaligned target. --- .github/workflows/layers_partitions.yml | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/.github/workflows/layers_partitions.yml b/.github/workflows/layers_partitions.yml index 089466a1392..55492733625 100644 --- a/.github/workflows/layers_partitions.yml +++ b/.github/workflows/layers_partitions.yml @@ -189,6 +189,7 @@ jobs: ) ' '${{ matrix.layer }}-${{ matrix.arch }}.policy.json' > /dev/null; then echo 'public=true' >> "$GITHUB_OUTPUT" + echo 'Commercial source layer is public' else RESULT=$? if (( RESULT > 1 )); then @@ -196,6 +197,7 @@ jobs: exit 1 fi echo 'public=false' >> "$GITHUB_OUTPUT" + echo 'Commercial source layer is private' fi - id: transform run: | @@ -229,6 +231,7 @@ jobs: id: create-layer env: SOURCE_IS_PUBLIC: ${{ steps.source_policy.outputs.public }} + VERSION: ${{ inputs.version }} run: | jq '{"LayerName": "${{ matrix.layer }}-${{ matrix.arch }}", "Description": .Description, "CompatibleRuntimes": .CompatibleRuntimes, "CompatibleArchitectures": .CompatibleArchitectures, "LicenseInfo": .LicenseInfo} | with_entries(select(.value != null))' '${{ matrix.layer }}-${{ matrix.arch }}.json' > input.json @@ -238,6 +241,11 @@ jobs: --query 'Version' \ --output text) + if (( LAYER_VERSION != VERSION )); then + echo "Expected to publish as version ${VERSION}, received ${LAYER_VERSION}" + exit 1 + fi + echo "LAYER_VERSION=$LAYER_VERSION" >> "$GITHUB_OUTPUT" if [[ "$SOURCE_IS_PUBLIC" == "true" ]]; then From c83cb8eb26dd6a7c029d0f4bc9ef5c39658f4f5c Mon Sep 17 00:00:00 2001 From: Andrea Amorosi Date: Fri, 4 Sep 2026 13:11:17 +0200 Subject: [PATCH 3/3] ref(ci): centralize layer policy classification Move partition layer visibility detection into one fail-safe script shared by the balancer and deployment workflows. Also query STS account and ARN in one request when validating target credentials. --- .github/scripts/layer_policy_visibility.sh | 24 +++++++++ .../workflows/layers_partition_balance.yml | 52 +++++++------------ .github/workflows/layers_partitions.yml | 39 +++----------- 3 files changed, 51 insertions(+), 64 deletions(-) create mode 100644 .github/scripts/layer_policy_visibility.sh diff --git a/.github/scripts/layer_policy_visibility.sh b/.github/scripts/layer_policy_visibility.sh new file mode 100644 index 00000000000..f83bcf2f302 --- /dev/null +++ b/.github/scripts/layer_policy_visibility.sh @@ -0,0 +1,24 @@ +#!/usr/bin/env bash + +set -euo pipefail + +POLICY_FILE=${1:?Policy file is required} + +if jq -e ' + (.Policy | if type == "string" then fromjson else . end) + | any(.Statement[]?; + .Effect == "Allow" + and ((.Action // [] | if type == "array" then . else [.] end) | any(. == "*" or . == "lambda:*" or . == "lambda:GetLayerVersion")) + and (((.Principal | if type == "object" then .AWS // "" else . end) | if type == "array" then . else [.] end) | index("*") != null) + and ((.Condition // {}) | length == 0) + ) +' "$POLICY_FILE" > /dev/null; then + echo public +else + RESULT=$? + if (( RESULT > 1 )); then + echo "Unable to evaluate layer policy ${POLICY_FILE} (jq exit ${RESULT})" >&2 + exit "$RESULT" + fi + echo private +fi diff --git a/.github/workflows/layers_partition_balance.yml b/.github/workflows/layers_partition_balance.yml index 76cc6a581fd..298152f48e8 100644 --- a/.github/workflows/layers_partition_balance.yml +++ b/.github/workflows/layers_partition_balance.yml @@ -209,6 +209,8 @@ jobs: region: ${{ fromJson(needs.setup.outputs.regions) }} architecture: ${{ fromJson(needs.setup.outputs.architectures) }} steps: + - name: Checkout repository + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 - name: Download commercial layer versions uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8.0.1 with: @@ -239,8 +241,8 @@ jobs: exit 1 fi - CALLER_ACCOUNT=$(aws --region "$REGION" sts get-caller-identity --query Account --output text) - CALLER_ARN=$(aws --region "$REGION" sts get-caller-identity --query Arn --output text) + IDENTITY=$(aws --region "$REGION" sts get-caller-identity --query '[Account, Arn]' --output text) + read -r CALLER_ACCOUNT CALLER_ARN <<< "$IDENTITY" if [[ "$CALLER_ACCOUNT" != "$AWS_ACCOUNT" ]] || [[ "$CALLER_ARN" != "arn:${PARTITION}:"* ]]; then echo "Assumed role does not match the expected account and partition for ${REGION}" @@ -261,29 +263,6 @@ jobs: mkdir -p scratch mkdir -p target - has_public_permission() { - local result - - if jq -e ' - (.Policy | if type == "string" then fromjson else . end) - | any(.Statement[]?; - .Effect == "Allow" - and ((.Action // [] | if type == "array" then . else [.] end) | any(. == "*" or . == "lambda:*" or . == "lambda:GetLayerVersion")) - and (((.Principal | if type == "object" then .AWS // "" else . end) | if type == "array" then . else [.] end) | index("*") != null) - and ((.Condition // {}) | length == 0) - ) - ' "$1" > /dev/null; then - return 0 - else - result=$? - if (( result > 1 )); then - echo "Unable to evaluate layer policy $1 (jq exit ${result})" - exit 1 - fi - return 1 - fi - } - if ! aws --region "$REGION" lambda list-layer-versions \ --layer-name "$NAME" \ --output json > scratch/versions.json 2> scratch/list-error.txt; then @@ -326,19 +305,25 @@ jobs: fi HAS_PUBLIC_PERMISSION=false - if aws --region "$REGION" lambda get-layer-version-policy \ + if ! aws --region "$REGION" lambda get-layer-version-policy \ --layer-name "$NAME" \ --version-number "$VERSION" > scratch/policy.json 2> scratch/policy-error.txt; then - if has_public_permission scratch/policy.json; then - HAS_PUBLIC_PERMISSION=true + if grep -q ResourceNotFoundException scratch/policy-error.txt; then + echo '{"Policy":null}' > scratch/policy.json + else + cat scratch/policy-error.txt + exit 1 fi - elif ! grep -q ResourceNotFoundException scratch/policy-error.txt; then - cat scratch/policy-error.txt - exit 1 + fi + + TARGET_VISIBILITY=$(bash .github/scripts/layer_policy_visibility.sh scratch/policy.json) + if [[ "$TARGET_VISIBILITY" == "public" ]]; then + HAS_PUBLIC_PERMISSION=true fi SOURCE_IS_PUBLIC=false - if has_public_permission "$SOURCE_POLICY"; then + SOURCE_VISIBILITY=$(bash .github/scripts/layer_policy_visibility.sh "$SOURCE_POLICY") + if [[ "$SOURCE_VISIBILITY" == "public" ]]; then SOURCE_IS_PUBLIC=true fi echo "Commercial source ${NAME}:${VERSION} public: ${SOURCE_IS_PUBLIC}" @@ -425,7 +410,8 @@ jobs: fi TARGET_IS_PUBLIC=false - if has_public_permission scratch/policy.json; then + TARGET_VISIBILITY=$(bash .github/scripts/layer_policy_visibility.sh scratch/policy.json) + if [[ "$TARGET_VISIBILITY" == "public" ]]; then TARGET_IS_PUBLIC=true fi diff --git a/.github/workflows/layers_partitions.yml b/.github/workflows/layers_partitions.yml index 55492733625..21c8c4b73f4 100644 --- a/.github/workflows/layers_partitions.yml +++ b/.github/workflows/layers_partitions.yml @@ -160,6 +160,8 @@ jobs: - arm64 - x86_64 steps: + - name: Checkout repository + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 - name: Download Zip uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8.0.1 with: @@ -179,23 +181,11 @@ jobs: - id: source_policy name: Source Layer Visibility run: | - if jq -e ' - (.Policy | if type == "string" then fromjson else . end) - | any(.Statement[]?; - .Effect == "Allow" - and ((.Action // [] | if type == "array" then . else [.] end) | any(. == "*" or . == "lambda:*" or . == "lambda:GetLayerVersion")) - and (((.Principal | if type == "object" then .AWS // "" else . end) | if type == "array" then . else [.] end) | index("*") != null) - and ((.Condition // {}) | length == 0) - ) - ' '${{ matrix.layer }}-${{ matrix.arch }}.policy.json' > /dev/null; then + VISIBILITY=$(bash .github/scripts/layer_policy_visibility.sh '${{ matrix.layer }}-${{ matrix.arch }}.policy.json') + if [[ "$VISIBILITY" == "public" ]]; then echo 'public=true' >> "$GITHUB_OUTPUT" echo 'Commercial source layer is public' else - RESULT=$? - if (( RESULT > 1 )); then - echo "Unable to evaluate source layer policy (jq exit ${RESULT})" - exit 1 - fi echo 'public=false' >> "$GITHUB_OUTPUT" echo 'Commercial source layer is private' fi @@ -220,8 +210,8 @@ jobs: exit 1 fi - CALLER_ACCOUNT=$(aws --region "$REGION" sts get-caller-identity --query Account --output text) - CALLER_ARN=$(aws --region "$REGION" sts get-caller-identity --query Arn --output text) + IDENTITY=$(aws --region "$REGION" sts get-caller-identity --query '[Account, Arn]' --output text) + read -r CALLER_ACCOUNT CALLER_ARN <<< "$IDENTITY" if [[ "$CALLER_ACCOUNT" != "$AWS_ACCOUNT" ]] || [[ "$CALLER_ARN" != "arn:${PARTITION}:"* ]]; then echo "Assumed role does not match the expected account and partition for ${REGION}" @@ -280,22 +270,9 @@ jobs: fi TARGET_IS_PUBLIC=false - if jq -e ' - (.Policy | if type == "string" then fromjson else . end) - | any(.Statement[]?; - .Effect == "Allow" - and ((.Action // [] | if type == "array" then . else [.] end) | any(. == "*" or . == "lambda:*" or . == "lambda:GetLayerVersion")) - and (((.Principal | if type == "object" then .AWS // "" else . end) | if type == "array" then . else [.] end) | index("*") != null) - and ((.Condition // {}) | length == 0) - ) - ' target-policy.json > /dev/null; then + TARGET_VISIBILITY=$(bash .github/scripts/layer_policy_visibility.sh target-policy.json) + if [[ "$TARGET_VISIBILITY" == "public" ]]; then TARGET_IS_PUBLIC=true - else - RESULT=$? - if (( RESULT > 1 )); then - echo "Unable to evaluate target layer policy (jq exit ${RESULT})" - exit 1 - fi fi if [[ "$TARGET_IS_PUBLIC" != "$SOURCE_IS_PUBLIC" ]]; then