Android AppCenter Tests

name: Android AppCenter Tests

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/android-appcenter.yml'
      - 'binding/android/PorcupineTestApp/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/android-appcenter.yml'
      - 'binding/android/PorcupineTestApp/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'

defaults:
  run:
    working-directory: binding/android/PorcupineTestApp

jobs:
  build:
    name: Run Android Tests on AppCenter
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js LTS
      uses: actions/setup-node@v3
      with:
        node-version: lts/*

    - name: Install AppCenter CLI
      run: npm install -g appcenter-cli

    - name: set up JDK 11
      uses: actions/setup-java@v3
      with:
        java-version: '11'
        distribution: 'temurin'

    - name: Copy test_resources
      run: ./copy_test_resources.sh

    - name: Inject AccessKey
      run: echo pvTestingAccessKey="${{secrets.PV_VALID_ACCESS_KEY}}" >> local.properties

    - name: Inject Android keystore variables
      run: |
        echo storePassword="${{secrets.ANDROID_RELEASE_KEYSTORE_PASSWORD}}" >> local.properties
        echo keyPassword="${{secrets.ANDROID_RELEASE_KEYSTORE_PASSWORD}}" >> local.properties
        echo keyAlias=picovoice >> local.properties
        echo storeFile=../picovoice.jks >> local.properties

    - name: Setup Android keystore file
      run: echo "${{secrets.ANDROID_RELEASE_KEYSTORE_FILE_B64}}" | base64 -d > picovoice.jks

    - name: Grant execute permission for gradlew
      run: chmod +x gradlew

    - name: Build app
      run: ./gradlew assembleEnDebug

    - name: Build androidTest
      run: ./gradlew assembleEnDebugAndroidTest

    - name: Run tests on AppCenter
      run: appcenter test run espresso
        --token ${{secrets.APPCENTERAPITOKEN}}
        --app "Picovoice/Porcupine-Android"
        --devices "Picovoice/android-min-max"
        --app-path porcupine-test-app/build/outputs/apk/en/debug/porcupine-test-app-en-debug.apk
        --test-series "porcupine-android"
        --locale "en_US"
        --build-dir porcupine-test-app/build/outputs/apk/androidTest/en/debug

  build-integ:
    name: Run Android Integration Tests on AppCenter
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js LTS
      uses: actions/setup-node@v3
      with:
        node-version: lts/*

    - name: Install AppCenter CLI
      run: npm install -g appcenter-cli

    - name: set up JDK 11
      uses: actions/setup-java@v3
      with:
        java-version: '11'
        distribution: 'temurin'

    - name: Copy test_resources
      run: ./copy_test_resources.sh

    - name: Inject AccessKey
      run: echo pvTestingAccessKey="${{secrets.PV_VALID_ACCESS_KEY}}" >> local.properties

    - name: Inject Android keystore variables
      run: |
        echo storePassword="${{secrets.ANDROID_RELEASE_KEYSTORE_PASSWORD}}" >> local.properties
        echo keyPassword="${{secrets.ANDROID_RELEASE_KEYSTORE_PASSWORD}}" >> local.properties
        echo keyAlias=picovoice >> local.properties
        echo storeFile=../picovoice.jks >> local.properties

    - name: Setup Android keystore file
      run: echo "${{secrets.ANDROID_RELEASE_KEYSTORE_FILE_B64}}" | base64 -d > picovoice.jks

    - name: Grant execute permission for gradlew
      run: chmod +x gradlew

    - name: Build app
      run: ./gradlew assembleEnRelease

    - name: Build androidTest
      run: ./gradlew assembleEnReleaseAndroidTest -DtestBuildType=integ

    - name: Run tests on AppCenter
      run: appcenter test run espresso
        --token ${{secrets.APPCENTERAPITOKEN}}
        --app "Picovoice/Porcupine-Android"
        --devices "Picovoice/android-min-max"
        --app-path porcupine-test-app/build/outputs/apk/en/release/porcupine-test-app-en-release.apk
        --test-series "porcupine-android"
        --locale "en_US"
        --build-dir porcupine-test-app/build/outputs/apk/androidTest/en/release


Android Demos

name: Android Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/android-demos.yml'
      - 'demo/android/**'
      - '!demo/android/Activity/README.md'
      - '!demo/android/Service/README.md'
      - '!demo/android/STT/README.md'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/android-demos.yml'
      - 'demo/android/**'
      - '!demo/android/Activity/README.md'
      - '!demo/android/Service/README.md'
      - '!demo/android/STT/README.md'

jobs:
  build-activity-demo:
    runs-on: ubuntu-latest
    defaults:
      run:
        working-directory: demo/android/Activity

    steps:
    - uses: actions/checkout@v3

    - name: set up JDK 11
      uses: actions/setup-java@v3
      with:
        java-version: '11'
        distribution: 'temurin'

    - name: Build English
      run: ./gradlew assembleEnDebug

    - name: Build Other Language
      run: ./gradlew assembleArDebug

  build-service-demo:
    runs-on: ubuntu-latest
    defaults:
      run:
        working-directory: demo/android/Service

    steps:
    - uses: actions/checkout@v3

    - name: set up JDK 11
      uses: actions/setup-java@v3
      with:
        java-version: '11'
        distribution: 'temurin'

    - name: Build
      run: ./gradlew assembleDebug

  build-stt-demo:
    runs-on: ubuntu-latest
    defaults:
      run:
        working-directory: demo/android/STT

    steps:
    - uses: actions/checkout@v3

    - name: set up JDK 11
      uses: actions/setup-java@v3
      with:
        java-version: '11'
        distribution: 'temurin'

    - name: Build
      run: ./gradlew assembleDebug


Android Performance

name: Android Performance

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/android-perf.yml'
      - 'binding/android/PorcupineTestApp/**/build.gradle'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/android-perf.yml'
      - 'binding/android/PorcupineTestApp/**/build.gradle'

defaults:
  run:
    working-directory: binding/android/PorcupineTestApp/

