Skip to content

Commit cc01714

Browse files
Merge origin/main preferring incoming changes
Co-authored-by: paolosalvatori <1658419+paolosalvatori@users.noreply.github.com>
2 parents ceff059 + e16f867 commit cc01714

349 files changed

Lines changed: 83231 additions & 2731 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.github/CODEOWNERS

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
* @localstack/smurf

.github/PULL_REQUEST_TEMPLATE.md

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
<!--
2+
Please refer to the contribution guidelines before raising a PR.
3+
https://github.com/localstack/localstack/blob/main/docs/CONTRIBUTING.md
4+
-->
5+
6+
## Motivation
7+
8+
<!--
9+
Elaborate the background and intent for raising this PR.
10+
-->
11+
12+
## Changes
13+
14+
<!--
15+
Summarise the changes proposed in the PR.
16+
-->
17+
18+
## Tests
19+
20+
<!--
21+
Optional: How are the proposed changes tested?
22+
-->
23+
24+
## Related
25+
26+
<!--
27+
Optional: Links to related issues and references (e.g., Linear IDs).
28+
-->

.github/scripts/build-matrix.sh

Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
#!/usr/bin/env bash
2+
set -euo pipefail
3+
4+
# Builds a dynamic GitHub Actions matrix for run-samples.yml.
5+
# Usage: build-matrix.sh <run_mode> [base_sha]
6+
7+
# "all" runs every test; "changed" only runs tests whose watch_folders have modified files
8+
RUN_MODE="${1:-all}"
9+
BASE_SHA="${2:-}"
10+
11+
# Get JSON metadata for all tests from run-samples.sh --list
12+
TEST_META=$(./run-samples.sh --list)
13+
TOTAL=$(echo "$TEST_META" | jq length)
14+
echo "Run mode: $RUN_MODE | Total tests: $TOTAL"
15+
16+
# Changes to these files affect all tests, so any modification triggers a full run
17+
INFRA_FILES="run-samples.sh Makefile .github/workflows/run-samples.yml .github/scripts/build-matrix.sh pyproject.toml requirements-dev.txt requirements-runtime.txt"
18+
19+
if [[ "$RUN_MODE" == "changed" && -n "$BASE_SHA" ]]; then
20+
# Get list of files changed between base branch and current HEAD
21+
CHANGED=$(git diff --name-only "$BASE_SHA"..HEAD || true)
22+
echo "Changed files:"
23+
echo "$CHANGED"
24+
25+
# Safety net: if any infrastructure file changed, run all tests
26+
RUN_ALL=false
27+
for f in $INFRA_FILES; do
28+
if echo "$CHANGED" | grep -qF "$f"; then
29+
echo "Infra changed: $f -> running all"
30+
RUN_ALL=true && break
31+
fi
32+
done
33+
34+
if [[ "$RUN_ALL" == "true" ]]; then
35+
INDICES=$(seq 0 $((TOTAL-1)))
36+
else
37+
# Match changed files against each test's watch_folders using prefix matching
38+
INDICES=""
39+
for (( i=0; i<TOTAL; i++ )); do
40+
mapfile -t folders < <(echo "$TEST_META" | jq -r ".[$i].watch_folders[]")
41+
for wf in "${folders[@]}"; do
42+
if echo "$CHANGED" | grep -q "^${wf}/"; then
43+
INDICES+=" $i" && break
44+
fi
45+
done
46+
done
47+
INDICES=$(echo "$INDICES" | xargs)
48+
fi
49+
else
50+
# "all" mode: select every test
51+
INDICES=$(seq 0 $((TOTAL-1)))
52+
fi
53+
54+
# Output the matrix JSON for GitHub Actions
55+
if [[ -z "${INDICES:-}" ]]; then
56+
echo "No tests to run."
57+
echo "has_tests=false" >> "$GITHUB_OUTPUT"
58+
echo 'matrix={"include":[]}' >> "$GITHUB_OUTPUT"
59+
else
60+
echo "has_tests=true" >> "$GITHUB_OUTPUT"
61+
# Convert space-separated indices to JSON array, then build the matrix object
62+
IDX_JSON=$(echo "$INDICES" | tr ' ' '\n' | jq -R 'tonumber' | jq -s '.')
63+
MATRIX=$(echo "$TEST_META" | jq -c --argjson idx "$IDX_JSON" \
64+
'{include: [$idx[] as $i | .[$i] | {shard, splits, name}]}')
65+
echo "matrix=$MATRIX" >> "$GITHUB_OUTPUT"
66+
echo "Matrix:" && echo "$MATRIX" | jq .
67+
fi

