-
Notifications
You must be signed in to change notification settings - Fork 1
ci: adds shared reusable setup polytest and mock server actions #18
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
aorumbayev
merged 11 commits into
algorandfoundation:main
from
aorumbayev:feat/ghcr-and-shared-action
Dec 8, 2025
Merged
Changes from 10 commits
Commits
Show all changes
11 commits
Select commit
Hold shift + click to select a range
7a2b711
chore: cd for image publishing
aorumbayev 9d72675
chore: test (#1)
aorumbayev ce73f8c
Merge remote-tracking branch 'aorumbayev/main' into feat/ghcr-and-sha…
aorumbayev 878a3fa
feat: add shared setup-polytest gh action
aorumbayev 6ea91d1
chore: Update test_configs/kmd_client.jsonc
aorumbayev 02d14c4
chore: update .github/workflows/publish-docker.yml
aorumbayev b502a56
refactor: adds run-mock-server GitHub Action
aorumbayev 99fdb19
chore: tweak health check
aorumbayev f23f474
Merge branch 'main' into feat/ghcr-and-shared-action
aorumbayev b0617e7
docs: tweak docs
aorumbayev 2c0ff3d
chore: copilot comments
aorumbayev File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,158 @@ | ||
| # Run Mock Server Action | ||
|
|
||
| A GitHub Actions composite action to start a mock server for testing Algorand API clients (algod, indexer, kmd). | ||
|
|
||
| ## Description | ||
|
|
||
| This action sets up and starts a Bun-based mock server that simulates Algorand node APIs. It handles: | ||
|
|
||
| - Installing Bun runtime | ||
| - Installing mock-server dependencies | ||
| - Starting the server in the background | ||
| - Waiting for the server to be healthy | ||
| - Exporting environment variables for use in subsequent steps | ||
|
|
||
| ## Inputs | ||
|
|
||
| | Input | Required | Default | Description | | ||
| | -------- | -------- | ------- | ------------------------------------------------------------------ | | ||
| | `client` | Yes | - | The client type to mock: `algod`, `indexer`, or `kmd` | | ||
| | `port` | No | \* | Port to run the server on | | ||
| | `ref` | No | `main` | Git ref to use when the action is called from external repos | | ||
|
|
||
| \* Default ports by client type: | ||
|
|
||
| - `algod`: 8000 | ||
| - `kmd`: 8001 | ||
| - `indexer`: 8002 | ||
|
|
||
| ## Outputs | ||
|
|
||
| This action exports the following environment variables: | ||
|
|
||
| | Client | Environment Variable | Example Value | | ||
| | --------- | --------------------- | ----------------------- | | ||
| | `algod` | `MOCK_ALGOD_URL` | `http://localhost:8000` | | ||
| | `indexer` | `MOCK_INDEXER_URL` | `http://localhost:8002` | | ||
| | `kmd` | `MOCK_KMD_URL` | `http://localhost:8001` | | ||
|
|
||
| ## Usage | ||
|
|
||
| ### Basic Usage (within the same repo) | ||
|
|
||
| ```yaml | ||
| jobs: | ||
| test: | ||
| runs-on: ubuntu-latest | ||
| steps: | ||
| - uses: actions/checkout@v4 | ||
|
|
||
| - name: Start algod mock server | ||
| uses: ./.github/actions/run-mock-server | ||
| with: | ||
| client: algod | ||
|
|
||
| - name: Run tests | ||
| run: | | ||
| echo "Mock server URL: $MOCK_ALGOD_URL" | ||
| # Your test commands here | ||
| ``` | ||
|
|
||
| ### Multiple Mock Servers | ||
|
|
||
| ```yaml | ||
| jobs: | ||
| test: | ||
| runs-on: ubuntu-latest | ||
| steps: | ||
| - uses: actions/checkout@v4 | ||
|
|
||
| - name: Start algod mock server | ||
| uses: ./.github/actions/run-mock-server | ||
| with: | ||
| client: algod | ||
|
|
||
| - name: Start indexer mock server | ||
| uses: ./.github/actions/run-mock-server | ||
| with: | ||
| client: indexer | ||
|
|
||
| - name: Start kmd mock server | ||
| uses: ./.github/actions/run-mock-server | ||
| with: | ||
| client: kmd | ||
|
|
||
| - name: Run tests | ||
| run: | | ||
| echo "Algod URL: $MOCK_ALGOD_URL" | ||
| echo "Indexer URL: $MOCK_INDEXER_URL" | ||
| echo "KMD URL: $MOCK_KMD_URL" | ||
| ``` | ||
|
|
||
| ### Custom Port | ||
|
|
||
| ```yaml | ||
| jobs: | ||
| test: | ||
| runs-on: ubuntu-latest | ||
| steps: | ||
| - uses: actions/checkout@v4 | ||
|
|
||
| - name: Start algod mock server on custom port | ||
| uses: ./.github/actions/run-mock-server | ||
| with: | ||
| client: algod | ||
| port: 9000 | ||
|
|
||
| - name: Run tests | ||
| run: | | ||
| # MOCK_ALGOD_URL will be http://localhost:9000 | ||
| curl $MOCK_ALGOD_URL/health | ||
| ``` | ||
|
|
||
| ### Usage from External Repository | ||
|
|
||
| ```yaml | ||
| jobs: | ||
| test: | ||
| runs-on: ubuntu-latest | ||
| steps: | ||
| - name: Checkout algokit-polytest | ||
| uses: actions/checkout@v4 | ||
| with: | ||
| repository: algorandfoundation/algokit-polytest | ||
| ref: main | ||
| path: algokit-polytest | ||
|
|
||
| - name: Start mock server | ||
| uses: ./algokit-polytest/.github/actions/run-mock-server | ||
| with: | ||
| client: algod | ||
| ref: main | ||
| ``` | ||
aorumbayev marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| ## Requirements | ||
|
|
||
| - The mock-server must be located at `resources/mock-server/` relative to this action's parent repository | ||
| - The runner must support Bun installation (Linux and macOS runners are supported) | ||
|
|
||
| ## Troubleshooting | ||
|
|
||
| ### Server fails to start | ||
|
|
||
| Check the server logs which are written to `/tmp/mock-server-{client}.log`. The action will automatically display these logs if the health check fails. | ||
|
|
||
| ### Port conflicts | ||
|
|
||
| If the default port is already in use, specify a custom port: | ||
|
|
||
| ```yaml | ||
| - uses: ./.github/actions/run-mock-server | ||
| with: | ||
| client: algod | ||
| port: 9999 | ||
| ``` | ||
|
|
||
| ### Health check timeout | ||
|
|
||
| The action waits up to 30 seconds for the server to become healthy. If you need more time, consider checking your mock-server configuration or increasing server resources. | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,134 @@ | ||
| name: "Run Mock Server" | ||
| description: "Start a mock server for testing Algorand API clients (algod, indexer, kmd)" | ||
|
|
||
| inputs: | ||
| client: | ||
| description: "The client type to mock (algod, indexer, kmd)" | ||
| required: true | ||
| port: | ||
| description: "Port to run the server on (defaults: algod=8000, indexer=8002, kmd=8001)" | ||
| required: false | ||
| default: "" | ||
| ref: | ||
| description: "Git ref to use when action is called from external repos" | ||
| required: false | ||
| default: "main" | ||
aorumbayev marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| runs: | ||
| using: "composite" | ||
| steps: | ||
| - name: Determine port | ||
| id: port | ||
| shell: bash | ||
| run: | | ||
| set -Eeuo pipefail | ||
aorumbayev marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| CLIENT="${{ inputs.client }}" | ||
| PORT="${{ inputs.port }}" | ||
|
|
||
| # Validate client type | ||
| if [[ ! "$CLIENT" =~ ^(algod|indexer|kmd)$ ]]; then | ||
| echo "::error::Invalid client type '$CLIENT'. Must be one of: algod, indexer, kmd" | ||
| exit 1 | ||
| fi | ||
|
|
||
| # Set default port based on client type if not provided | ||
| if [[ -z "$PORT" ]]; then | ||
| case "$CLIENT" in | ||
| algod) PORT=8000 ;; | ||
| indexer) PORT=8002 ;; | ||
| kmd) PORT=8001 ;; | ||
| esac | ||
| fi | ||
|
|
||
| # Validate port is a number | ||
| if [[ ! "$PORT" =~ ^[0-9]+$ ]]; then | ||
| echo "::error::Invalid port '$PORT'. Must be a number" | ||
| exit 1 | ||
| fi | ||
|
|
||
| echo "port=$PORT" >> "$GITHUB_OUTPUT" | ||
| echo "Using port $PORT for $CLIENT mock server" | ||
|
|
||
| - name: Setup Bun | ||
| uses: oven-sh/setup-bun@v2 | ||
|
|
||
| - name: Install mock-server dependencies | ||
| shell: bash | ||
| working-directory: ${{ github.action_path }}/../../../resources/mock-server | ||
| run: | | ||
| set -Eeuo pipefail | ||
aorumbayev marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| bun install --frozen-lockfile | ||
|
|
||
| - name: Start mock server | ||
| shell: bash | ||
| working-directory: ${{ github.action_path }}/../../../resources/mock-server | ||
| run: | | ||
| set -Eeuo pipefail | ||
aorumbayev marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| CLIENT="${{ inputs.client }}" | ||
| PORT="${{ steps.port.outputs.port }}" | ||
| CLIENT_UPPER=$(echo "$CLIENT" | tr '[:lower:]' '[:upper:]') | ||
|
|
||
| echo "Starting $CLIENT mock server on port $PORT..." | ||
|
|
||
| # Export port for the mock server to read | ||
| export "${CLIENT_UPPER}_PORT=$PORT" | ||
|
|
||
| # Start server in background with nohup | ||
| nohup bun bin/server.ts "$CLIENT" > /tmp/mock-server-${CLIENT}.log 2>&1 & | ||
| SERVER_PID=$! | ||
|
|
||
| echo "Mock server started with PID $SERVER_PID" | ||
| echo "MOCK_SERVER_PID=$SERVER_PID" >> "$GITHUB_ENV" | ||
|
|
||
| - name: Wait for health check | ||
| shell: bash | ||
| run: | | ||
| set -Eeuo pipefail | ||
aorumbayev marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| CLIENT="${{ inputs.client }}" | ||
| PORT="${{ steps.port.outputs.port }}" | ||
| HEALTH_URL="http://localhost:${PORT}/health" | ||
| MAX_RETRIES=30 | ||
| RETRY_INTERVAL=1 | ||
|
|
||
| echo "Waiting for $CLIENT mock server health check at $HEALTH_URL..." | ||
|
|
||
| for ((i=1; i<=MAX_RETRIES; i++)); do | ||
| # Use -s (silent) and check HTTP status code | ||
| # Accept ANY HTTP response (even 4xx/5xx) as server being ready | ||
| # The mock server returns 500 for unrecorded endpoints like /health | ||
| HTTP_CODE=$(curl -s -o /dev/null -w "%{http_code}" --max-time 2 "$HEALTH_URL" 2>/dev/null || echo "000") | ||
|
|
||
| if [[ "$HTTP_CODE" != "000" ]]; then | ||
| echo "Mock server is responding (HTTP $HTTP_CODE) after $i seconds" | ||
| break | ||
| fi | ||
|
|
||
| if [[ $i -eq $MAX_RETRIES ]]; then | ||
| echo "::error::Health check failed after ${MAX_RETRIES} seconds" | ||
| echo "Server logs:" | ||
| cat /tmp/mock-server-${CLIENT}.log 2>/dev/null || echo "No logs available" | ||
| exit 1 | ||
| fi | ||
|
|
||
| echo "Attempt $i/$MAX_RETRIES: Server not ready, retrying in ${RETRY_INTERVAL}s..." | ||
| sleep "$RETRY_INTERVAL" | ||
| done | ||
|
|
||
| - name: Export environment variables | ||
| shell: bash | ||
| run: | | ||
| set -Eeuo pipefail | ||
aorumbayev marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| CLIENT="${{ inputs.client }}" | ||
| PORT="${{ steps.port.outputs.port }}" | ||
| URL="http://localhost:${PORT}" | ||
|
|
||
| # Convert client to uppercase for env var name | ||
| CLIENT_UPPER=$(echo "$CLIENT" | tr '[:lower:]' '[:upper:]') | ||
| ENV_VAR_NAME="MOCK_${CLIENT_UPPER}_URL" | ||
|
|
||
| echo "${ENV_VAR_NAME}=${URL}" >> "$GITHUB_ENV" | ||
| echo "Exported $ENV_VAR_NAME=$URL" | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,17 @@ | ||
| name: Setup Polytest | ||
| description: Install Rust and polytest CLI | ||
|
|
||
| inputs: | ||
| version: | ||
| description: Polytest version (empty for latest) | ||
| required: false | ||
| default: "" | ||
|
|
||
| runs: | ||
| using: composite | ||
| steps: | ||
| - uses: dtolnay/rust-toolchain@stable | ||
|
|
||
| - name: Install polytest | ||
| shell: bash | ||
| run: cargo install polytest --locked ${{ inputs.version && format('--version {0}', inputs.version) || '' }} |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.