jobs:
  build:
    name: Run Android Speed Tests on AppCenter
    runs-on: ubuntu-latest

    strategy:
      matrix:
        device: [single-android, 32bit-android]
        include:
        - device: single-android
          performanceThresholdSec: 0.5
        - device: 32bit-android
          performanceThresholdSec: 2.75

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js LTS
      uses: actions/setup-node@v3
      with:
        node-version: lts/*

    - name: Install AppCenter CLI
      run: npm install -g appcenter-cli

    - name: set up JDK 11
      uses: actions/setup-java@v3
      with:
        java-version: '11'
        distribution: 'temurin'

    - name: Copy test_resources
      run: ./copy_test_resources.sh

    - name: Inject AccessKey
      run: echo pvTestingAccessKey="${{secrets.PV_VALID_ACCESS_KEY}}" >> local.properties

    - name: Inject Android keystore variables
      run: |
        echo storePassword="${{secrets.ANDROID_RELEASE_KEYSTORE_PASSWORD}}" >> local.properties
        echo keyPassword="${{secrets.ANDROID_RELEASE_KEYSTORE_PASSWORD}}" >> local.properties
        echo keyAlias=picovoice >> local.properties
        echo storeFile=../picovoice.jks >> local.properties

    - name: Setup Android keystore file
      run: echo "${{secrets.ANDROID_RELEASE_KEYSTORE_FILE_B64}}" | base64 -d > picovoice.jks

    - name: Inject Number of Iterations
      run: echo numTestIterations="100" >> local.properties

    - name: Inject Performance Threshold
      run: echo performanceThresholdSec="${{ matrix.performanceThresholdSec }}" >> local.properties

    - name: Grant execute permission for gradlew
      run: chmod +x gradlew

    - name: Build app
      run: ./gradlew assembleEnDebug

    - name: Build androidTest
      run: ./gradlew assembleEnDebugAndroidTest -DtestBuildType=perf

    - name: Run tests on AppCenter
      run: appcenter test run espresso
        --token ${{secrets.APPCENTERAPITOKEN}}
        --app "Picovoice/Porcupine-Android"
        --devices "Picovoice/${{ matrix.device }}"
        --app-path porcupine-test-app/build/outputs/apk/en/debug/porcupine-test-app-en-debug.apk
        --test-series "porcupine-android"
        --locale "en_US"
        --build-dir porcupine-test-app/build/outputs/apk/androidTest/en/debug


Angular Codestyle

name: Angular Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '**/angular/*.js'
      - '**/angular/*.ts'
      - '.github/workflows/angular-codestyle.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '**/angular/*.js'
      - '**/angular/*.ts'
      - '.github/workflows/angular-codestyle.yml'

jobs:
  check-angular-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js LTS
      uses: actions/setup-node@v3
      with:
        node-version: lts/*

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Run Binding Linter
      run: yarn && yarn lint
      working-directory: binding/angular

    - name: Run Demo Linter
      run: yarn && yarn lint
      working-directory: demo/angular


Angular Demos

name: Angular Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'demo/angular/**'
      - 'demo/angular-stt/**'
      - '!demo/angular/README.md'
      - '!demo/angular-stt/README.md'
      - '.github/workflows/angular-demos.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'demo/angular/**'
      - 'demo/angular-stt/**'
      - '!demo/angular/README.md'
      - '!demo/angular-stt/README.md'
      - '.github/workflows/angular-demos.yml'

defaults:
  run:
    working-directory: demo/angular

jobs:
  build-demos:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install

    - name: Build
      run: yarn build en

    - name: Build another language
      run: yarn build ja

  build-stt-demo:
    runs-on: ubuntu-latest
    defaults:
      run:
        working-directory: demo/angular-stt

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js LTS
      uses: actions/setup-node@v3
      with:
        node-version: lts/*

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install

    - name: Build
      run: yarn build


Angular

name: Angular

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'binding/angular/**'
      - '!binding/angular/README.md'
      - 'lib/common/**'
      - 'lib/wasm/**'
      - 'resources/**'
      - '!resources/.lint/**'
      - '.github/workflows/angular.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'binding/angular/**'
      - '!binding/angular/README.md'
      - 'lib/common/**'
      - 'lib/wasm/**'
      - 'resources/**'
      - '!resources/.lint/**'
      - '.github/workflows/angular.yml'

defaults:
  run:
    working-directory: binding/angular

jobs:
  build:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install

    - name: Build
      run: yarn build porcupine-angular

    - name: Set up test
      run: yarn setup-test

    - name: Run test
      run: yarn test --env ACCESS_KEY=${{secrets.PV_VALID_ACCESS_KEY}}


C Codestyle

name: C Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '**/*.c'
      - '.github/workflows/c-codestyle.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '**/*.c'
      - '.github/workflows/c-codestyle.yml'

jobs:
  check-c-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up Python 3.10
      uses: actions/setup-python@v4
      with:
        python-version: '3.10'

    - name: Install dependencies
      run: sudo apt install clang-format

    - name: Check c codestyle
      run: python3 resources/.lint/c/formatter.py -c -v


C Demos

name: C Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '!demo/c/README.md'
      - '.github/workflows/c-demos.yml'
      - 'demo/c/**'
      - 'lib/beaglebone/**'
      - 'lib/common/**'
      - 'lib/jetson/**'
      - 'lib/linux/**'
      - 'lib/mac/**'
      - 'lib/raspberry-pi/**'
      - 'lib/windows/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '!demo/c/README.md'
      - '.github/workflows/c-demos.yml'
      - 'demo/c/**'
      - 'lib/beaglebone/**'
      - 'lib/common/**'
      - 'lib/jetson/**'
      - 'lib/linux/**'
      - 'lib/mac/**'
      - 'lib/raspberry-pi/**'
      - 'lib/windows/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'

defaults:
  run:
    working-directory: demo/c

jobs:
  build-micdemo-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]

    steps:
    - uses: actions/checkout@v3
      with:
        submodules: recursive

    - name: Create build directory
      run: cmake -B ./build

    - name: Build micdemo
      run: cmake --build ./build --target porcupine_demo_mic

  build-micdemo-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]

    steps:
    - uses: actions/checkout@v3
      with:
        submodules: recursive

    - name: Create build directory
      run: cmake -B ./build

    - name: Build micdemo
      run: cmake --build ./build --target porcupine_demo_mic

  build-filedemo-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]
        include:
        - os: ubuntu-latest
          platform: linux
          arch: x86_64
        - os: windows-latest
          platform: windows
          arch: amd64
        - os: macos-latest
          platform: mac
          arch: x86_64

    steps:
    - uses: actions/checkout@v3
      with:
        submodules: recursive

    - name: Set up Python '3.10'
      uses: actions/setup-python@v4
      with:
        python-version: '3.10'

    - name: Create build directory
      run: cmake -B ./build

    - name: Build filedemo
      run: cmake --build ./build --target porcupine_demo_file

    - name: Install dependencies
      run: pip install -r test/requirements.txt

    - name: Test
      run: python test/test_porcupine_c.py ${{secrets.PV_VALID_ACCESS_KEY}} ${{ matrix.platform }} ${{ matrix.arch }}

  build-filedemo-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]
        include:
        - machine: rpi2
          platform: raspberry-pi
          arch: cortex-a7
        - machine: rpi3-32
          platform: raspberry-pi
          arch: cortex-a53
        - machine: rpi3-64
          platform: raspberry-pi
          arch: cortex-a53-aarch64
        - machine: rpi4-32
          platform: raspberry-pi
          arch: cortex-a72
        - machine: rpi4-64
          platform: raspberry-pi
          arch: cortex-a72-aarch64
        - machine: rpi5-64
          platform: raspberry-pi
          arch: cortex-a76-aarch64
        - machine: jetson
          platform: jetson
          arch: cortex-a57-aarch64
        - machine: beaglebone
          platform: beaglebone
          arch: ''

    steps:
    - uses: actions/checkout@v3
      with:
        submodules: recursive

    - name: Create build directory
      run: cmake -B ./build

    - name: Build filedemo
      run: cmake --build ./build --target porcupine_demo_file

    - name: Install dependencies
      run: pip install -r test/requirements.txt

    - name: Test
      run: python3 test/test_porcupine_c.py ${{secrets.PV_VALID_ACCESS_KEY}} ${{ matrix.platform }} ${{ matrix.arch }}


.NET Codestyle

name: .NET Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'binding/dotnet/**/*.cs'
      - 'demo/dotnet/**/*.cs'
      - 'demo/dotnet-vui/**/*.cs'
      - '.github/workflows/dotnet-codestyle.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'binding/dotnet/**/*.cs'
      - 'demo/dotnet/**/*.cs'
      - 'demo/dotnet-vui/**/*.cs'
      - '.github/workflows/dotnet-codestyle.yml'

jobs:
  check-dotnet-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up .NET 6.0
      uses: actions/setup-dotnet@v3
      with:
        dotnet-version: 6.0.x

    - name: Run Binding Codestyle
      run: dotnet format --verify-no-changes
      working-directory: binding/dotnet

    - name: Run Demo Codestyle
      run: dotnet format --verify-no-changes
      working-directory: demo/dotnet

    - name: Run Demo-vui Codestyle
      run: dotnet format --verify-no-changes
      working-directory: demo/dotnet-vui


.NET Demos