.github/workflows/run-samples.yml

Lines changed: 87 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,7 @@
11
name: Samples CI
22

3-
# Theory of Operation:
4-
# This workflow automates the testing of Azure sample applications against the LocalStack Azure emulator.
5-
# It follows the best practices from the localstack-pro repository:
6-
# 1. Parallel Testing: Splits the sample suite into shards to reduce execution time.
7-
# 2. Standardized Tooling: Uses a Makefile for environment setup and test orchestration.
8-
# 3. Cloud Emulation: Configures the Azure CLI to target the LocalStack emulator.
9-
# 4. IaC Coverage: Tests bash scripts, Terraform deployments, and Bicep deployments.
3+
# Tests Azure samples against the LocalStack emulator.
4+
# Each test runs in its own job. Set DEFAULT_RUN_MODE to 'changed' to only run affected tests.
105

116
concurrency:
127
group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }}
@@ -16,18 +11,67 @@ on:
1611
pull_request:
1712
branches: [ main ]
1813
workflow_dispatch:
14+
inputs:
15+
run_mode:
16+
description: "Test mode: 'all' runs every test, 'changed' runs only tests with modified files"
17+
required: false
18+
type: choice
19+
options:
20+
- all
21+
- changed
22+
default: changed
23+
24+
# Default run mode for pull_request events (change to 'changed' to only run affected tests)
25+
env:
26+
DEFAULT_RUN_MODE: changed
1927

2028
jobs:
29+
# Lightweight job that builds the dynamic test matrix for the main test jobs
30+
setup:
31+
name: "Build Test Matrix"
32+
runs-on: ubuntu-latest
33+
outputs:
34+
matrix: ${{ steps.build-matrix.outputs.matrix }}
35+
has_tests: ${{ steps.build-matrix.outputs.has_tests }}
36+
steps:
37+
- name: Checkout repo
38+
uses: actions/checkout@v4
39+
with:
40+
fetch-depth: 0 # Full history needed for git diff in "changed" mode
41+
42+
- name: Build dynamic matrix
43+
id: build-matrix
44+
run: |
45+
# Pick run mode: manual dispatch uses the dropdown, PRs use the env default
46+
if [[ "${{ github.event_name }}" == "workflow_dispatch" ]]; then
47+
RUN_MODE="${{ github.event.inputs.run_mode }}"
48+
else
49+
RUN_MODE="${{ env.DEFAULT_RUN_MODE }}"
50+
fi
51+
52+
# In "changed" mode, determine the base commit to diff against
53+
BASE_SHA=""
54+
if [[ "$RUN_MODE" == "changed" ]]; then
55+
if [[ "${{ github.event_name }}" == "pull_request" ]]; then
56+
BASE_SHA="${{ github.event.pull_request.base.sha }}"
57+
else
58+
BASE_SHA=$(git rev-parse origin/main 2>/dev/null || git rev-parse HEAD~1)
59+
fi
60+
fi
61+
62+
.github/scripts/build-matrix.sh "$RUN_MODE" "$BASE_SHA"
63+
64+
# Each test runs in its own job — one matrix entry per test from the setup job
2165
scripts:
22-
name: "Run Test Scripts (amd64) — Part ${{ matrix.shard }} of ${{ matrix.splits }}"
66+
name: "Test: ${{ matrix.name }}"
67+
needs: setup
68+
if: needs.setup.outputs.has_tests == 'true' # Skip entirely when no tests match
2369
environment: AZURE
2470
strategy:
2571
fail-fast: false
26-
matrix:
27-
shard: [1, 2, 3, 4]
28-
splits: [4]
29-
runs-on: github-ubuntu2204-amd64-4
30-
72+
matrix: ${{ fromJSON(needs.setup.outputs.matrix) }}
73+
runs-on: ubuntu-22.04
74+
3175
env:
3276
IMAGE_NAME: localstack/localstack-azure-alpha
3377
DEFAULT_TAG: latest
@@ -48,7 +92,12 @@ jobs:
4892
- name: Set up .NET
4993
uses: actions/setup-dotnet@v4
5094
with:
51-
dotnet-version: '9.0'
95+
dotnet-version: '10.0'
96+
97+
- uses: actions/setup-java@v5
98+
with:
99+
distribution: 'temurin'
100+
java-version: '25'
52101

53102
- name: Install System Dependencies
54103
# Essential tools for script execution, app packaging, and database connectivity.
@@ -67,7 +116,7 @@ jobs:
67116
terraform_wrapper: false
68117

