Invoke-Build Documentation

repository·main·Indexed 20 days ago

https://github.com/nightroman/invoke-build

A build and test automation engine for PowerShell (v3.0+) that allows developers to define complex build pipelines as scripts. It supports incremental builds, parallelism, persistent builds, and batch testing. Invoke-Build can be installed as a PowerShell module, a dotnet tool (ib), or as standalone scripts. Key features include task management via Add-BuildTask, execution control with Invoke-BuildExec, and environment management using Use-BuildEnv.

Tokens
50.6K
Snippets
203
Records
274
Agent score
64%

What's inside Invoke-Build

  1. Overview of Invoke-Build features

    main

    Invoke-Build is a build and test automation tool for PowerShell (v3.0+). It allows you to define tasks in PowerShell scripts and provides advanced automation capabilities including:

    • Incremental tasks: Efficiently processes tasks based on inputs and outputs.
    • Persistent builds: Resumable builds that can recover from interruptions.
    • Parallel builds: Executes builds in separate workspaces with shared statistics.
    • Batch testing: Composes tests as tasks for batch invocation.
    • Custom task classes: Ability to define new types of tasks.
    • Cross-platform support: Works with PowerShell Core (v3.0.1+).
    • IDE Integration: Effective use in VSCode and ISE.
  2. Explore Invoke-Build command reference

    main

    Invoke-Build provides a suite of specialized PowerShell functions and scripts for build automation. You can use these to define tasks, execute external applications, assert conditions, manage files, and control the build environment.

    Key functional areas include:

    • Task Management: Add-BuildTask to define tasks, Invoke-Build.ps1 to run them, and Build-Checkpoint.ps1 for persistent builds.
    • Execution & Control: Invoke-BuildExec for running applications with exit code checking, Build-Parallel.ps1 for parallel execution, and Confirm-Build for user prompts.
    • Assertions & Validation: Assert-Build for general conditions, Assert-BuildEquals for equality checks, and Test-BuildAsset to verify required assets.
    • Environment & Properties: Get-BuildProperty to retrieve session/environment variables, Use-BuildEnv to run scripts with temporary environment changes, and Use-BuildAlias for tool aliasing.
    • Output & Logging: Write-Build for colored text output and functions for managing task headers/footers (Set-BuildHeader, Set-BuildFooter).
    • File & System Utilities: Remove-BuildItem for deletion, Get-BuildVersion for file versioning, and Resolve-MSBuild.ps1 to locate MSBuild.
  3. Sub tasks technique overview

    main

    The invoke-build project supports two approaches for managing sub-tasks:

    1. New solution: Uses build script inheritance. This is the recommended modern approach.
    2. Old solution: The legacy sub-tasks technique, which is considered obsolete.

    For more information on how to extend functionality, see the Extends documentation.

  4. Use the InvokeBuild build engine commands

    main

    The InvokeBuild package provides three primary entry points for build and test automation:

    • Invoke-Build: The core build engine used to invoke build scripts.
    • Build-Checkpoint: Used for invoking persistent builds using the engine.
    • Build-Parallel: Used for invoking parallel builds using the engine.
    # Core commands
    Invoke-Build
    Build-Checkpoint
    Build-Parallel
  5. Configure the build root using $BuildRoot

    main

    The $BuildRoot variable defines the base directory for the build. While the engine maintains this variable, you can assign a custom path to it in special cases. The engine will normalize and test the path after the scripts are loaded.

    Note: Although you can assign a value to it, scripts should not attempt to change this variable once the build has started.

    $BuildRoot = "C:\MyCustomBuildPath"
  6. Automate PowerShell script project tasks with Invoke-Build

    main

    For pure PowerShell script projects, Invoke-Build can be used to automate a standard set of lifecycle tasks. Common automated tasks include:

    • Clean: Removing build artifacts and temporary directories.
    • Test: Running test suites and comparing results against expected outputs.
    • Help Generation: Building help files (e.g., in PowerShell MAML format).
    • Documentation: Converting Markdown files to HTML for package distribution.
    • Packaging: Creating final distribution packages.
  7. Use the automatic variable $Task

    main

    In v2.7.4 and later, a new automatic variable $Task is available to represent the current task instance. This variable is accessible within:

    • Task script blocks defined by If, Inputs, Outputs, or Jobs parameters.
    • Event functions Enter|Exit-BuildTask and Enter|Exit-BuildJob.

    Important Compatibility Notes:

    • Do not use $Task as a parameter name or a custom script variable in your build scripts, as it conflicts with the engine's automatic variable.
    • Do not attempt to override $Task in Enter|Exit-BuildTask or Enter|Exit-BuildJob; it is a constant provided by the engine.
    • In Enter|Exit-BuildJob, the first argument is now the job number; use $Task to access the task instance.
    # Example of using $Task in an event function
    function Enter-BuildTask {
        Write-Host "Entering task: $($Task.Name)"
    }
  8. How the Sub tasks technique works

    main

    The Sub tasks technique allows a root build script (e.g., root.build.ps1) to orchestrate child build scripts located in subdirectories.

    In this model, the root script contains standard tasks and two special tasks: build and deploy. These special tasks act as entry points to call specific child scripts (such as deploy/deploy.build.ps1 or src/build.build.ps1).

    To invoke a task within a child script, you use the following command structure:

    1. The first parameter Tasks specifies either a root task or one of the special tasks (build or deploy).
    2. If a special task is chosen, the second parameter SubTasks specifies the specific task to run within that child script.

    Note: This technique is OBSOLETE. Consider using the New build script inheritance technique instead.

    # Syntax pattern
    ./root.build.ps1 <SpecialTask> <SubTaskName>
    
    # Example: Running 'task1' inside the 'build' child script
    ./root.build.ps1 build task1
  9. Configure custom export and import for Build-Checkpoint

    main

    By default, Build-Checkpoint.ps1 saves and restores build tasks, the script path, and all declared script parameters. However, if you need to persist complex script variables or custom data, you can define custom export and import blocks using Set-BuildData.

    • Export Block: Set via Set-BuildData Checkpoint.Export. This block is executed during every task completion to determine what data to save.
    • Import Block: Set via Set-BuildData Checkpoint.Import. This block is executed once when resuming, before the task to be resumed starts. It receives the exported data as the $data parameter and runs in the script scope.

    Note: The data is serialized via Clixml, so ensure your data types are compatible with XML serialization.

    # Define what to save
    Set-BuildData Checkpoint.Export {
        $script:var1
        $script:var2
    }
    
    # Define how to restore it
    Set-BuildData Checkpoint.Import {
        param($data)
        $var1, $var2 = $data
    }
  10. How Invoke-Build executes tasks and jobs

    main

    Invoke-Build follows a specific lifecycle when executing a build script. When you run a build, the following sequence occurs:

    1. Task Selection: The tasks specified by the -Task parameter are selected. If -Task is null, empty, or ., Invoke-Build attempts to run the . task. If . is not defined, it runs the first task added to the script.
    2. Condition Checking: The -If parameter is evaluated. If it evaluates to $false, the task is skipped (though it may be run later if called again with a condition that evaluates to $true).
    3. Job Ordering: Task jobs are organized. This includes the original jobs from the -Jobs parameter and task references added via Before and After modifiers. Before jobs are inserted before the first script job, and After jobs are appended to the end.
    4. Input/Output Evaluation: Before executing script blocks, Invoke-Build compares the files/data specified in the -Inputs and -Outputs parameters. If the outputs are missing or out-of-date compared to the inputs, all script blocks are executed. If they are up-to-date, script blocks are skipped, but referenced tasks are still invoked.

    Important Note on Task Reusability: Once a task succeeds or fails, its contribution to the build is complete and it will not be invoked again in the same run. If you need code to run multiple times, define it as a function within the script and call that function from various tasks.

  11. Sub task command-line completion

    main

    The SubTasks parameter in the root script utilizes the ArgumentCompleter attribute. This enables the shell to provide tab-completion for the specific tasks defined within the child script when a special task is invoked.

    Example: Running ./root.build.ps1 build [TAB] will trigger completions for the tasks available in the child script (e.g., task1, build-task2).