name: .NET Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'demo/dotnet/**'
      - 'demo/dotnet-vui/**'
      - '!demo/dotnet/README.md'
      - '!demo/dotnet-vui/README.md'
      - '.github/workflows/dotnet-demos.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'demo/dotnet/**'
      - 'demo/dotnet-vui/**'
      - '!demo/dotnet/README.md'
      - '!demo/dotnet-vui/README.md'
      - '.github/workflows/dotnet-demos.yml'

defaults:
  run:
    working-directory: demo/dotnet/PorcupineDemo

jobs:
  build-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]

    steps:
    - uses: actions/checkout@v3

    - name: Set up .NET 6.0
      uses: actions/setup-dotnet@v3
      with:
        dotnet-version: 6.0.x

    - name: Package restore
      run: dotnet restore

    - name: Dotnet build micdemo
      run: dotnet build -c MicDemo.Release

    - name: Dotnet build filedemo
      run: dotnet build -c FileDemo.Release

    - name: Run Dotnet filedemo
      run: dotnet run -c FileDemo.Release -- --input_audio_path ../../../resources/audio_samples/multiple_keywords.wav --access_key ${{secrets.PV_VALID_ACCESS_KEY}} --keywords picovoice

  build-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]

    steps:
    - uses: actions/checkout@v3

    - name: Package restore
      run: dotnet restore

    - name: Dotnet build micdemo
      run: dotnet build -c MicDemo.Release

    - name: Dotnet build filedemo
      run: dotnet build -c FileDemo.Release

    - name: Run Dotnet filedemo
      run: dotnet run -c FileDemo.Release -- --input_audio_path ../../../resources/audio_samples/multiple_keywords.wav --access_key ${{secrets.PV_VALID_ACCESS_KEY}} --keywords picovoice

  build-vui-demo:
    runs-on: ${{ matrix.os }}
    defaults:
      run:
        working-directory: demo/dotnet-vui/AvaloniaVUI

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]

    steps:
    - uses: actions/checkout@v3

    - name: Set up .NET 6.0
      uses: actions/setup-dotnet@v3
      with:
        dotnet-version: 6.0.x

    - name: Package restore
      run: dotnet restore

    - name: Dotnet build
      run: dotnet build


.NET

name: .NET

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'binding/dotnet/**'
      - '!binding/dotnet/README.md'
      - 'lib/beaglebone/**'
      - 'lib/common/**'
      - 'lib/linux/**'
      - 'lib/jetson/**'
      - 'lib/mac/**'
      - 'lib/raspberry-pi/**'
      - 'lib/windows/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
      - '.github/workflows/dotnet.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'binding/dotnet/**'
      - '!binding/dotnet/README.md'
      - 'lib/beaglebone/**'
      - 'lib/common/**'
      - 'lib/linux/**'
      - 'lib/jetson/**'
      - 'lib/mac/**'
      - 'lib/raspberry-pi/**'
      - 'lib/windows/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
      - '.github/workflows/dotnet.yml'

defaults:
  run:
    working-directory: binding/dotnet

jobs:
  build-github-hosted:
    runs-on: ${{ matrix.os }}
    env:
      ACCESS_KEY: ${{secrets.PV_VALID_ACCESS_KEY}}

    strategy:
      matrix:
        os: [ubuntu-latest, macos-latest, windows-latest]
        dotnet-version: [2.1.x, 3.0.x, 3.1.x, 5.0.x, 6.0.x]
        include:
          - dotnet-version: 2.1.x
            binding-framework: netstandard2.0
            test-framework: netcoreapp2.1
          - dotnet-version: 3.0.x
            binding-framework: netcoreapp3.0
            test-framework: netcoreapp3.0
          - dotnet-version: 3.1.x
            binding-framework: netcoreapp3.0
            test-framework: netcoreapp3.1
          - dotnet-version: 5.0.x
            binding-framework: netcoreapp3.0
            test-framework: net5.0
          - dotnet-version: 6.0.x
            binding-framework: net6.0
            test-framework: net6.0

    steps:
    - uses: actions/checkout@v3

    - name: Set up .NET
      uses: actions/setup-dotnet@v3
      with:
        dotnet-version: ${{ matrix.dotnet-version }}

    - name: Build binding
      run: dotnet build Porcupine/Porcupine.csproj --framework ${{ matrix.binding-framework }}

    - name: Test
      run: dotnet test --framework ${{ matrix.test-framework }} -v n

  build-self-hosted:
    runs-on: ${{ matrix.machine }}
    env:
      ACCESS_KEY: ${{secrets.PV_VALID_ACCESS_KEY}}

    strategy:
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]

    steps:
    - uses: actions/checkout@v3

    - name: Build binding
      run: dotnet build Porcupine/Porcupine.csproj --framework net6.0

    - name: Test
      run: dotnet test --framework net6.0 -v n


Flutter Codestyle

name: Flutter Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '**/*.dart'
      - '.github/workflows/flutter-codestyle.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '**/*.dart'
      - '.github/workflows/flutter-codestyle.yml'

jobs:
  check-flutter-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Install Flutter 2.8.1
      uses: subosito/flutter-action@v2
      with:
        flutter-version: 2.8.1

    - name: Run Binding Analyzer
      run: flutter analyze --no-fatal-infos --no-fatal-warnings
      working-directory: binding/flutter

    - name: Run Demo Analyzer
      run: flutter analyze --no-fatal-infos --no-fatal-warnings
      working-directory: demo/flutter


Flutter Demos

name: Flutter Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/flutter-demos.yml'
      - 'demo/flutter/**'
      - '!demo/flutter/README.md'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/flutter-demos.yml'
      - 'demo/flutter/**'
      - '!demo/flutter/README.md'

defaults:
  run:
    working-directory: demo/flutter

jobs:
  build-android:
    name: Build Android demo
    runs-on: ubuntu-latest
    strategy:
      matrix:
        flutter-version: ['2.8.1', '3.0.4']

    steps:
    - uses: actions/checkout@v3

    - name: Set up JDK 11
      uses: actions/setup-java@v3
      with:
        java-version: '11'
        distribution: 'temurin'

    - name: Install Flutter ${{ matrix.flutter-version }}
      uses: subosito/flutter-action@v2
      with:
        flutter-version: ${{ matrix.flutter-version }}

    - name: Install dependencies
      run: flutter pub get

    - name: Prepare demo
      run: dart scripts/prepare_demo.dart en

    - name: Build
      run: flutter build apk

  build-ios:
    name: Build iOS demo
    runs-on: macos-11
    strategy:
      matrix:
        flutter-version: ['2.8.1', '3.0.4']

    steps:
    - uses: actions/checkout@v3

    - name: Install Flutter ${{ matrix.flutter-version }}
      uses: subosito/flutter-action@v2
      with:
        flutter-version: ${{ matrix.flutter-version }}
        architecture: x64

    - name: Update Cocoapods repo
      run: pod repo update

    - name: Install dependencies
      run: flutter pub get

    - name: Prepare demo
      run: dart scripts/prepare_demo.dart en

    - name: Build
      run: flutter build ios --release --no-codesign


Flutter Tests

name: Flutter Tests

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/flutter.yml'
      - 'demo/flutter/pubspec.yaml'
      - 'lib/common/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/android/**'
      - 'resources/keyword_files*/ios/**'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/flutter.yml'
      - 'demo/flutter/pubspec.yaml'
      - 'lib/common/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/android/**'
      - 'resources/keyword_files*/ios/**'

defaults:
  run:
    working-directory: demo/flutter

jobs:
  test-android:
    name: Test Android
    runs-on: pv-android

    steps:
    - uses: actions/checkout@v3

    - name: Copy test_resources
      run: ./copy_test_resources.sh

    - name: Inject AppID
      run: sed -i 's:{TESTING_ACCESS_KEY_HERE}:${{secrets.PV_VALID_ACCESS_KEY}}:'
        integration_test/app_test.dart

    - name: Install dependencies
      run: flutter pub get

    - name: Prepare demo
      run: dart scripts/prepare_demo.dart en

    - name: Run integration tests
      run: flutter test integration_test

  test-ios:
    name: Test iOS
    runs-on: pv-ios

    steps:
    - uses: actions/checkout@v3

    - name: Copy test_resources
      run: ./copy_test_resources.sh

    - name: Inject AppID
      run: sed -i '.bak' 's:{TESTING_ACCESS_KEY_HERE}:${{secrets.PV_VALID_ACCESS_KEY}}:'
        integration_test/app_test.dart

    - name: Update Cocoapods repo
      run: pod repo update

    - name: Install dependencies
      run: flutter pub get

    - name: Prepare demo
      run: dart scripts/prepare_demo.dart en

    - name: Run integration tests
      run: flutter test integration_test


Go Codestyle

name: Go Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '**/*.go'
      - '.github/workflows/go-codestyle.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '**/*.go'
      - '.github/workflows/go-codestyle.yml'

jobs:
  check-go-binding-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up go
      uses: actions/setup-go@v4
      with:
        go-version: 1.18

    - name: golangci-lint
      uses: golangci/golangci-lint-action@v3
      with:
        working-directory: binding/go

  check-go-micdemo-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up go
      uses: actions/setup-go@v4
      with:
        go-version: 1.18

    - name: golangci-lint
      uses: golangci/golangci-lint-action@v3
      with:
        working-directory: demo/go/micdemo

  check-go-filedemo-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up go
      uses: actions/setup-go@v4
      with:
        go-version: 1.18

    - name: golangci-lint
      uses: golangci/golangci-lint-action@v3
      with:
        working-directory: demo/go/filedemo


Go Demos

name: Go Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'demo/go/**'
      - '!demo/go/README.md'
      - '.github/workflows/go-demos.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'demo/go/**'
      - '!demo/go/README.md'
      - '.github/workflows/go-demos.yml'

defaults:
  run:
    working-directory: demo/go

jobs:
  build-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ ubuntu-latest, windows-latest, macos-latest ]
        go: [ '1.16', '1.17', '1.18', '1.19', '1.20', 'stable' ]

    steps:
    - uses: actions/checkout@v3

    - name: Set up Mingw
      uses: egor-tensin/setup-mingw@v2
      if: ${{ (matrix.os == 'windows-latest') && (matrix.go != 'stable') && (matrix.go < 1.20) }}
      with:
        version: 11.2.0

    - name: Set up go
      uses: actions/setup-go@v4
      with:
        go-version: ${{ matrix.go }}

    - name: Build micdemo
      run: go build micdemo/porcupine_mic_demo.go

    - name: Build filedemo
      run: go build filedemo/porcupine_file_demo.go

    - name: Test filedemo
      run: ./porcupine_file_demo -access_key ${{secrets.PV_VALID_ACCESS_KEY}} -input_audio_path ../../resources/audio_samples/multiple_keywords.wav -keywords picovoice

  build-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson ]

    steps:
    - uses: actions/checkout@v3

    - name: Build micdemo
      run: go build micdemo/porcupine_mic_demo.go

    - name: Build filedemo
      run: go build filedemo/porcupine_file_demo.go

    - name: Test filedemo
      run: ./porcupine_file_demo -access_key ${{secrets.PV_VALID_ACCESS_KEY}} -input_audio_path ../../resources/audio_samples/multiple_keywords.wav -keywords picovoice


Go

name: Go

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'binding/go/**'
      - '!binding/go/README.md'
      - 'lib/beaglebone/**'
      - 'lib/common/**'
      - 'lib/linux/**'
      - 'lib/jetson/**'
      - 'lib/mac/**'
      - 'lib/raspberry-pi/**'
      - 'lib/windows/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
      - '.github/workflows/go.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'binding/go/**'
      - '!binding/go/README.md'
      - 'lib/beaglebone/**'
      - 'lib/common/**'
      - 'lib/linux/**'
      - 'lib/jetson/**'
      - 'lib/mac/**'
      - 'lib/raspberry-pi/**'
      - 'lib/windows/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
      - '.github/workflows/go.yml'

defaults:
  run:
    working-directory: binding/go

jobs:
  build-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]
        go: [ '1.16', '1.17', '1.18', '1.19', '1.20', 'stable' ]

    steps:
    - uses: actions/checkout@v3

    - name: Set up Mingw
      uses: egor-tensin/setup-mingw@v2
      if: ${{ (matrix.os == 'windows-latest') && (matrix.go != 'stable') && (matrix.go < 1.20) }}
      with:
        version: 11.2.0

    - name: Set up go
      uses: actions/setup-go@v4
      with:
        go-version: ${{ matrix.go }}

    - name: Pre-build dependencies
      run: ./copy.sh

    - name: Install dependencies
      run: go get

    - name: Build
      run: go build

    - name: Test
      run: go test -v -access_key ${{secrets.PV_VALID_ACCESS_KEY}}

  build-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]

    steps:
    - uses: actions/checkout@v3

    - name: Pre-build dependencies
      run: ./copy.sh

    - name: Install dependencies
      run: go get

    - name: Build
      run: go build

    - name: Test
      run: go test -v -access_key ${{secrets.PV_VALID_ACCESS_KEY}}


iOS AppCenter Tests

name: iOS AppCenter Tests

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/ios-appcenter.yml'
      - 'binding/ios/PorcupineAppTest/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/ios-appcenter.yml'
      - 'binding/ios/PorcupineAppTest/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'

defaults:
  run:
    working-directory: binding/ios/PorcupineAppTest

jobs:
  build:
    name: Run iOS Tests on AppCenter
    runs-on: macos-latest

    steps:
      - name: Checkout
        uses: actions/checkout@v3

      - name: Set up Node.js LTS
        uses: actions/setup-node@v3
        with:
          node-version: lts/*

      - name: Install Cocoapods
        run: gem install cocoapods

      - name: Install AppCenter CLI
        run: npm install -g appcenter-cli

      - name: Make build dir
        run: mkdir ddp

      - name: Install resource script dependency
        run: |
          brew update
          brew install convmv

      - name: Copy test_resources
        run: ./copy_test_resources.sh

      - name: Run Cocoapods
        run: pod install

      - name: Inject AppID
        run: sed -i '.bak' 's:{TESTING_ACCESS_KEY_HERE}:${{secrets.PV_VALID_ACCESS_KEY}}:'
          PorcupineAppTestUITests/BaseTest.swift

      - name: XCode Build
        run: xcrun xcodebuild build-for-testing
          -configuration Debug
          -workspace PorcupineAppTest.xcworkspace
          -sdk iphoneos
          -scheme PorcupineAppTest
          -derivedDataPath ddp
          CODE_SIGNING_ALLOWED=NO

      - name: Run Tests on AppCenter
        run: appcenter test run xcuitest
          --token ${{secrets.APPCENTERAPITOKEN}}
          --app "Picovoice/Porcupine-iOS"
          --devices "Picovoice/ios-min-max"
          --test-series "porcupine-ios"
          --locale "en_US"
          --build-dir ddp/Build/Products/Debug-iphoneos


iOS Demos

name: iOS Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'demo/ios/**'
      - '.github/workflows/ios-demos.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'demo/ios/**'
      - '.github/workflows/ios-demos.yml'

jobs:
  build-foreground-app:
    runs-on: macos-latest
    defaults:
      run:
        working-directory: demo/ios/ForegroundApp

    steps:
      - name: Checkout
        uses: actions/checkout@v3

      - name: Set up Node.js LTS
        uses: actions/setup-node@v3
        with:
          node-version: lts/*

      - name: Install Cocoapods
        run: gem install cocoapods

      - name: Install AppCenter CLI
        run: npm install -g appcenter-cli

      - name: Make build dir
        run: mkdir ddp

      - name: Run Cocoapods
        run: pod install

      - name: Build English
        run: xcrun xcodebuild build
          -configuration Debug
          -workspace PorcupineForegroundAppDemo.xcworkspace
          -sdk iphoneos
          -scheme _enDemo
          -derivedDataPath ddp
          CODE_SIGNING_ALLOWED=NO

      - name: Build Other Language
        run: xcrun xcodebuild build
          -configuration Debug
          -workspace PorcupineForegroundAppDemo.xcworkspace
          -sdk iphoneos
          -scheme deDemo
          -derivedDataPath ddp
          CODE_SIGNING_ALLOWED=NO

  build-background-service:
    runs-on: macos-latest
    defaults:
      run:
        working-directory: demo/ios/BackgroundService

    steps:
      - name: Checkout
        uses: actions/checkout@v3

      - name: Set up Node.js LTS
        uses: actions/setup-node@v3
        with:
          node-version: lts/*

      - name: Install Cocoapods
        run: gem install cocoapods

      - name: Install AppCenter CLI
        run: npm install -g appcenter-cli

      - name: Make build dir
        run: mkdir ddp

      - name: Run Cocoapods
        run: pod install

      - name: Build
        run: xcrun xcodebuild build
          -configuration Debug
          -workspace PorcupineBackgroundServiceDemo.xcworkspace
          -sdk iphoneos
          -scheme PorcupineBackgroundServiceDemo
          -derivedDataPath ddp
          CODE_SIGNING_ALLOWED=NO


iOS Performance

name: iOS Performance

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'lib/ios/**'
      - 'lib/common/**'
      - 'resources/keyword_files/ios/**'
      - '.github/workflows/ios-perf.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'lib/ios/**'
      - 'lib/common/**'
      - 'resources/keyword_files/ios/**'
      - '.github/workflows/ios-perf.yml'

defaults:
  run:
    working-directory: binding/ios/PorcupineAppTest

jobs:
  build:
    name: Run iOS Tests on AppCenter
    runs-on: macos-latest

    strategy:
      matrix:
        device: [ios-perf]
        include:
        - device: ios-perf
          performanceThresholdSec: 0.5

    steps:
      - name: Checkout
        uses: actions/checkout@v3

      - name: Set up Node.js LTS
        uses: actions/setup-node@v3
        with:
          node-version: lts/*

      - name: Install Cocoapods
        run: gem install cocoapods

      - name: Install AppCenter CLI
        run: npm install -g appcenter-cli

      - name: Make build dir
        run: mkdir ddp

      - name: Install resource script dependency
        run: |
          brew update
          brew install convmv

      - name: Copy test_resources
        run: ./copy_test_resources.sh

      - name: Run Cocoapods
        run: pod install

      - name: Inject AppID
        run: sed -i '.bak' 's:{TESTING_ACCESS_KEY_HERE}:${{secrets.PV_VALID_ACCESS_KEY}}:'
          PerformanceTest/PerformanceTest.swift

      - name: Inject Number of Iterations
        run: sed -i '.bak' 's:{NUM_TEST_ITERATIONS}:100:'
          PerformanceTest/PerformanceTest.swift

      - name: Inject Performance Threshold
        run: sed -i '.bak' 's:{PERFORMANCE_THRESHOLD_SEC}:${{ matrix.performanceThresholdSec }}:'
          PerformanceTest/PerformanceTest.swift

      - name: XCode Build
        run: xcrun xcodebuild build-for-testing
          -configuration Debug
          -workspace PorcupineAppTest.xcworkspace
          -sdk iphoneos
          -scheme PerformanceTest
          -derivedDataPath ddp
          CODE_SIGNING_ALLOWED=NO

      - name: Run Tests on AppCenter
        run: appcenter test run xcuitest
          --token ${{secrets.APPCENTERAPITOKEN}}
          --app "Picovoice/Porcupine-iOS"
          --devices "Picovoice/${{ matrix.device }}"
          --test-series "porcupine-ios"
          --locale "en_US"
          --build-dir ddp/Build/Products/Debug-iphoneos


Java CodeStyle

name: Java CodeStyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '**/*.java'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '**/*.java'

jobs:
  check-java-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up JDK 11
      uses: actions/setup-java@v3
      with:
        java-version: '11'
        distribution: 'temurin'

    - name: Check Java CodeStyle
      run: java -Dconfig_loc=resources/.lint/java/ -jar resources/.lint/java/checkstyle-10.5.0-all.jar -c resources/.lint/java/checkstyle.xml binding/android/ binding/java/ binding/flutter/android/ binding/react-native/android/ demo/android/ demo/java/


Java Demos

name: Java Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/java-demos.yml'
      - 'demo/java/**'
      - '!demo/java/README.md'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/java-demos.yml'
      - 'demo/java/**'
      - '!demo/java/README.md'

defaults:
  run:
    working-directory: demo/java

jobs:
  build-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]

    steps:
    - uses: actions/checkout@v3

    - name: Set up JDK 11
      uses: actions/setup-java@v3
      with:
        java-version: '11'
        distribution: 'temurin'

    - name: Build
      run: ./gradlew build

    - name: Run filedemo
      run: java -jar build/libs/porcupine-file-demo.jar -a  ${{secrets.PV_VALID_ACCESS_KEY}} -i ../../resources/audio_samples/multiple_keywords.wav -k picovoice

  build-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]

    steps:
    - uses: actions/checkout@v3

    - name: Build
      run: ./gradlew build

    - name: Run filedemo
      run: java -jar build/libs/porcupine-file-demo.jar -a  ${{secrets.PV_VALID_ACCESS_KEY}} -i ../../resources/audio_samples/multiple_keywords.wav -k picovoice


Java Performance

name: Java Performance

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/java-perf.yml'
      - 'binding/java/**/PorcupinePerformanceTest.java'
      - 'lib/common/**'
      - 'lib/java/**'
      - 'resources/keyword_files/beaglebone/**'
      - 'resources/keyword_files/jetson/**'
      - 'resources/keyword_files/linux/**'
      - 'resources/keyword_files/mac/**'
      - 'resources/keyword_files/raspberry-pi/**'
      - 'resources/keyword_files/windows/**'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/java-perf.yml'
      - 'lib/common/**'
      - 'lib/java/**'
      - 'resources/keyword_files/beaglebone/**'
      - 'resources/keyword_files/jetson/**'
      - 'resources/keyword_files/linux/**'
      - 'resources/keyword_files/mac/**'
      - 'resources/keyword_files/raspberry-pi/**'
      - 'resources/keyword_files/windows/**'