69118
- name: Install test dependencies
70-
# Mirroring the localstack-pro approach: install all Python dependencies
119+
# Mirroring the localstack-pro approach: install all Python dependencies
71120
# (including the localstack CLI) into a virtual environment to avoid system-level conflicts.
72121
run: make install
73122

@@ -80,24 +129,23 @@ jobs:
80129
password: ${{ secrets.DOCKERHUB_PULL_TOKEN }}
81130

82131
- name: Free up disk space
83-
# Azure emulator images are large. Pruning unused Docker objects ensures enough
132+
# Azure emulator images are large. Pruning unused Docker objects ensures enough
84133
# disk space is available on the GitHub runner for image pulls and sidecar containers.
85134
run: |
86135
docker system prune -af --volumes
87136
docker builder prune -af
88137
89138
- name: Pull LocalStack Azure Image
90-
# Explicitly pull the image before starting. This mirrors the "Build Docker Image"
139+
# Explicitly pull the image before starting. This mirrors the "Build Docker Image"
91140
# step in localstack-pro and ensures the pull logic is separated from the start logic.
92141
run: docker pull ${{ env.IMAGE_NAME }}:${{ env.DEFAULT_TAG }}
93142

94143
- name: Start LocalStack
95144
# Run the emulator in detached mode using the virtual environment.
96-
# We use 'python -m localstack.cli.main' to ensure the correct CLI version from the venv is used.
97145
run: |
98146
source .venv/bin/activate
99-
python -m localstack.cli.main start -d
100-
python -m localstack.cli.main wait -t 120
147+
python -m localstack_cli.cli.main start -d
148+
python -m localstack_cli.cli.main wait -t 120
101149
env:
102150
IMAGE_NAME: ${{ env.IMAGE_NAME }}:${{ env.DEFAULT_TAG }}
103151
LOCALSTACK_AUTH_TOKEN: ${{ secrets.TEST_LOCALSTACK_AUTH_TOKEN }}
@@ -109,21 +157,35 @@ jobs:
109157

110158
- name: Install Azure Functions Core Tools
111159
# Required for publishing function app samples to the emulator.
112-
run: npm install -g azure-functions-core-tools@4 --unsafe-perm true
160+
run: |
161+
MAX_RETRIES=3
162+
DELAY=15
163+
for i in $(seq 1 $MAX_RETRIES); do
164+
echo "Attempt $i/$MAX_RETRIES..."
165+
npm install -g azure-functions-core-tools@4 --unsafe-perm true && break
166+
if [ "$i" -eq "$MAX_RETRIES" ]; then
167+
echo "All $MAX_RETRIES attempts failed"
168+
exit 1
169+
fi
170+
echo "Retrying in ${DELAY}s..."
171+
sleep $DELAY
172+
DELAY=$((DELAY * 2))
173+
done
113174
114175
- name: Install MSSQL ODBC and Tools
115-
# Required for the 'web-app-sql-database' sample which uses 'sqlcmd' to
176+
# Required for the 'web-app-sql-database' sample which uses 'sqlcmd' to
116177
# initialize and verify the database schema in the local emulator.
117178
run: |
179+
sudo rm -f /etc/apt/sources.list.d/microsoft-prod.list
118180
curl https://packages.microsoft.com/keys/microsoft.asc | sudo tee /etc/apt/trusted.gpg.d/microsoft.asc
119181
curl https://packages.microsoft.com/config/ubuntu/$(lsb_release -rs)/prod.list | sudo tee /etc/apt/sources.list.d/mssql-release.list
120182
sudo apt-get update
121183
sudo ACCEPT_EULA=Y apt-get install -y msodbcsql18 mssql-tools18
122184
echo "/opt/mssql-tools18/bin" >> $GITHUB_PATH
123185
124-
- name: Run Test Scripts
125-
# Executes the sharded test suite. Each shard runs a subset of samples in parallel.
126-
# This includes bash scripts, Terraform deployments, and Bicep deployments.
186+
- name: "Run: ${{ matrix.name }}"
187+
# Each job runs exactly one test. SPLITS equals the total test count, and SHARD
188+
# is the 1-based index of this specific test, so run-samples.sh executes only it.
127189
run: make test SHARD=${{ matrix.shard }} SPLITS=${{ matrix.splits }}
128190
env:
129191
LOCALSTACK_AUTH_TOKEN: ${{ secrets.TEST_LOCALSTACK_AUTH_TOKEN }}

