Build Unity

The Build Unity workflow in Buildalon automates the process of compiling Unity projects across multiple platforms. By configuring a job matrix and using specific actions, this workflow handles Unity project setup, licensing, building, and artifact management. This setup ensures efficient builds across different platforms and simplifies artifact handling for release and testing.

Register at buildalon.com and we’ll help you set up a workflow tailored to your project.

Job Matrix

A job matrix allows you to define multiple configurations within a single workflow. Each configuration specifies an operating system and build target, letting you build for multiple platforms concurrently. Below is an example of a job matrix configured to build for the Windows platform using the StandaloneWindows64 target.

Example Job Matrix Configuration

jobs:
  build:
    if: ${{ github.event_name != 'pull_request' || github.event.pull_request.draft == false }}
    env:
      UNITY_PROJECT_PATH: ''
    runs-on: ${{ matrix.os }}
    strategy:
      fail-fast: false
      matrix:
        include:
          - os: buildalon-windows
            build-target: StandaloneWindows64
            build-args: ''

Steps

Here are the minimum recommended steps to build Unity.

1. Checkout the Code

Clones the repository with submodules, Git LFS, and options for a clean checkout.

If your project depends on packages or repositories outside of your repository, refer to the Accessing Dependencies page.

- uses: actions/checkout@v7
  with:
    clean: ${{ inputs.clean }}
    lfs: true
    submodules: 'recursive'

Documentation for actions/checkout

2. Setup Unity

Installs Unity Hub and the version of Unity used by your project. If you have more than one project, you need to specify the path to the ProjectVersion.txt file.

- uses: buildalon/unity-setup@v2
  with:
    version-file: 'path/to/your/unity/project/ProjectSettings/ProjectVersion.txt'
    build-targets: '${{ matrix.build-target }}'

Documentation for buildalon/unity-setup

3. Activate Unity License

Authenticates Unity using personal or professional license credentials.

Personal License:

- uses: buildalon/activate-unity-license@v2
  with:
    license: 'Personal'
    username: '${{ secrets.UNITY_USERNAME }}'
    password: '${{ secrets.UNITY_PASSWORD }}'

Professional License:

- uses: buildalon/activate-unity-license@v2
  with:
    license: 'Professional'
    username: '${{ secrets.UNITY_USERNAME }}'
    password: '${{ secrets.UNITY_PASSWORD }}'
    serial: '${{ secrets.UNITY_SERIAL }}'

Documentation for buildalon/activate-unity-license

4. Add Build Pipeline Package

Adds the Build Pipeline package to your project. This package is required to build your project from the command line.

- name: Add Build Pipeline Package
  working-directory: ${{ env.UNITY_PROJECT_PATH }}
  run: |
    npm install -g openupm-cli
    openupm add com.virtualmaker.buildalon

Documentation for com.virtualmaker.buildalon

5. Project Validation

Validates the Unity project by opening it, importing all assets, and checking for script compile errors.

- uses: buildalon/unity-action@v3
  name: Project Validation
  with:
    log-name: 'project-validation'
    build-target: '${{ matrix.build-target }}'
    args: '-quit -batchmode -executeMethod Buildalon.Editor.BuildPipeline.UnityPlayerBuildTools.ValidateProject'

Documentation for buildalon/unity-action

6. Clean the Selected Build Output

Persistent and self-hosted runners can retain untracked build outputs between jobs. Remove only the active matrix target before building so a successful artifact cannot contain files from an older run.

- name: Clean ${{ matrix.build-target }} Build Output
  shell: pwsh
  env:
    BUILD_OUTPUT_PATH: ${{ env.UNITY_PROJECT_PATH }}/Builds/${{ matrix.build-target }}
  run: |
    $projectPath = [System.IO.Path]::GetFullPath($env:UNITY_PROJECT_PATH)
    $outputPath = [System.IO.Path]::GetFullPath($env:BUILD_OUTPUT_PATH)
    $relativePath = [System.IO.Path]::GetRelativePath($projectPath, $outputPath)

    if ($relativePath -eq '.' -or $relativePath.StartsWith('..') -or [System.IO.Path]::IsPathRooted($relativePath)) {
      throw "Refusing to clean build output outside project path: $outputPath"
    }

    if (Test-Path -LiteralPath $outputPath) {
      Remove-Item -LiteralPath $outputPath -Recurse -Force
    }

    New-Item -ItemType Directory -Path $outputPath -Force | Out-Null