defaults:
  run:
    working-directory: binding/java

jobs:
  perf-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      fail-fast: false
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]
        include:
        - os: ubuntu-latest
          performance_threshold_sec: 0.5
        - os: windows-latest
          performance_threshold_sec: 0.5
        - os: macos-latest
          performance_threshold_sec: 0.5

    steps:
    - uses: actions/checkout@v3

    - name: Set up JDK 11
      uses: actions/setup-java@v3
      with:
        java-version: '11'
        distribution: 'temurin'

    - name: Build
      run: ./gradlew assemble

    - name: Test
      run: ./gradlew test --info --tests PorcupinePerformanceTest -DpvTestingAccessKey="${{secrets.PV_VALID_ACCESS_KEY}}" -DnumTestIterations="100" -DperformanceThresholdSec="${{matrix.performance_threshold_sec}}"

  perf-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      fail-fast: false
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]
        include:
        - machine: rpi2
          num_test_iterations: 20
          performance_threshold_sec: 5.5
        - machine: rpi3-32
          num_test_iterations: 50
          performance_threshold_sec: 2.0
        - machine: rpi3-64
          num_test_iterations: 50
          performance_threshold_sec: 2.5
        - machine: rpi4-32
          num_test_iterations: 50
          performance_threshold_sec: 1.5
        - machine: rpi4-64
          num_test_iterations: 50
          performance_threshold_sec: 1.5
        - machine: rpi5-64
          num_test_iterations: 50
          performance_threshold_sec: 1.0
        - machine: jetson
          num_test_iterations: 50
          performance_threshold_sec: 2.0
        - machine: beaglebone
          num_test_iterations: 10
          performance_threshold_sec: 20.0

    steps:
    - uses: actions/checkout@v3

    - name: Build
      run: ./gradlew assemble

    - name: Machine state before
      working-directory: resources/scripts
      run: bash machine-state.sh

    - name: Test
      run: ./gradlew test --info --tests PorcupinePerformanceTest -DpvTestingAccessKey="${{secrets.PV_VALID_ACCESS_KEY}}" -DnumTestIterations="${{matrix.num_test_iterations}}" -DperformanceThresholdSec="${{matrix.performance_threshold_sec}}"

    - name: Machine state after
      working-directory: resources/scripts
      run: bash machine-state.sh