.gitignore

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ bld/
2222
[Oo]bj/
2323
[Ll]og/
2424
[Ll]ogs/
25+
publish/
2526

2627
# .NET Core
2728
project.lock.json
@@ -216,4 +217,13 @@ cython_debug/
216217
# before adapting.
217218
# Usually, these files will be generated by your IDE, so it is
218219
# better to have them ignored.
219-
.idea/
220+
.idea/
221+
## Terraform
222+
.terraform/
223+
*.tfstate
224+
*.tfstate.backup
225+
tfplan
226+
override.tf
227+
override.tf.json
228+
*_override.tf
229+
*_override.tf.json

README.md

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -28,12 +28,15 @@ This repository contains comprehensive sample projects demonstrating how to deve
2828
|-------------|-------------|
2929
| [Function App and Storage](./samples/function-app-storage-http/dotnet/README.md) | Azure Functions App using Blob, Queue, and Table Storage |
3030
| [Function App and Front Door](./samples/function-app-front-door/python/README.md) | Azure Functions App exposed via Front Door |
31-
| [Function App and Managed Identities](./samples/function-app-managed-identity/python/README.md) | Azure Function App using Managed Identities |
32-
| [Web App and PostgreSQL Database](./samples/web-app-postgresql-database/python/README.md) | Azure Web App using PostgreSQL Flexible Server |
31+
| [Function App and Managed Identities](./samples/function-app-managed-identity/python/README.md) | Azure Function App using Managed Identities |
32+
| [Function App and Service Bus](./samples/function-app-service-bus/dotnet/README.md) | Azure Function App using Service Bus |
3333
| [Web App and CosmosDB for MongoDB API ](./samples/web-app-cosmosdb-mongodb-api/python/README.md) | Azure Web App using CosmosDB for MongoDB API |
34-
| [Web App and CosmosDB for NoSQL API ](./samples/web-app-cosmosdb-nosql-api/python/README.md) | Azure Web App using CosmosDB for NoSQL API |
35-
| [Web App and Managed Identities](./samples/web-app-managed-identity/python/README.md) | Azure Web App using Managed Identities |
36-
| [Web App and SQL Database ](./samples/web-app-sql-database/python/README.md) | Azure Web App using SQL Database |
34+
| [Web App and CosmosDB for NoSQL API ](./samples/web-app-cosmosdb-nosql-api/python/README.md) | Azure Web App using CosmosDB for NoSQL API |
35+
| [Web App and Managed Identities](./samples/web-app-managed-identity/python/README.md) | Azure Web App using Managed Identities |
36+
| [Web App and SQL Database ](./samples/web-app-sql-database/python/README.md) | Azure Web App using SQL Database |
37+
| [Web App with Custom Docker Image](./samples/web-app-custom-image/python/README.md) | Azure Web App running a custom Docker image |
38+
| [ACI and Blob Storage](./samples/aci-blob-storage/python/README.md) | Azure Container Instances with ACR, Key Vault, and Blob Storage |
39+
| [Azure Service Bus with Spring Boot](./samples/servicebus/java/README.md) | Azure Service Bus used by a Spring Boot application |
3740

3841
## Sample Structure
3942

@@ -73,7 +76,7 @@ Follow the comprehensive setup guide in [LocalStack for Azure Quick Start](./doc
7376

7477
## Documentation
7578

76-
- [LocalStack for Azure Documentation](https://azure.localstack.cloud/)
79+
- [LocalStack for Azure Documentation](https://docs.localstack.cloud/azure/)
7780
- [Azure CLI with LocalStack](https://azure.localstack.cloud/user-guides/sdks/az/)
7881
- [Supported Azure Services](https://azure.localstack.cloud/references/coverage/)
7982

docs/LOCALSTACK.md

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,8 +28,15 @@ You can start the Azure emulator using one of the following methods:
2828
Make sure the `localstack` CLI is installed (`pip install localstack` or `brew install localstack/tap/localstack`).
2929

3030
```bash
31+
# Set the authentication token
3132
export LOCALSTACK_AUTH_TOKEN=<your_auth_token>
32-
IMAGE_NAME=localstack/localstack-azure-alpha localstack start
33+
34+
# Start the LocalStack Azure emulator
35+
IMAGE_NAME=localstack/localstack-azure-alpha localstack start -d
36+
localstack wait -t 60
37+
38+
# Route all Azure CLI calls to the LocalStack Azure emulator
39+
azlocal start-interception
3340
```
3441

3542
This:

0 commit comments

Comments
 (0)