7. Build Unity Project

Executes the Unity build process for the specified platform target.

- uses: buildalon/unity-action@v3
  name: '${{ matrix.build-target }}-Build'
  with:
    log-name: '${{ matrix.build-target }}-Build'
    build-target: '${{ matrix.build-target }}'
    args: '-quit -batchmode -executeMethod Buildalon.Editor.BuildPipeline.UnityPlayerBuildTools.StartCommandLineBuild${{ matrix.build-args }}'

8. Upload Build and Log Artifacts

Upload successful build deliverables separately from diagnostic logs. The build path uses the active matrix target so parallel jobs cannot include another platform’s output. Logs and test results use always() and best-effort settings so they remain available when an earlier step fails without masking the original failure.

If you register at buildalon.com, we’ll help you set up the correct paths for your selected platforms.

- uses: actions/upload-artifact@v7
  id: upload-artifact
  name: Upload ${{ matrix.build-target }} Build
  if: success()
  with:
    compression-level: 0
    retention-days: 1
    name: ${{ github.run_number }}.${{ github.run_attempt }}-${{ matrix.os }}-${{ matrix.build-target }}-Build
    path: |
      ${{ env.UNITY_PROJECT_PATH }}/Builds/${{ matrix.build-target }}/**/*
      !${{ env.UNITY_PROJECT_PATH }}/Library/**/*
      !/**/*_BackUpThisFolder_ButDontShipItWithYourGame/**
      !/**/*_BurstDebugInformation_DoNotShip/**

- uses: actions/upload-artifact@v7
  id: upload-logs
  name: Upload ${{ matrix.build-target }} Logs
  if: always()
  continue-on-error: true
  with:
    retention-days: 1
    if-no-files-found: ignore
    name: ${{ github.run_number }}.${{ github.run_attempt }}-${{ matrix.os }}-${{ matrix.build-target }}-Logs
    path: |
      ${{ github.workspace }}/**/*.log
      ${{ github.workspace }}/**/*.xml

9. Clean Uploaded Logs and Optional Build Artifacts

Remove uploaded logs after every job so they cannot be included in a later run. When the manual clean input is enabled, also remove the selected target’s build output after upload. The generated cleanup is best-effort and therefore cannot replace the original build result.

- name: Clean Artifacts
  if: always()
  shell: bash
  continue-on-error: true
  run: |
    set -xe
    echo "Cleaning logs..."
    logs=$(find "${{ github.workspace }}" -type f -name "*.log")
    for log in $logs; do
      rm -f "$log" || echo "::warning::Failed to delete log file: $log"
    done

    clean='${{ inputs.clean }}'
    if [ "$clean" == 'true' ]; then
      artifacts="${{ env.UNITY_PROJECT_PATH }}/Builds/${{ matrix.build-target }}"
      rm -rf "$artifacts" || echo "::warning::Failed to delete artifacts folder: $artifacts"
    }

Additional Build Steps for Specific Platforms

Some platforms require additional steps to complete the build process.

iOS, macOS, and visionOS IL2CPP builds require an additional step to build the generated XCode project.

Universal Windows Platform (UWP) builds require an additional step to build the generated Visual Studio solution.

Having Trouble?

Next Steps

  • Triggers: Set up triggers to start workflows automatically.
  • Build Unity: Set up automated builds for your Unity project.
  • Buildalon Actions: Explore the actions available to use in your workflows.
  • Unit Testing: Automate unit testing to ensure stability and quality.
  • Deploy to Stores: Add deployment steps to distribute your app to users.
  • Dependencies: Learn what to do if your project depends on other private packages or repositories.

© 2026 Virtual Maker Corporation