Java

name: Java

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/java.yml'
      - 'binding/java/**'
      - '!binding/java/README.md'
      - 'lib/common/**'
      - 'lib/java/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
      - 'resources/.test/**'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/java.yml'
      - 'binding/java/**'
      - '!binding/java/README.md'
      - 'lib/common/**'
      - 'lib/java/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
      - 'resources/.test/**'

defaults:
  run:
    working-directory: binding/java

jobs:
  build-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]

    steps:
    - uses: actions/checkout@v3

    - name: Set up JDK 11
      uses: actions/setup-java@v3
      with:
        java-version: '11'
        distribution: 'temurin'

    - name: Build
      run: ./gradlew assemble

    - name: Test
      run: ./gradlew test --info --tests PorcupineTest -DpvTestingAccessKey="${{secrets.PV_VALID_ACCESS_KEY}}"

  build-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]

    steps:
    - uses: actions/checkout@v3

    - name: Build
      run: ./gradlew assemble

    - name: Test
      run: ./gradlew test --info --tests PorcupineTest -DpvTestingAccessKey="${{secrets.PV_VALID_ACCESS_KEY}}"


Check Markdown links

name: Check Markdown links

on:
  workflow_dispatch:
  push:
    branches: [ master ]
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]

jobs:
  markdown-link-check:
    runs-on: ubuntu-latest
    steps:
    - uses: actions/checkout@master
    - uses: gaurav-nelson/github-action-markdown-link-check@1.0.14
      with:
        use-quiet-mode: 'yes'
        use-verbose-mode: 'yes'


Node.js Codestyle

