### GitHub Actions Upload and Output Example Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md This example demonstrates how to use the action to upload an app and then access its output variables in subsequent steps. ```yaml - id: upload uses: mobile-dev-inc/action-maestro-cloud@v3 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: ${{ env.PROJECT_ID }} app-file: app.apk - name: Check Results run: | echo "Binary ID: ${{ steps.upload.outputs.MAESTRO_CLOUD_APP_BINARY_ID }}" echo "Console: ${{ steps.upload.outputs.MAESTRO_CLOUD_CONSOLE_URL }}" echo "Status: ${{ steps.upload.outputs.MAESTRO_CLOUD_UPLOAD_STATUS }}" echo "Results: ${{ steps.upload.outputs.MAESTRO_CLOUD_FLOW_RESULTS }}" ``` -------------------------------- ### Multiline Environment Variable Example Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/types.md Provides an example of how to format the multiline 'env' input for the GitHub Action. It shows a typical structure with multiple environment variables defined on separate lines. ```text USERNAME=alice PASSWORD=secret123 API_ENDPOINT=https://api.example.com ``` -------------------------------- ### Postprocess Execution Examples Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/postprocess.md Illustrates how to run the postprocess script in different modes. The synchronous mode passes an exit code, while the asynchronous mode does not. Examples also show behavior with a missing JUnit file. ```bash # Synchronous mode (exit code passed): node dist/postprocess.js /tmp/junit.xml 0 # Sets: MAESTRO_CLOUD_FLOW_RESULTS='[{"name":"login","status":"SUCCESS","errors":[]}]' # MAESTRO_CLOUD_UPLOAD_STATUS='SUCCESS' # Async mode (no exit code): node dist/postprocess.js /tmp/junit.xml # Sets: MAESTRO_CLOUD_FLOW_RESULTS='[]' # (MAESTRO_CLOUD_UPLOAD_STATUS not set) # Missing file: node dist/postprocess.js /nonexistent/junit.xml 0 # Sets: MAESTRO_CLOUD_FLOW_RESULTS='[]' # MAESTRO_CLOUD_UPLOAD_STATUS='SUCCESS' (exit 0) ``` -------------------------------- ### Usage Pattern: Uploading and then Using App Binary ID Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Example demonstrating uploading an app in one step and referencing its ID in a subsequent step. ```yaml - id: upload uses: mobile-dev-inc/action-maestro-cloud@v3 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: ${{ env.PROJECT_ID }} app-file: app.zip - uses: mobile-dev-inc/action-maestro-cloud@v3 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: ${{ env.PROJECT_ID }} app-binary-id: ${{ steps.upload.outputs.MAESTRO_CLOUD_APP_BINARY_ID }} ``` -------------------------------- ### FlowResult Example Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/postprocess.md An example demonstrating how to create a FlowResult object, indicating a flow named 'login-flow' that encountered an error. ```typescript const flow: FlowResult = { name: 'login-flow', status: 'ERROR', errors: ['Element "LoginButton" not found after 10 seconds'] } ``` -------------------------------- ### Incorrect File Path Example Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/README.md Illustrates an incorrect configuration where the 'app-file' path is specified incorrectly, potentially leading to a 'File Not Found' error. ```yaml # Wrong app-file: 'app.apk' ``` -------------------------------- ### Environment Variable Layering Example Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/architecture.md Demonstrates how environment variables are exported and potentially cleared across job steps using $GITHUB_ENV to prevent stale data leakage. ```text Job Step 1: exportVariable('MDEV_APP_BINARY_ID', 'app_xyz') → $GITHUB_ENV $GITHUB_ENV accumulates: MDEV_APP_BINARY_ID=app_xyz Job Step 2 (same action, different invocation): exportVariable('MDEV_APP_FILE', '/path/to/app.apk') exportVariable('MDEV_APP_BINARY_ID', '') ← Clear previous step's value → $GITHUB_ENV overwrites with empty $GITHUB_ENV now contains: MDEV_APP_BINARY_ID= ← Empty (cleared) MDEV_APP_FILE=/path/to/app.apk ``` -------------------------------- ### Derive Upload Status Example Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/types.md Demonstrates the usage of the `deriveUploadStatus` function, showing how it processes an array of `FlowResult` objects and an exit code to determine the overall upload status. This example results in an 'ERROR' status due to a flow failure. ```typescript const status: UploadStatus = deriveUploadStatus( [ { name: 'auth-flow', status: 'SUCCESS', errors: [] }, { name: 'payment-flow', status: 'ERROR', errors: ['Payment gateway timeout'] } ], 1 ); // Result: 'ERROR' ``` -------------------------------- ### App Input Validation for Mobile Tests Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/errors.md For non-web OS, provide exactly one of 'app-file' or 'app-binary-id'. This example shows valid configurations. ```yaml # Case 1: app-file only app-file: 'app.apk' app-binary-id: '' # Not provided # Case 2: app-binary-id only app-file: '' # Not provided app-binary-id: 'app_xyz' ``` -------------------------------- ### parseJunit Example Usage Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/postprocess.md Demonstrates how to use the parseJunit function with a sample JUnit XML string and shows the expected array of FlowResult objects. ```typescript const xml = ` Element "PaymentButton" not found ` const results = parseJunit(xml); // Returns: // [ // { name: 'login', status: 'SUCCESS', errors: [] }, // { name: 'checkout', status: 'ERROR', errors: ['Element "PaymentButton" not found'] } // ] ``` -------------------------------- ### App Input Validation for Web Tests Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/errors.md For web tests, omit both 'app-file' and 'app-binary-id'. This example shows a valid web configuration. ```yaml device-os: 'web' # app-file and app-binary-id omitted ``` -------------------------------- ### Example Upload Status Output Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Illustrates possible values for the MAESTRO_CLOUD_UPLOAD_STATUS output variable. ```plaintext PENDING PREPARING INSTALLING RUNNING SUCCESS ERROR CANCELED WARNING STOPPED ``` -------------------------------- ### Example Environment Variables After Execution Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/prelude.md Illustrates the environment variables exported by the action after its main execution, specifically for an app-file upload scenario. This helps in understanding the output format and available parameters. ```typescript // This is called automatically by the action; no direct invocation needed. // Example environment after main() completes (for app-file upload): // MDEV_API_KEY=rb_xyz // MDEV_PROJECT_ID=proj_abc // MDEV_BRANCH=feature/foo // MDEV_NAME=Add feature X // MDEV_APP_FILE=/work/app.apk // MDEV_APP_BINARY_ID= // MDEV_MAPPING_FILE= // MDEV_DEVICE_OS=android-33 // ... (other MDEV_* variables) ``` -------------------------------- ### Basic GitHub Actions Workflow Setup Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Add this snippet to your GitHub Actions workflow file to run Flows on Maestro Cloud. Ensure you replace the placeholder project ID and app file path with your actual values. The API key should be stored as a secret. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' # replace this with your actual project id app-file: ``` -------------------------------- ### Test Prelude Setup Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/testing.md Resets mocks and clears environment variables before each test to ensure isolation. Cleans up INPUT_* environment variables after each test. ```typescript beforeEach(() => { ;(github as any).context = JSON.parse(JSON.stringify(baseContext)) exportedVars = {} jest.spyOn(core, 'exportVariable').mockImplementation((k, v) => { exportedVars[k] = String(v) }) jest.spyOn(core, 'setFailed').mockImplementation((m) => { failures.push(typeof m === 'string' ? m : m.message) }) }) afterEach(() => { jest.restoreAllMocks() for (const k of Object.keys(process.env)) { if (k.startsWith('INPUT_')) delete process.env[k] } }) ``` -------------------------------- ### Specify iOS Device Model and OS Version Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Configure the action to run tests on a specific iOS device model and OS version. Use 'iPhone-11' for device model and 'iOS-18-2' for OS version as examples. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: app.zip device-model: iPhone-11 device-os: iOS-18-2 ``` -------------------------------- ### Run BATS Integration Tests Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/testing.md Execute BATS integration tests for the bash script. Requires BATS to be installed globally. ```bash BATS_LIB_PATH=$(npm root -g) bats __tests__/run-cloud.bats ``` -------------------------------- ### Specify Android Device Model and OS Version Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Configure the action to run tests on a specific Android device model and OS version. Use 'pixel_6' for device model and 'android-33' for OS version as examples. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: app.apk device-model: pixel_6 device-os: android-33 ``` -------------------------------- ### FlowResult Example Usage Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/types.md Illustrates how to create a `FlowResult` object, typically used to represent a failed flow. The example shows a flow named 'login-flow' with an 'ERROR' status and a specific error message. ```typescript const result: FlowResult = { name: 'login-flow', status: 'ERROR', errors: ['Button "Sign In" not found after 10 seconds'] } ``` -------------------------------- ### Parsing Flow Results with jq Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Example of parsing the JSON output of `MAESTRO_CLOUD_FLOW_RESULTS` using `jq` to filter for errors. ```yaml - run: | RESULTS='${{ steps.upload.outputs.MAESTRO_CLOUD_FLOW_RESULTS }}' # Parse with jq echo "$RESULTS" | jq '.[] | select(.status=="ERROR") | .name' ``` -------------------------------- ### Example Flow Results Output Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Shows the structure of the MAESTRO_CLOUD_FLOW_RESULTS output variable, which is an array of objects detailing flow execution status and errors. ```json [ { "name": "my-first-flow", "status": "SUCCESS", "errors": [] }, { "name": "my-second-flow", "status": "SUCCESS", "errors": [] }, { "name": "my-cancelled-flow", "status": "CANCELED", "errors": [] } ] ``` -------------------------------- ### Derive Upload Status Examples Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/postprocess.md Demonstrates how the `deriveUploadStatus` function determines the overall upload status based on an array of flow results and an exit code. It covers various scenarios including success, errors, stopped flows, and handling of empty flow arrays. ```typescript const flows1: FlowResult[] = [ { name: 'a', status: 'SUCCESS', errors: [] }, { name: 'b', status: 'SUCCESS', errors: [] } ]; deriveUploadStatus(flows1, 0); // Returns: 'SUCCESS' const flows2: FlowResult[] = [ { name: 'a', status: 'SUCCESS', errors: [] }, { name: 'b', status: 'ERROR', errors: ['Element not found'] } ]; deriveUploadStatus(flows2, 1); // Returns: 'ERROR' const flows3: FlowResult[] = [ { name: 'a', status: 'SUCCESS', errors: [] }, { name: 'b', status: 'STOPPED', errors: [] } ]; deriveUploadStatus(flows3, 1); // Returns: 'STOPPED' // Empty flows: trust exit code deriveUploadStatus([], 0); // Returns: 'SUCCESS' deriveUploadStatus([], 1); // Returns: 'ERROR' ``` -------------------------------- ### Build and Upload App Binary Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md This snippet demonstrates a two-step process: first building the app, then uploading it. The upload step can be configured for different platforms. ```yaml - id: build run: | # Build app and upload ./build.sh - id: upload-android uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_android' app-file: app-android.apk - id: upload-ios uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_ios' app-binary-id: ${{ steps.upload-android.outputs.MAESTRO_CLOUD_APP_BINARY_ID }} ``` -------------------------------- ### main Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/prelude.md The main entry point for the prelude step. It reads and validates GitHub Actions inputs, resolves file globs, and exports environment variables for downstream steps. ```APIDOC ## main ### Description Main entry point for the prelude step. Reads all GitHub Actions inputs, validates them, resolves file globs, and exports environment variables via `core.exportVariable` for consumption by downstream steps. ### Method async function ### Parameters None. Reads from GitHub Actions inputs and context. ### Return Type `Promise` - Does not return a value; side effects via `core.exportVariable`. ### Example ```typescript // This function is typically called automatically by the action runner. // Direct invocation example: await main(); ``` ``` -------------------------------- ### Run Release Command Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/RELEASING.md Execute this command to build and push artifacts for a new release. Replace `` with the desired semantic version (e.g., 1.2.3). ```bash npm run release ``` -------------------------------- ### Run All Tests Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/testing.md Execute all integration and unit tests using npm. ```bash npm test ``` -------------------------------- ### iOS Configuration Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Configure the action for iOS builds, specifying the .app file path. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: .app mapping-file: .app.dSYM ``` -------------------------------- ### Minimal Action Configuration Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md The most basic configuration for the action, requiring only API key, project ID, and the app file. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: app.apk ``` -------------------------------- ### Run Web Tests Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Execute web tests by setting 'device-os' to 'web'. The 'app-file' input is not required for web tests. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' device-os: web ``` -------------------------------- ### Optional Input: Workspace Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Directory containing Maestro flow files (.yaml or .yml). Defaults to '.maestro' if not specified. ```yaml workspace: 'myFlows/' ``` -------------------------------- ### Android Configuration Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Configure the action for Android builds, specifying the APK file path. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: app/build/outputs/apk/debug/app-debug.apk ``` -------------------------------- ### Upload App Binary and Use App Binary ID Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Uploads an app binary and then uses its ID in a subsequent step. Ensure the 'upload' step completes successfully before referencing its outputs. ```yaml - id: upload uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: app.zip - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-binary-id: ${{ steps.upload.outputs.MAESTRO_CLOUD_APP_BINARY_ID }} ``` -------------------------------- ### Specify App Build Output Path Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/README.md Use 'app-file' to specify the path to your application's build output. Supports exact paths or glob patterns. ```yaml app-file: 'app/build/outputs/apk/debug/app-debug.apk' ``` ```yaml app-file: '**/build/outputs/apk/debug/*.apk' ``` -------------------------------- ### Trigger Workflow on Issue Comment with Custom Branch Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md This example shows how to trigger a workflow on an issue comment and use the comment to specify a custom branch for testing. It retrieves the branch name using the GitHub CLI. ```yaml on: issue_comment: types: [created] jobs: test: if: contains(github.event.comment.body, '/test') runs-on: ubuntu-latest steps: - name: Get PR branch id: pr env: PR_NUMBER: ${{ github.event.issue.number }} GH_TOKEN: ${{ github.token }} run: | HEAD_REF=$(gh pr view "$PR_NUMBER" --json headRefName --jq '.headRefName') echo "branch=$HEAD_REF" >> $GITHUB_OUTPUT - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: app.zip branch: ${{ steps.pr.outputs.branch }} ``` -------------------------------- ### Advanced Configuration for App Upload Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Use this snippet for detailed app upload configurations, including device specifics, workspace, tags, and environment variables. ```yaml - id: upload uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: app.apk device-os: 'android-33' device-model: 'pixel_6' device-locale: 'de_DE' workspace: 'flows/' include-tags: 'smoke' exclude-tags: 'flaky,wip' env: | USERNAME=${{ secrets.TEST_USER }} PASSWORD=${{ secrets.TEST_PASS }} ENVIRONMENT=staging timeout: '90' ``` -------------------------------- ### Minimal Action Maestro Cloud Configuration Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/README.md Basic configuration for the Action Maestro Cloud. Requires API key, project ID, and the application file path. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example' app-file: app.apk ``` -------------------------------- ### Arithmetic Expansion for Condition Testing in Bash Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/shell-script.md While the example shows a common conditional test `[ -z "$VAR" ]` for checking if a variable is empty, arithmetic expansion itself is typically used for mathematical operations like `(( expression ))`. ```bash [ -z "$VAR" ] ``` -------------------------------- ### Maestro Cloud CLI Command Structure Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/architecture.md This bash script demonstrates how the maestro cloud CLI command is constructed using environment variables and optional flags. It is used to upload applications and run tests. ```bash maestro cloud \ --apiKey "$MDEV_API_KEY" \ --project-id "$MDEV_PROJECT_ID" \ [optional flags] \ "${env_args[@]}" \ "${format_args[@]}" \ --flows "$MDEV_WORKSPACE" ``` -------------------------------- ### Conditional Input: App File (APK/IPA/Bundle) Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Path to the application binary or a glob pattern. Used when `app-binary-id` is not provided. ```yaml app-file: app/build/outputs/apk/debug/app-debug.apk ``` ```yaml # or glob pattern: app-file: app/build/outputs/apk/**/*.apk ``` -------------------------------- ### iOS Configuration with dSYM Mapping File Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Configure the action for an iOS app, including the path to the dSYM file for symbolication. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: MyApp.app mapping-file: MyApp.app.dSYM ``` -------------------------------- ### Build Process Script Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/architecture.md The build script used to compile TypeScript files and bundle them with dependencies using @vercel/ncc. ```bash npm run build # Compiles prelude.ts and postprocess.ts to dist/prelude.js and dist/postprocess.js # Uses @vercel/ncc for bundling with dependencies ``` -------------------------------- ### Async Mode App Upload Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Configure the action to run in async mode for non-blocking uploads. This is useful when you don't need immediate feedback on the upload status. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: app.apk async: 'true' ``` -------------------------------- ### Create Temporary Files and Set Cleanup Trap Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/shell-script.md This snippet creates temporary files for JUnit XML output and standard CLI output capture. It also sets up a trap to ensure these temporary files are removed upon script exit, whether successful or due to an error. ```bash JUNIT_FILE=$(mktemp "${TMPDIR:-/tmp}/maestro-junit.XXXXXX") || \ { echo "::error::failed to create temp junit file"; exit 1; } OUTPUT_FILE=$(mktemp) || \ { echo "::error::failed to create temp file for CLI output"; exit 1; } trap 'rm -f "$OUTPUT_FILE" "$JUNIT_FILE"' EXIT ``` -------------------------------- ### Enable Asynchronous Flow Execution Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Set to 'true' to return immediately without waiting for flow results. Output variables like results and status will not be available. ```yaml async: 'true' ``` -------------------------------- ### Simulate GitHub Actions Inputs Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/testing.md Sets environment variables prefixed with INPUT_ to simulate GitHub Actions inputs for testing. Clears existing INPUT_* variables before setting new ones. ```typescript const setInputs = (inputs: Record) => { for (const k of Object.keys(process.env)) { if (k.startsWith('INPUT_')) delete process.env[k] } for (const [k, v] of Object.entries(inputs)) { process.env[`INPUT_${k.replace(/ /g, '_').toUpperCase()}`] = v } } setInputs({ 'api-key': 'k', 'project-id': 'p', 'app-file': 'a.apk' }) ``` -------------------------------- ### Correctly Set Environment Variables Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/README.md Environment variables must be set with a key-value pair using '='. Avoid setting them with only a key. ```yaml # Wrong (missing =) env: | USERNAME # Correct env: | USERNAME=alice PASSWORD=secret ``` -------------------------------- ### Specify Target Device Model Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Define the specific device model for running flows. Use 'maestro list-devices' to find supported models. ```yaml # iOS device-model: 'iPhone-11' device-model: 'iPhone-14-Pro' # Android device-model: 'pixel_6' device-model: 'pixel_7' ``` -------------------------------- ### Custom Device and Environment Variables Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/README.md Configures the Action Maestro Cloud to target a specific device OS, model, and locale, and sets custom environment variables for the test run. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example' app-file: app.apk device-os: 'android-33' device-model: 'pixel_6' device-locale: 'de_DE' env: | USERNAME=${{ secrets.TEST_USER }} PASSWORD=${{ secrets.TEST_PASS }} ``` -------------------------------- ### Access Action Output Variables Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Demonstrates how to access and print various output variables set by the action, such as console URL, flow results, upload status, and app binary ID. The 'if: always()' condition ensures these commands run regardless of previous step failures. ```yaml - id: upload uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: # ... any other parameters - name: Access Outputs if: always() run: | echo "Console URL: ${{ steps.upload.outputs.MAESTRO_CLOUD_CONSOLE_URL }}" echo "Flow Results: ${{ steps.upload.outputs.MAESTRO_CLOUD_FLOW_RESULTS }}" echo "Upload Status: ${{ steps.upload.outputs.MAESTRO_CLOUD_UPLOAD_STATUS }}" echo "App Binary ID: ${{ steps.upload.outputs.MAESTRO_CLOUD_APP_BINARY_ID }}" ``` -------------------------------- ### Postprocess Main Function Signature Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/postprocess.md The main entry point for the postprocess step. It reads a JUnit XML file, parses flow results, derives the upload status, and sets GitHub Actions outputs. It reads parameters from command-line arguments. ```typescript async function main(): Promise ``` -------------------------------- ### Release Process Script Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/architecture.md The script responsible for tagging, pushing, and creating GitHub releases. ```bash ./_release.sh # Tag, push, and create GitHub release ``` -------------------------------- ### Async Upload Configuration Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/README.md Configures the Action Maestro Cloud for an asynchronous upload. The action returns immediately after initiating the upload. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example' app-file: app.apk async: 'true' ``` -------------------------------- ### Validate App Input (File or Binary ID) Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/README.md Provide either 'app-file' or 'app-binary-id', but not both. This ensures the action knows which application artifact to use. ```yaml # Wrong (both provided) app-file: 'app.apk' app-binary-id: 'app_xyz' # Correct (app-file only) app-file: 'app.apk' # Correct (app-binary-id only) app-binary-id: 'app_xyz' ``` -------------------------------- ### Maestro CLI Output Processing Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/architecture.md Illustrates the flow of data and processing steps from the Maestro CLI's standard output to GitHub Actions outputs. ```text maestro CLI stdout ↓ run-cloud.sh: Parse & capture ↓ - Extract binary ID (regex: "App binary id: \S+") - Extract console URL (regex: "https://app.maestro.dev/\S+") - Run postprocess.js ↓ postprocess.ts: parseJunit(junit_xml) ↓ Flow results + upload status ↓ core.setOutput(key, value) ↓ $GITHUB_OUTPUT (GitHub Actions' output persistence) ↓ Downstream steps: ${{ steps.id.outputs.KEY }} ``` -------------------------------- ### Extract App Binary ID and Console URL Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/shell-script.md Parses the cleaned CLI output to extract the 'App binary id' and the Maestro console URL using `grep`, `awk`, and `head`. These patterns are designed to match the specific output format of the Maestro CLI. ```bash APP_BINARY_ID=$(echo "$CLEANED" | grep -oE "App binary id: \S+" | awk '{print $NF}' | head -n 1) CONSOLE_URL=$(echo "$CLEANED" | grep -oE "https://app\.maestro\.dev/\S+" | head -n 1) ``` -------------------------------- ### Optional Input: Name Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md A friendly name for the upload. If omitted, it's auto-derived from the PR title, commit message, or commit SHA. ```yaml name: 'My Custom Run Name' ``` -------------------------------- ### Inspect Action Outputs in GitHub Actions Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/errors.md Log the output variables produced by a GitHub Actions step. This is crucial for understanding the results of the action and for passing data to subsequent steps. ```yaml - run: | echo "Binary ID: ${{ steps.upload.outputs.MAESTRO_CLOUD_APP_BINARY_ID }}" echo "Console URL: ${{ steps.upload.outputs.MAESTRO_CLOUD_CONSOLE_URL }}" echo "Status: ${{ steps.upload.outputs.MAESTRO_CLOUD_UPLOAD_STATUS }}" echo "Results: ${{ steps.upload.outputs.MAESTRO_CLOUD_FLOW_RESULTS }}" ``` -------------------------------- ### Build Maestro Cloud CLI Command Array Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/shell-script.md Constructs a bash array representing the maestro cloud command. It uses conditional expansions for optional flags and handles format arguments based on the MDEV_ASYNC variable. ```bash format_args=() if [ -z "$MDEV_ASYNC" ]; then format_args=(--format junit --output "$JUNIT_FILE") fi CLOUD_COMMAND=( maestro cloud --apiKey "$MDEV_API_KEY" --project-id "$MDEV_PROJECT_ID" ${MDEV_API_URL:+--api-url "$MDEV_API_URL"} ${MDEV_NAME:+--name "$MDEV_NAME"} ${MDEV_BRANCH:+--branch "$MDEV_BRANCH"} ${MDEV_COMMIT_SHA:+--commit-sha "$MDEV_COMMIT_SHA"} ${MDEV_REPO_OWNER:+--repoOwner "$MDEV_REPO_OWNER"} ${MDEV_REPO_NAME:+--repoName "$MDEV_REPO_NAME"} ${MDEV_PR_ID:+--pullRequestId "$MDEV_PR_ID"} ${MDEV_APP_FILE:+--app-file "$MDEV_APP_FILE"} ${MDEV_APP_BINARY_ID:+--app-binary-id "$MDEV_APP_BINARY_ID"} ${MDEV_MAPPING_FILE:+--mapping "$MDEV_MAPPING_FILE"} ${MDEV_DEVICE_OS:+--device-os "$MDEV_DEVICE_OS"} ${MDEV_DEVICE_LOCALE:+--device-locale "$MDEV_DEVICE_LOCALE"} ${MDEV_DEVICE_MODEL:+--device-model "$MDEV_DEVICE_MODEL"} ${MDEV_INCLUDE_TAGS:+--include-tags "$MDEV_INCLUDE_TAGS"} ${MDEV_EXCLUDE_TAGS:+--exclude-tags "$MDEV_EXCLUDE_TAGS"} ${MDEV_TIMEOUT:+--timeout "$MDEV_TIMEOUT"} ${MDEV_ASYNC:+--async} ${MDEV_ANDROID_API_LEVEL:+--android-api-level "$MDEV_ANDROID_API_LEVEL"} ${MDEV_IOS_VERSION:+--ios-version "$MDEV_IOS_VERSION"} "${format_args[@]+${format_args[@]}}" "${env_args[@]+${env_args[@]}}" --flows "${MDEV_WORKSPACE:-.maestro}" ) ``` ```bash maestro cloud \ --apiKey "rb_xyz" \ --project-id "proj_abc" \ --name "My Upload" \ --branch "feature/foo" \ --device-os "android-33" \ --format junit --output "/tmp/junit.XXXXXX" \ -e "USERNAME=alice" \ -e "PASSWORD=secret" \ --flows ".maestro" ``` -------------------------------- ### Android Upload with ProGuard Mapping Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/README.md Configuration for uploading an Android application with ProGuard mapping files. This is essential for deobfuscating stack traces from release builds. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example' app-file: app/build/outputs/apk/release/app-release.apk mapping-file: app/build/outputs/mapping/release/mapping.txt ``` -------------------------------- ### Generate Coverage Report Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/testing.md Generate a test coverage report. ```bash npm run test:coverage ``` -------------------------------- ### GitHub Actions Primitive String Inputs Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/types.md Lists the primitive string inputs accepted by the GitHub Action. These cover essential configuration like API keys, project IDs, and optional parameters for customizing the upload and execution. ```typescript { 'api-key': string // Required. API authentication key. 'project-id': string // Required. Maestro Cloud project identifier. 'api-url': string // Optional. Custom API endpoint URL. 'name': string // Optional. Display name for the upload. 'branch': string // Optional. Git branch name (overrides detection). 'app-file': string // Optional (required if no app-binary-id). App file path or glob. 'app-binary-id': string // Optional (required if no app-file). Pre-uploaded binary ID. 'mapping-file': string // Optional. ProGuard mapping or dSYM file path. 'workspace': string // Optional. Maestro flows directory (default: .maestro). 'device-os': string // Optional. Target OS version (e.g., android-33, iOS-18-2, web). 'device-model': string // Optional. Target device model (e.g., pixel_6, iPhone-11). 'device-locale': string // Optional. Device locale (e.g., en_US, de_DE). 'include-tags': string // Optional. Comma-separated tags to include. 'exclude-tags': string // Optional. Comma-separated tags to exclude. 'timeout': string // Optional. Minutes to wait (numeric string). 'async': string // Optional. Boolean as string: 'true' or 'false'. 'maestro-cli-version': string // Optional. Specific CLI version pin. 'android-api-level': string // Deprecated. Use device-os instead. 'ios-version': string // Deprecated. Use device-os instead. } ``` -------------------------------- ### Handle Temp File Creation Failures Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/shell-script.md Writes an error message to standard output using GitHub Actions error directive and exits with status 1 if temporary file creation fails. ```bash { echo "::error::failed to create temp junit file"; exit 1; } ``` -------------------------------- ### Optional Input: Mapping File (Android/iOS) Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Path to ProGuard mapping file (Android) or dSYM archive (iOS) for symbol deobfuscation. Supports glob patterns. ```yaml # Android mapping-file: app/build/outputs/mapping/release/mapping.txt ``` ```yaml # iOS mapping-file: MyApp.app.dSYM ``` -------------------------------- ### Input to Internal Variables Data Flow Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/architecture.md Illustrates the data flow from GitHub Actions inputs to internal environment variables used by the action. This process involves input retrieval, validation, and environment variable export. ```text GitHub Actions inputs (action.yml) ↓ prelude.ts: core.getInput(key) ↓ Validation & transformation ↓ core.exportVariable(MDEV_*, value) ↓ $GITHUB_ENV (GitHub Actions' environment persistence) ↓ run-cloud.sh: Read ${MDEV_*} variables ``` -------------------------------- ### Set GitHub Actions Outputs Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/shell-script.md Conditionally writes environment variables to the GITHUB_OUTPUT file in the format KEY=VALUE. This is used to pass information to subsequent steps in a GitHub Actions workflow. ```bash [ -n "$APP_BINARY_ID" ] && echo "MAESTRO_CLOUD_APP_BINARY_ID=$APP_BINARY_ID" >> "$GITHUB_OUTPUT" [ -n "$CONSOLE_URL" ] && echo "MAESTRO_CLOUD_CONSOLE_URL=$CONSOLE_URL" >> "$GITHUB_OUTPUT" ``` -------------------------------- ### Run Action in Asynchronous Mode Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Configure the action to run asynchronously, meaning it won't wait for the upload to complete. This is useful for faster workflow execution when immediate feedback on upload status is not critical. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: app.zip async: true ``` -------------------------------- ### Verify Action Inputs in GitHub Actions Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/errors.md Log the values of inputs passed to a GitHub Actions workflow step. This is a common debugging technique to ensure the correct data is being used. ```yaml - run: | echo "api-key: ${{ inputs.api-key }}" echo "project-id: ${{ inputs.project-id }}" echo "app-file: ${{ inputs.app-file }}" ``` -------------------------------- ### iOS Upload with dSYM Mapping Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/README.md Configuration for uploading an iOS application with dSYM files. This allows for symbolication of crash reports. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example' app-file: MyApp.app mapping-file: MyApp.app.dSYM ``` -------------------------------- ### Specify Device Locale Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Set the locale for the target device. The format is ISO-639-1 (lowercase) plus ISO-3166-1 (uppercase), separated by an underscore. ```yaml device-locale: 'en_US' device-locale: 'de_DE' device-locale: 'fr_FR' ``` -------------------------------- ### Configure Device Locale Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Sets the device locale for test execution. The locale format is a combination of ISO-639-1 and ISO-3166-1 codes (e.g., 'de_DE'). ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: app.zip device-locale: de_DE ``` -------------------------------- ### Pass Environment Variables to Upload Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/README.md Include environment variables as a multiline string in the 'env' argument. This allows you to pass custom configurations or secrets to your test environment. ```yaml - uses: mobile-dev-inc/action-maestro-cloud@v3.0.1 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_01example0example1example2' app-file: app.zip env: | USERNAME= PASSWORD= ``` -------------------------------- ### Enable Debug Logging in GitHub Actions Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/errors.md Set the `ACTIONS_STEP_DEBUG` environment variable to `true` to enable verbose logging within GitHub Actions. This will log all inputs and environment variables for debugging purposes. ```yaml env: ACTIONS_STEP_DEBUG: true ``` -------------------------------- ### Watch Mode for Tests Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/testing.md Continuously re-run tests in response to file changes. ```bash npm run test:watch ``` -------------------------------- ### Maestro CLI Version Pinning Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Configure a specific version of the Maestro CLI to be used by the action. Defaults to the latest version if not specified. ```yaml maestro-cli-version: '1.37.0' ``` -------------------------------- ### Optional Input: Branch Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md Git branch name for upload metadata. Auto-detected from GitHub context if omitted. Useful for specific event triggers. ```yaml branch: 'feature/my-feature' ``` -------------------------------- ### Conditional Input: App Binary ID Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md ID of a previously uploaded binary. Use when the app is already uploaded and `app-file` is not provided. ```yaml app-binary-id: ${{ steps.upload.outputs.MAESTRO_CLOUD_APP_BINARY_ID }} ``` -------------------------------- ### Execute Maestro CLI and Capture Output/Exit Code Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/api-reference/shell-script.md Executes the constructed Maestro CLI command and pipes its standard output to `tee` for simultaneous display and file capture. It specifically captures the exit code of the CLI command, not `tee`. ```bash "${CLOUD_COMMAND[@]}" | tee "$OUTPUT_FILE" EXIT_CODE=${PIPESTATUS[0]} ``` -------------------------------- ### Fixing App File Glob Pattern Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/errors.md Correct the 'app-file' path or glob pattern if it resolves to zero matching files. Ensure the file exists in the working directory. ```yaml # Correct path app-file: 'app/build/outputs/apk/debug/app-debug.apk' # Or use glob app-file: '**/app-debug.apk' ``` -------------------------------- ### Defensive XML Parsing for JUnit Testcases Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/testing.md Demonstrates how the `parseJunit` function defensively ignores testcases that are missing required attributes like 'name' or 'status'. This allows for partial parsing of malformed JUnit XML files. ```typescript it('ignores testcases missing name or status', () => { const xml = ` ` expect(parseJunit(xml)).toEqual([ { name: 'z', status: 'SUCCESS', errors: [] }, ]) }) ``` -------------------------------- ### Deprecated iOS Version Configuration Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/configuration.md This snippet shows the deprecated `ios-version` configuration. It is recommended to use `device-os` instead. ```yaml ios-version: '18' # ⚠ Deprecated ``` -------------------------------- ### Conditional Step Execution Based on Success or Failure Source: https://github.com/mobile-dev-inc/action-maestro-cloud/blob/main/_autodocs/errors.md Implement conditional logic in GitHub Actions to execute specific steps based on whether a previous step succeeded or failed. This is useful for reporting or cleanup. ```yaml - id: upload uses: mobile-dev-inc/action-maestro-cloud@v3 with: api-key: ${{ secrets.MAESTRO_CLOUD_API_KEY }} project-id: 'proj_xyz' app-file: 'app.apk' - name: Report Success if: success() run: | echo "Upload status: ${{ steps.upload.outputs.MAESTRO_CLOUD_UPLOAD_STATUS }}" - name: Report Failure if: failure() run: | echo "Upload failed; check action logs" ```