name: Node.js Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '**/nodejs/*.js'
      - '**/nodejs/*.ts'
      - '.github/workflows/nodejs-codestyle.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '**/nodejs/*.js'
      - '**/nodejs/*.ts'
      - '.github/workflows/nodejs-codestyle.yml'

jobs:
  check-nodejs-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js LTS
      uses: actions/setup-node@v3
      with:
        node-version: lts/*

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Run Binding Linter
      run: yarn && yarn lint
      working-directory: binding/nodejs


Node.js Demos

name: Node.js Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'demo/nodejs/**'
      - '!demo/nodejs/README.md'
      - 'lib/node/**'
      - '.github/workflows/nodejs-demos.yml'

  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'demo/nodejs/**'
      - '!demo/nodejs/README.md'
      - 'lib/node/**'
      - '.github/workflows/nodejs-demos.yml'

defaults:
  run:
    working-directory: demo/nodejs

jobs:
  build-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Use Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Install dependencies
      run: yarn install

    - name: Test
      run: yarn file -a ${{secrets.PV_VALID_ACCESS_KEY}} -i ../../resources/audio_samples/multiple_keywords.wav -k picovoice

  build-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]

    steps:
    - uses: actions/checkout@v3

    - name: Install dependencies
      run: yarn install

    - name: Test
      run: yarn file -a ${{secrets.PV_VALID_ACCESS_KEY}} -i ../../resources/audio_samples/multiple_keywords.wav -k picovoice


Node.js Performance

name: Node.js Performance

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/nodejs-perf.yml'
      - 'lib/node/**'
      - 'lib/common/**'
      - 'resources/keyword_files/beaglebone/**'
      - 'resources/keyword_files/jetson/**'
      - 'resources/keyword_files/linux/**'
      - 'resources/keyword_files/mac/**'
      - 'resources/keyword_files/raspberry-pi/**'
      - 'resources/keyword_files/windows/**'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/nodejs-perf.yml'
      - 'lib/node/**'
      - 'lib/common/**'
      - 'resources/keyword_files/beaglebone/**'
      - 'resources/keyword_files/jetson/**'
      - 'resources/keyword_files/linux/**'
      - 'resources/keyword_files/mac/**'
      - 'resources/keyword_files/raspberry-pi/**'
      - 'resources/keyword_files/windows/**'

defaults:
  run:
    working-directory: binding/nodejs

jobs:
  performance-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      fail-fast: false
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]
        include:
        - os: ubuntu-latest
          performance_threshold_sec: 0.5
        - os: windows-latest
          performance_threshold_sec: 0.5
        - os: macos-latest
          performance_threshold_sec: 0.75

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js '18.x'
      uses: actions/setup-node@v3
      with:
        node-version: '18.x'

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install

    - name: Test
      run: yarn test test/perf.test.ts --access_key=${{secrets.PV_VALID_ACCESS_KEY}} --num_test_iterations=100 --performance_threshold_sec=${{matrix.performance_threshold_sec}}

  performance-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      fail-fast: false
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]
        include:
        - machine: rpi2
          num_test_iterations: 20
          performance_threshold_sec: 5.5
        - machine: rpi3-32
          num_test_iterations: 50
          performance_threshold_sec: 2.0
        - machine: rpi3-64
          num_test_iterations: 50
          performance_threshold_sec: 2.5
        - machine: rpi4-32
          num_test_iterations: 50
          performance_threshold_sec: 1.5
        - machine: rpi4-64
          num_test_iterations: 50
          performance_threshold_sec: 1.5
        - machine: rpi5-64
          num_test_iterations: 50
          performance_threshold_sec: 0.5
        - machine: jetson
          num_test_iterations: 50
          performance_threshold_sec: 2.0
        - machine: beaglebone
          num_test_iterations: 10
          performance_threshold_sec: 20.0

    steps:
    - uses: actions/checkout@v3

    - name: Pre-build dependencies
      run: npm install --global yarn

    - name: Install dependencies
      run: yarn install

    - name: Machine state before
      working-directory: resources/scripts
      run: bash machine-state.sh

    - name: Test
      run: yarn test test/perf.test.ts --access_key=${{secrets.PV_VALID_ACCESS_KEY}} --num_test_iterations=${{matrix.num_test_iterations}} --performance_threshold_sec=${{matrix.performance_threshold_sec}}

    - name: Machine state after
      working-directory: resources/scripts
      run: bash machine-state.sh


Node.js

name: Node.js

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/nodejs.yml'
      - 'binding/nodejs/**'
      - '!binding/nodejs/README.md'
      - 'lib/node/**'
      - 'lib/common/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
      - 'resources/test/**'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/nodejs.yml'
      - 'binding/nodejs/**'
      - '!binding/nodejs/README.md'
      - 'lib/node/**'
      - 'lib/common/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
      - 'resources/test/**'

defaults:
  run:
    working-directory: binding/nodejs

jobs:
  build-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install

    - name: Test
      run: yarn test test/index.test.ts --access_key=${{secrets.PV_VALID_ACCESS_KEY}}

  build-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]

    steps:
    - uses: actions/checkout@v3

    - name: Pre-build dependencies
      run: npm install --global yarn

    - name: Install dependencies
      run: yarn install

    - name: Test
      run: yarn test test/index.test.ts --access_key=${{secrets.PV_VALID_ACCESS_KEY}}


Python Codestyle

name: Python Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'binding/python/*.py'
      - 'demo/python/*.py'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'binding/python/*.py'
      - 'demo/python/*.py'

jobs:
  check-python-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up Python 3.10
      uses: actions/setup-python@v4
      with:
        python-version: '3.10'

    - name: Install dependencies
      run: pip install flake8 pep8-naming

    - name: Check python codestyle
      run: flake8 --ignore=F401,F403,F405 --max-line-length=120 binding/python demo/python


Python Demos

name: Python Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/python-demos.yml'
      - 'demo/python/**'
      - '!demo/python/README.md'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/python-demos.yml'
      - 'demo/python/**'
      - '!demo/python/README.md'

defaults:
  run:
    working-directory: demo/python

jobs:
  build-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]
        python-version: ['3.8', '3.9', '3.10', '3.11', '3.12']

    steps:
    - uses: actions/checkout@v3

    - name: Set up Python ${{ matrix.python-version }}
      uses: actions/setup-python@v4
      with:
        python-version: ${{ matrix.python-version }}

    - name: Pre-build dependencies
      run: python -m pip install --upgrade pip

    - name: Install dependencies
      run: pip install -r requirements.txt

    - name: Test
      run: python porcupine_demo_file.py --access_key ${{secrets.PV_VALID_ACCESS_KEY}} --wav_path ../../resources/audio_samples/multiple_keywords.wav --keywords picovoice

  build-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]

    steps:
    - uses: actions/checkout@v3

    - name: Install dependencies
      run: pip3 install -r requirements.txt

    - name: Test
      run: python3 porcupine_demo_file.py --access_key ${{secrets.PV_VALID_ACCESS_KEY}} --wav_path ../../resources/audio_samples/multiple_keywords.wav --keywords picovoice


Python Perfomance

name: Python Perfomance

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/python-perf.yml'
      - 'binding/python/test_porcupine_perf.py'
      - 'lib/beaglebone/**'
      - 'lib/common/**'
      - 'lib/jetson/**'
      - 'lib/linux/**'
      - 'lib/mac/**'
      - 'lib/raspberry-pi/**'
      - 'lib/windows/**'
      - 'resources/keyword_files/beaglebone/**'
      - 'resources/keyword_files/jetson/**'
      - 'resources/keyword_files/linux/**'
      - 'resources/keyword_files/mac/**'
      - 'resources/keyword_files/raspberry-pi/**'
      - 'resources/keyword_files/windows/**'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/python-perf.yml'
      - 'binding/python/test_porcupine_perf.py'
      - 'lib/beaglebone/**'
      - 'lib/common/**'
      - 'lib/jetson/**'
      - 'lib/linux/**'
      - 'lib/mac/**'
      - 'lib/raspberry-pi/**'
      - 'lib/windows/**'
      - 'resources/keyword_files/beaglebone/**'
      - 'resources/keyword_files/jetson/**'
      - 'resources/keyword_files/linux/**'
      - 'resources/keyword_files/mac/**'
      - 'resources/keyword_files/raspberry-pi/**'
      - 'resources/keyword_files/windows/**'

defaults:
  run:
    working-directory: binding/python

jobs:
  perf-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      fail-fast: false
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]
        include:
        - os: ubuntu-latest
          performance_threshold_sec: 0.5
        - os: windows-latest
          performance_threshold_sec: 0.5
        - os: macos-latest
          performance_threshold_sec: 0.65

    steps:
    - uses: actions/checkout@v3

    - name: Set up Python '3.10'
      uses: actions/setup-python@v4
      with:
        python-version: '3.10'

    - name: Test
      run: python test_porcupine_perf.py ${{secrets.PV_VALID_ACCESS_KEY}} 100 ${{matrix.performance_threshold_sec}}

  perf-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      fail-fast: false
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, jetson, beaglebone]
        include:
        - machine: rpi2
          num_test_iterations: 20
          performance_threshold_sec: 7.6
        - machine: rpi3-32
          num_test_iterations: 50
          performance_threshold_sec: 3.2
        - machine: rpi3-64
          num_test_iterations: 50
          performance_threshold_sec: 3.5
        - machine: rpi4-32
          num_test_iterations: 50
          performance_threshold_sec: 1.5
        - machine: rpi4-64
          num_test_iterations: 50
          performance_threshold_sec: 1.5
        - machine: rpi5-64
          num_test_iterations: 50
          performance_threshold_sec: 0.5
        - machine: jetson
          num_test_iterations: 50
          performance_threshold_sec: 2.0
        - machine: beaglebone
          num_test_iterations: 10
          performance_threshold_sec: 12.0

    steps:
    - uses: actions/checkout@v3

    - name: Machine state before
      working-directory: resources/scripts
      run: bash machine-state.sh

    - name: Test
      run: python3 test_porcupine_perf.py ${{secrets.PV_VALID_ACCESS_KEY}} ${{matrix.num_test_iterations}} ${{matrix.performance_threshold_sec}}

    - name: Machine state after
      working-directory: resources/scripts
      run: bash machine-state.sh


Python

name: Python

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'binding/python/**'
      - '!binding/python/README.md'
      - 'lib/beaglebone/**'
      - 'lib/common/**'
      - 'lib/linux/**'
      - 'lib/jetson/**'
      - 'lib/mac/**'
      - 'lib/raspberry-pi/**'
      - 'lib/windows/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
      - 'resources/.test/**'
      - '.github/workflows/python.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'binding/python/**'
      - '!binding/python/README.md'
      - 'lib/beaglebone/**'
      - 'lib/common/**'
      - 'lib/linux/**'
      - 'lib/jetson/**'
      - 'lib/mac/**'
      - 'lib/raspberry-pi/**'
      - 'lib/windows/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
      - 'resources/.test/**'
      - '.github/workflows/python.yml'

defaults:
  run:
    working-directory: binding/python

jobs:
  build-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]
        python-version: ['3.8', '3.9', '3.10', '3.11', '3.12']

    steps:
    - uses: actions/checkout@v3

    - name: Set up Python ${{ matrix.python-version }}
      uses: actions/setup-python@v4
      with:
        python-version: ${{ matrix.python-version }}

    - name: Install dependencies
      run: pip install -r requirements.txt

    - name: Test
      run: python test_porcupine.py ${{secrets.PV_VALID_ACCESS_KEY}}

  build-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi2, rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson, beaglebone]

    steps:
    - uses: actions/checkout@v3

    - name: Install dependencies
      run: pip install -r requirements.txt

    - name: Test
      run: python3 test_porcupine.py ${{secrets.PV_VALID_ACCESS_KEY}}


React Codestyle

name: React Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '**/react/*.js'
      - '**/react/*.ts'
      - '**/react/*.jsx'
      - '**/react/*.tsx'
      - '.github/workflows/react-codestyle.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '**/react/*.js'
      - '**/react/*.ts'
      - '**/react/*.jsx'
      - '**/react/*.tsx'
      - '.github/workflows/react-codestyle.yml'

jobs:
  check-react-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js LTS
      uses: actions/setup-node@v3
      with:
        node-version: lts/*

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Run Binding Linter
      run: yarn && yarn lint
      working-directory: binding/react

    - name: Run Demo Linter
      run: yarn && yarn lint
      working-directory: demo/react


React Demos

name: React Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'demo/react/**'
      - '!demo/react/README.md'
      - '.github/workflows/react-demos.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'demo/react/**'
      - '!demo/react/README.md'
      - '.github/workflows/react-demos.yml'

defaults:
  run:
    working-directory: demo/react

jobs:
  build:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install

    - name: Build English
      run: yarn build en

    - name: Build Other Language
      run: yarn build ko


React Native Codestyle

name: React Native Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '**/react-native/*.js'
      - '**/react-native/*.ts'
      - '**/react-native/*.jsx'
      - '**/react-native/*.tsx'
      - '.github/workflows/react-native-codestyle.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '**/react-native/*.js'
      - '**/react-native/*.ts'
      - '**/react-native/*.jsx'
      - '**/react-native/*.tsx'
      - '.github/workflows/react-native-codestyle.yml'

jobs:
  check-react-native-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js LTS
      uses: actions/setup-node@v3
      with:
        node-version: lts/*

    - name: Run Binding Linter
      run: yarn && yarn lint
      working-directory: binding/react-native

    - name: Run Demo Linter
      run: yarn && yarn lint
      working-directory: demo/react-native


React Native Demos

name: React Native Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'demo/react-native/**'
      - '!demo/react-native/README.md'
      - '.github/workflows/react-native-demos.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'demo/react-native/**'
      - '!demo/react-native/README.md'
      - '.github/workflows/react-native-demos.yml'

defaults:
  run:
    working-directory: demo/react-native

jobs:
  build-android:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Use Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Install dependencies
      run: yarn android-install

    - name: Build bundle
      run: yarn android-bundle pt

    - name: Build
      run: ./gradlew assembleDebug
      working-directory: demo/react-native/android

  build-ios:
    runs-on: macos-latest

    strategy:
      matrix:
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Use Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Install dependencies
      run: yarn ios-install

    - name: Build bundle
      run: yarn ios-bundle nl

    - name: Build
      run: xcrun xcodebuild build
        -configuration Debug
        -workspace PorcupineDemo.xcworkspace
        -sdk iphoneos
        -scheme PorcupineDemo
        -derivedDataPath ddp
        CODE_SIGNING_ALLOWED=NO
      working-directory: demo/react-native/ios


React Native Tests

name: React Native Tests
on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/react-native-tests.yml'
      - 'binding/react-native/**'
      - '!binding/react-native/README.md'
      - 'lib/common/**'
      - 'lib/android/**'
      - 'lib/ios/**'
      - 'resources/.test/test_data.json'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/android/**'
      - 'resources/keyword_files*/ios/**'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/react-native-tests.yml'
      - 'binding/react-native/**'
      - '!binding/react-native/README.md'
      - 'lib/common/**'
      - 'lib/android/**'
      - 'lib/ios/**'
      - 'resources/.test/test_data.json'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/android/**'
      - 'resources/keyword_files*/ios/**'

defaults:
  run:
    working-directory: binding/react-native/test-app/PorcupineTestApp

jobs:
  test-android:
    name: Run tests on Android
    runs-on: pv-android

    steps:
    - uses: actions/checkout@v3
      with:
        submodules: 'recursive'

    - name: Pre-build dependencies
      run: |
        yarn install
        ./copy_test_resources.sh

    - name: Inject AppID
      run: sed -i 's:{TESTING_ACCESS_KEY_HERE}:${{secrets.PV_VALID_ACCESS_KEY}}:' Tests.ts

    - name: Build tests
      run: detox build --configuration android.att.release

    - name: Run tests
      run: detox test --configuration android.att.release

  test-ios:
    name: Run tests on iOS
    runs-on: pv-ios

    steps:
    - uses: actions/checkout@v3
      with:
        submodules: 'recursive'

    - name: Pre-build dependencies
      run: |
        yarn install
        ./copy_test_resources.sh

    - name: Cocoapods install
      working-directory: binding/react-native/test-app/PorcupineTestApp/ios
      run: pod install --repo-update

    - name: Inject AppID
      run: sed -i '.bak' 's:{TESTING_ACCESS_KEY_HERE}:${{secrets.PV_VALID_ACCESS_KEY}}:' Tests.ts

    - name: Build tests
      run: detox build --configuration ios.sim.release

    - name: Run tests
      run: detox test --configuration ios.sim.release


React Native

name: React Native
on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'binding/react-native/**'
      - '!binding/react-native/README.md'
      - 'lib/common/**'
      - 'lib/android/**'
      - 'lib/ios/**'
      - 'resources/.test/test_data.json'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files/android/**'
      - 'resources/keyword_files/ios/**'
      - '.github/workflows/react-native.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'binding/react-native/**'
      - '!binding/react-native/README.md'
      - 'lib/common/**'
      - 'lib/android/**'
      - 'lib/ios/**'
      - 'resources/.test/test_data.json'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files/android/**'
      - 'resources/keyword_files/ios/**'
      - '.github/workflows/react-native.yml'

defaults:
  run:
    working-directory: binding/react-native

jobs:
  build:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install

    - name: Build
      run: yarn prepare


React

name: React

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'binding/react/**'
      - '!binding/react/README.md'
      - 'lib/common/**'
      - 'lib/wasm/**'
      - 'resources/**'
      - '!resources/.lint/**'
      - '.github/workflows/react.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'binding/react/**'
      - '!binding/react/README.md'
      - 'lib/common/**'
      - 'lib/wasm/**'
      - 'resources/**'
      - '!resources/.lint/**'
      - '.github/workflows/react.yml'

defaults:
  run:
    working-directory: binding/react

jobs:
  build:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install

    - name: Build
      run: yarn build

    - name: Set up test
      run: yarn setup-test

    - name: Run test
      run: yarn test --env ACCESS_KEY=${{secrets.PV_VALID_ACCESS_KEY}}


Rust Codestyle

name: Rust Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/rust-codestyle.yml'
      - 'binding/rust/**/*.rs'
      - 'demo/rust/**/*.rs'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/rust-codestyle.yml'
      - 'binding/rust/**/*.rs'
      - 'demo/rust/**/*.rs'

env:
  CARGO_TERM_COLOR: always

defaults:
  run:
    shell: bash

jobs:
  check-rust-binding-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Rust pre-build
      run: bash copy.sh
      working-directory: binding/rust

    - name: Rust dependencies
      if: matrix.os == 'ubuntu-latest'
      run: sudo apt install libasound2-dev -y

    - name: Install stable toolchain
      uses: actions-rs/toolchain@v1
      with:
        profile: minimal
        toolchain: stable
        override: true

    - name: Run clippy
      run: cargo clippy -- -D warnings
      working-directory: binding/rust

  check-rust-filedemo-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Rust dependencies
      if: matrix.os == 'ubuntu-latest'
      run: sudo apt install libasound2-dev -y

    - name: Install stable toolchain
      uses: actions-rs/toolchain@v1
      with:
        profile: minimal
        toolchain: stable
        override: true

    - name: Run clippy
      run: cargo clippy -- -D warnings
      working-directory: demo/rust/filedemo

  check-rust-micdemo-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Rust dependencies
      if: matrix.os == 'ubuntu-latest'
      run: sudo apt install libasound2-dev -y

    - name: Install stable toolchain
      uses: actions-rs/toolchain@v1
      with:
        profile: minimal
        toolchain: stable
        override: true

    - name: Run clippy
      run: cargo clippy -- -D warnings
      working-directory: demo/rust/micdemo


Rust Demos

name: Rust Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/rust-demos.yml'
      - 'demo/rust/**'
      - '!demo/rust/README.md'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/rust-demos.yml'
      - 'demo/rust/**'
      - '!demo/rust/README.md'

env:
  CARGO_TERM_COLOR: always

defaults:
  run:
    working-directory: demo/rust

jobs:
  build-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]

    steps:
    - uses: actions/checkout@v3

    - name: Rust dependencies
      if: matrix.os == 'ubuntu-latest'
      run: sudo apt install libasound2-dev -y

    - name: Install stable toolchain
      uses: actions-rs/toolchain@v1
      with:
        profile: minimal
        toolchain: stable
        override: true

    - name: Rust build micdemo
      run: cargo build --verbose
      working-directory: demo/rust/micdemo

    - name: Rust build filedemo
      run: cargo build --verbose
      working-directory: demo/rust/filedemo

    - name: Test
      run: cargo run --release -- --access_key ${{secrets.PV_VALID_ACCESS_KEY}} --input_audio_path ../../../resources/audio_samples/multiple_keywords.wav --keywords picovoice
      working-directory: demo/rust/filedemo

  build-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson]

    steps:
    - uses: actions/checkout@v3

    - name: Install stable toolchain
      uses: actions-rs/toolchain@v1
      with:
        toolchain: nightly
        override: true

    - name: Rust build micdemo
      run: cargo build --verbose
      working-directory: demo/rust/micdemo

    - name: Rust build filedemo
      run: cargo build --verbose
      working-directory: demo/rust/filedemo

    - name: Test
      run: cargo run --release -- --access_key ${{secrets.PV_VALID_ACCESS_KEY}} --input_audio_path ../../../resources/audio_samples/multiple_keywords.wav --keywords picovoice
      working-directory: demo/rust/filedemo


Rust

name: Rust

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '.github/workflows/rust.yml'
      - 'binding/rust/**'
      - 'binding/rust/**/*.rs'
      - '!binding/rust/README.md'
      - 'lib/beaglebone/**'
      - 'lib/common/**'
      - 'lib/linux/**'
      - 'lib/jetson/**'
      - 'lib/mac/**'
      - 'lib/raspberry-pi/**'
      - 'lib/windows/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
      - 'resources/.test/**'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '.github/workflows/rust.yml'
      - 'binding/rust/**'
      - 'binding/rust/**/*.rs'
      - '!binding/rust/README.md'
      - 'lib/beaglebone/**'
      - 'lib/common/**'
      - 'lib/linux/**'
      - 'lib/jetson/**'
      - 'lib/mac/**'
      - 'lib/raspberry-pi/**'
      - 'lib/windows/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/beaglebone/**'
      - 'resources/keyword_files*/jetson/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/raspberry-pi/**'
      - 'resources/keyword_files*/windows/**'
      - 'resources/.test/**'

env:
  CARGO_TERM_COLOR: always

defaults:
  run:
    working-directory: binding/rust
    shell: bash

jobs:
  build-github-hosted:
    runs-on: ${{ matrix.os }}

    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]

    steps:
    - uses: actions/checkout@v3

    - name: Rust pre-build
      run: bash copy.sh

    - name: Rust dependencies
      if: matrix.os == 'ubuntu-latest'
      run: sudo apt install libasound2-dev -y

    - name: Install stable toolchain
      uses: actions-rs/toolchain@v1
      with:
        profile: minimal
        toolchain: stable
        override: true

    - name: Rust build
      run: cargo build --verbose

    - name: Rust run tests
      run: PV_ACCESS_KEY=${{secrets.PV_VALID_ACCESS_KEY}} cargo test --verbose

  build-self-hosted:
    runs-on: ${{ matrix.machine }}

    strategy:
      matrix:
        machine: [rpi3-32, rpi3-64, rpi4-32, rpi4-64, rpi5-64, jetson]

    steps:
    - uses: actions/checkout@v3

    - name: Rust pre-build
      run: bash copy.sh

    - name: Install stable toolchain
      uses: actions-rs/toolchain@v1
      with:
        toolchain: nightly
        override: true

    - name: Rust build
      run: cargo build --verbose

    - name: Rust run tests
      run: PV_ACCESS_KEY=${{secrets.PV_VALID_ACCESS_KEY}} cargo test --verbose


SpellCheck

name: SpellCheck

on:
  workflow_dispatch:
  push:
    branches: [ master ]
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]

jobs:
  markdown:
    runs-on: ubuntu-20.04

    steps:
      - uses: actions/checkout@v3

      - uses: actions/setup-node@v3
        with:
          node-version: 18

      - name: Install CSpell
        run: npm install -g cspell

      - name: Run CSpell
        run: cspell --config resources/.lint/spell-check/.cspell.json "**/*"


Swift Codestyle

name: Swift Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '**/*.swift'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '**/*.swift'

jobs:
  check-switch-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Check swift codestyle
      uses: norio-nomura/action-swiftlint@3.2.1
      with:
        args: lint --config resources/.lint/swift/.swiftlint.yml --strict


Unity Codestyle

name: Unity Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'binding/unity/**/*.cs'
      - 'demo/unity/**/*.cs'
      - '.github/workflows/unity-codestyle.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'binding/unity/**/*.cs'
      - 'demo/unity/**/*.cs'
      - '.github/workflows/unity-codestyle.yml'

jobs:
  check-unity-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Run Binding Codestyle
      run: dotnet format whitespace binding/unity/Assets/Porcupine --folder --verify-no-changes

    - name: Run Demo Codestyle
      run: dotnet format whitespace demo/unity --folder --verify-no-changes


Unity

name: Unity

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'binding/unity/**'
      - '!binding/unity/README.md'
      - 'lib/common/**'
      - 'lib/android/**'
      - 'lib/ios/**'
      - 'lib/linux/**'
      - 'lib/mac/**'
      - 'lib/windows/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/android/**'
      - 'resources/keyword_files*/ios/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/windows/**'
      - '.github/workflows/unity.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'binding/unity/**'
      - '!binding/unity/README.md'
      - 'lib/common/**'
      - 'lib/android/**'
      - 'lib/ios/**'
      - 'lib/linux/**'
      - 'lib/mac/**'
      - 'lib/windows/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
      - 'resources/keyword_files*/android/**'
      - 'resources/keyword_files*/ios/**'
      - 'resources/keyword_files*/linux/**'
      - 'resources/keyword_files*/mac/**'
      - 'resources/keyword_files*/windows/**'
      - '.github/workflows/unity.yml'

defaults:
  run:
    working-directory: binding/unity

jobs:
  playtest-linux:
    name: Run PlayTest unit tests on Linux
    runs-on: pv-android

    steps:
    - uses: actions/checkout@v3
      with:
        submodules: 'recursive'

    - name: Pre-build dependencies
      run: |
        ./copy.sh
        ./copy_test_resources.sh

    - name: Inject AppID
      run: sed -i 's:{TESTING_ACCESS_KEY_HERE}:${{secrets.PV_VALID_ACCESS_KEY}}:'
        Assets/Porcupine/Tests/Integration.cs

    - name: Run tests
      run: xvfb-run --auto-servernum --server-args='-screen 0 640x480x24' /home/picovoice/Unity/Hub/Editor/2021.3.31f1/Editor/Unity -runTests -batchmode -projectPath . -testResults unityresults.xml -testPlatform StandaloneLinux64 -logFile -

    - name: Check Results
      run: sed -n 2p unityresults.xml | grep 'result="Passed"'

  # NOTE: fix later as mac runner halts unity test app in between runs. Running locally works fine as well as first try after restarting runner.
  # playtest-mac:
  #   name: Run PlayTest unit tests on macOS
  #   runs-on: pv-ios

  #   steps:
  #   - uses: actions/checkout@v3
  #     with:
  #       submodules: 'recursive'

  #   - name: Pre-build dependencies
  #     run: |
  #       ./copy.sh
  #       ./copy_test_resources.sh

  #   - name: Inject AppID
  #     run: sed -i '.bak' 's:{TESTING_ACCESS_KEY_HERE}:${{secrets.PV_VALID_ACCESS_KEY}}:'
  #       Assets/Porcupine/Tests/Integration.cs

  #   - name: Run tests
  #     run: /Applications/Unity/Hub/Editor/2021.3.31f1/Unity.app/Contents/MacOS/Unity -runTests -batchmode -projectPath . -testResults unityresults.xml -testPlatform StandaloneOSX -logFile -

  #   - name: Check Results
  #     run: sed -n 2p unityresults.xml | grep 'result="Passed"'

  playtest-windows:
    name: Run PlayTest unit tests on Windows
    runs-on: pv-windows

    steps:
    - uses: actions/checkout@v3
      with:
        submodules: 'recursive'

    - name: Pre-build dependencies
      run: |
        dos2unix copy.sh
        bash copy.sh
        dos2unix copy_test_resources.sh
        bash copy_test_resources.sh

    - name: Inject AppID
      run: bash -c "sed -i 's:{TESTING_ACCESS_KEY_HERE}:${{secrets.PV_VALID_ACCESS_KEY}}:'
        Assets/Porcupine/Tests/Integration.cs"

    - name: Run tests
      run: >
        & "C:\Program Files\Unity\Hub\Editor\2021.3.31f1\Editor\Unity.exe" -runTests -batchmode -projectPath . -testResults unityresults.xml -testPlatform StandaloneWindows64 -logFile - | Out-Host

    - name: Check Results
      run: bash -c "sed -n 2p unityresults.xml | grep Passed"

  playtest-android:
    name: Run PlayTest unit tests on Android
    runs-on: pv-ios

    steps:
    - uses: actions/checkout@v3
      with:
        submodules: 'recursive'

    - name: Pre-build dependencies
      run: |
        ./copy.sh
        ./copy_test_resources.sh

    - name: Inject AppID
      run: sed -i '.bak' 's:{TESTING_ACCESS_KEY_HERE}:${{secrets.PV_VALID_ACCESS_KEY}}:'
        Assets/Porcupine/Tests/Integration.cs

    - name: Start Emulator
      run: /Users/alirezakenarsari-anhari/Library/Android/sdk/emulator/emulator -avd Pixel_6_API_33 &

    - name: Run tests
      run: /Applications/Unity/Hub/Editor/2021.3.31f1/Unity.app/Contents/MacOS/Unity -runTests -batchmode -buildTarget Android -projectPath . -testResults unityresults.xml -testPlatform Android -logFile -

    - name: Check Results
      run: sed -n 2p unityresults.xml | grep 'result="Passed"'


Vue Codestyle

name: Vue Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '**/vue/*.js'
      - '**/vue/*.ts'
      - '**/vue/*.vue'
      - '**/vue/*.vue'
      - '.github/workflows/vue-codestyle.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '**/vue/*.js'
      - '**/vue/*.ts'
      - '**/vue/*.vue'
      - '**/vue/*.vue'
      - '.github/workflows/vue-codestyle.yml'

jobs:
  check-vue-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js LTS
      uses: actions/setup-node@v3
      with:
        node-version: lts/*

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Run Binding Linter
      run: yarn && yarn lint
      working-directory: binding/vue

    - name: Run Demo Linter
      run: yarn && yarn lint
      working-directory: demo/vue


Vue Demos

name: Vue Demos

on:
  push:
    branches: [ master ]
    paths:
      - 'demo/vue/**'
      - '!demo/vue/README.md'
      - '.github/workflows/vue-demos.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'demo/vue/**'
      - '!demo/vue/README.md'
      - '.github/workflows/vue-demos.yml'

defaults:
  run:
    working-directory: demo/vue

jobs:
  build-demos:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install

    - name: Build
      run: yarn build en

    - name: Build another language
      run: yarn build ja


Vue

name: Vue

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'binding/vue/**'
      - '!binding/vue/README.md'
      - 'lib/common/**'
      - 'lib/wasm/**'
      - 'resources/**'
      - '!resources/.lint/**'
      - '.github/workflows/vue.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'binding/vue/**'
      - '!binding/vue/README.md'
      - 'lib/common/**'
      - 'lib/wasm/**'
      - 'resources/**'
      - '!resources/.lint/**'
      - '.github/workflows/vue.yml'

defaults:
  run:
    working-directory: binding/vue

jobs:
  build:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install

    - name: Build
      run: yarn build

    - name: Set up test
      run: yarn setup-test

    - name: Run test
      run: yarn test --env ACCESS_KEY=${{secrets.PV_VALID_ACCESS_KEY}}


Web Codestyle

name: Web Codestyle

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - '**/web/*.js'
      - '**/web/*.ts'
      - '.github/workflows/web-codestyle.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - '**/web/*.js'
      - '**/web/*.ts'
      - '.github/workflows/web-codestyle.yml'

jobs:
  check-web-codestyle:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js LTS
      uses: actions/setup-node@v3
      with:
        node-version: lts/*

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Run Binding Linter
      run: yarn && yarn lint
      working-directory: binding/web


Web Demos

name: Web Demos

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'demo/web/**'
      - '!demo/web/README.md'
      - '.github/workflows/web-demos.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'demo/web/**'
      - '!demo/web/README.md'
      - '.github/workflows/web-demos.yml'

defaults:
  run:
    working-directory: demo/web

jobs:
  build:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install


Web Performance

name: Web Performance

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'lib/wasm/**'
      - 'lib/common/**'
      - '.github/workflows/web-perf.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'lib/wasm/**'
      - 'lib/common/**'
      - '.github/workflows/web-perf.yml'

defaults:
  run:
    working-directory: binding/web

jobs:
  build:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        node-version: [lts/*]
        include:
        - node-version: lts/*
          initPerformanceThresholdSec: 0.5
          procPerformanceThresholdSec: 0.65

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install

    - name: Copy libs
      run: yarn copywasm && yarn copyppn

    - name: Build
      run: yarn build

    - name: Prepare Test
      run: yarn setup-test

    - name: Test
      run: yarn test-perf --env ACCESS_KEY=${{secrets.PV_VALID_ACCESS_KEY}},NUM_TEST_ITERATIONS=20,INIT_PERFORMANCE_THRESHOLD_SEC=${{matrix.initPerformanceThresholdSec}},PROC_PERFORMANCE_THRESHOLD_SEC=${{matrix.procPerformanceThresholdSec}}


Web

name: Web

on:
  workflow_dispatch:
  push:
    branches: [ master ]
    paths:
      - 'binding/web/**'
      - '!binding/web/README.md'
      - 'lib/common/**'
      - 'lib/wasm/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
      - '.github/workflows/web.yml'
  pull_request:
    branches: [ master, 'v[0-9]+.[0-9]+' ]
    paths:
      - 'binding/web/**'
      - '!binding/web/README.md'
      - 'lib/common/**'
      - 'lib/wasm/**'
      - 'resources/.test/**'
      - 'resources/audio_samples/**'
      - '.github/workflows/web.yml'

defaults:
  run:
    working-directory: binding/web

jobs:
  build:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        node-version: [16.x, 18.x, 20.x]

    steps:
    - uses: actions/checkout@v3

    - name: Set up Node.js ${{ matrix.node-version }}
      uses: actions/setup-node@v3
      with:
        node-version: ${{ matrix.node-version }}

    - name: Pre-build dependencies
      run: npm install yarn

    - name: Install dependencies
      run: yarn install

    - name: Copy libs
      run: yarn copywasm && yarn copyppn

    - name: Build
      run: yarn build

    - name: Prepare Test
      run: yarn setup-test

    - name: Test
      run: yarn test --env ACCESS_KEY=${{secrets.PV_VALID_ACCESS_KEY}}


unit-tests

name: unit-tests

on: [pull_request]
jobs:
  unit-test-python:
    runs-on: ${{ matrix.os }}
    strategy:
      fail-fast: false
      matrix:
        python-version: [ "3.9", "3.10", "3.11"]
        os: [ ubuntu-latest, macos-13 ]
        exclude:
          - os: macos-13
            python-version: "3.9"
    env:
      OS: ${{ matrix.os }}
      PYTHON: ${{ matrix.python-version }}
    steps:
      - uses: actions/checkout@v4
      - name: Setup Python
        id: setup-python
        uses: actions/setup-python@v5
        with:
          python-version: ${{ matrix.python-version }}
          architecture: x64
      - name: Install uv
        run: |
          curl -LsSf https://astral.sh/uv/install.sh | sh
      - name: Get uv cache dir
        id: uv-cache
        run: |
          echo "::set-output name=dir::$(uv cache dir)"
      - name: uv cache
        uses: actions/cache@v4
        with:
          path: ${{ steps.uv-cache.outputs.dir }}
          key: ${{ runner.os }}-${{ steps.setup-python.outputs.python-version }}-uv-${{ hashFiles(format('**/py{0}-ci-requirements.txt', env.PYTHON)) }}
      - name: Install dependencies
        run: make install-python-ci-dependencies-uv
      - name: Test Python
        run: make test-python-unit

  unit-test-ui:
    runs-on: ubuntu-latest
    env:
      NPM_TOKEN: ${{ secrets.NPM_TOKEN }}
    steps:
      - uses: actions/checkout@v4
      - uses: actions/setup-node@v3
        with:
          node-version: '17.x'
          registry-url: 'https://registry.npmjs.org'
      - name: Install yarn dependencies
        working-directory: ./ui
        run: yarn install
      - name: Build yarn rollup
        working-directory: ./ui
        run: yarn build:lib
      - name: Run yarn tests
        working-directory: ./ui
        run: yarn test --watchAll=false