Use a PowerShell script to customize your build pipeline

Azure Pipelines | TFS 2018 | TFS 2017 | TFS 2015 | Previous versions (XAML builds)


In Microsoft Team Foundation Server (TFS) 2018 and previous versions, build and release pipelines are called definitions, runs are called builds, service connections are called service endpoints, stages are called environments, and jobs are called phases.

When you are ready to move beyond the basics of compiling and testing your code, use a PowerShell script to add your team's business logic to your build pipeline.

You can run Windows PowerShell on a Windows build agent. PowerShell Core runs on any platform.

  1. Push your script into your repo.

  2. Add a pwsh or powershell step:

# for PowerShell Core
- pwsh: ./my-script.ps1

# for Windows PowerShell
- powershell: .\my-script.ps1

You can run Windows PowerShell Script on a Windows build agent.

  1. Push your script into your repo.

  2. Add a PowerShell build task.

    Add task

    Add PowerShell task

  3. Drag the build task where you want it to run.

  4. Specify the name of the script.

Example: Version your assemblies

For example, to version to your assemblies, copy and upload this script to your project:

# Look for a pattern in the build number.
# If found use it to version the assemblies.
# For example, if the 'Build number format' build pipeline parameter 
# $(BuildDefinitionName)_$(Year:yyyy).$(Month).$(DayOfMonth)$(Rev:.r)
# then your build numbers come out like this:
# "Build HelloWorld_2013.07.19.1"
# This script would then apply version 2013.07.19.1 to your assemblies.
# Enable -Verbose option
# Regular expression pattern to find the version in the build number 
# and then apply it to the assemblies
$VersionRegex = "\d+\.\d+\.\d+\.\d+"
# If this script is not running on a build server, remind user to 
# set environment variables so that this script can be debugged
	Write-Error "You must set the following environment variables"
	Write-Error "to test this script interactively."
	Write-Host '$Env:BUILD_SOURCESDIRECTORY - For example, enter something like:'
	Write-Host '$Env:BUILD_SOURCESDIRECTORY = "C:\code\FabrikamTFVC\HelloWorld"'
	Write-Host '$Env:BUILD_BUILDNUMBER - For example, enter something like:'
	Write-Host '$Env:BUILD_BUILDNUMBER = "Build HelloWorld_0000.00.00.0"'
	exit 1
# Make sure path to source code directory is available
	Write-Error ("BUILD_SOURCESDIRECTORY environment variable is missing.")
	exit 1
elseif (-not (Test-Path $Env:BUILD_SOURCESDIRECTORY))
	exit 1
# Make sure there is a build number
	Write-Error ("BUILD_BUILDNUMBER environment variable is missing.")
	exit 1
# Get and validate the version data
$VersionData = [regex]::matches($Env:BUILD_BUILDNUMBER,$VersionRegex)
         Write-Error "Could not find version number data in BUILD_BUILDNUMBER."
         exit 1
   1 {}
         Write-Warning "Found more than instance of version data in BUILD_BUILDNUMBER." 
         Write-Warning "Will assume first instance is version."
$NewVersion = $VersionData[0]
Write-Verbose "Version: $NewVersion"
# Apply the version to the assembly property files
$files = gci $Env:BUILD_SOURCESDIRECTORY -recurse -include "*Properties*","My Project" | 
	?{ $_.PSIsContainer } | 
	foreach { gci -Path $_.FullName -Recurse -include AssemblyInfo.* }
	Write-Verbose "Will apply $NewVersion to $($files.count) files."
	foreach ($file in $files) {
		$filecontent = Get-Content($file)
		attrib $file -r
		$filecontent -replace $VersionRegex, $NewVersion | Out-File $file
		Write-Verbose "$file.FullName - version applied"
	Write-Warning "Found no files."

Add the build task to your build pipeline.

Apply version to assemblies build task

Specify your build number with something like this:

Build number format


Use the OAuth token to access the REST API

You can use $env:SYSTEM_ACCESSTOKEN in your script in a YAML pipeline to access the OAuth token.

- task: PowerShell@2
    targetType: 'inline'
    script: |
      $url = "$($env:SYSTEM_TEAMFOUNDATIONCOLLECTIONURI)$env:SYSTEM_TEAMPROJECTID/_apis/build/definitions/$($env:SYSTEM_DEFINITIONID)?api-version=5.0"
              Write-Host "URL: $url"
              $pipeline = Invoke-RestMethod -Uri $url -Headers @{
                  Authorization = "Bearer $env:SYSTEM_ACCESSTOKEN"
              Write-Host "Pipeline = $($pipeline | ConvertTo-Json -Depth 100)"
     SYSTEM_ACCESSTOKEN: $(System.AccessToken)


What variables are available for me to use in my scripts?

Use variables

How do I set a variable so that it can be read by subsequent scripts and tasks?

Define and modify your build variables in a script

Define and modify your release variables in a script

Which branch of the script does the build run?

The build runs the script same branch of the code you are building.

What kinds of parameters can I use?

You can use named parameters. Other kinds of parameters, such as switch parameters, are not yet supported and will cause errors.

I use TFS on-premises and I don't see some of these features. Why not?

Some of these features are available only on Azure Pipelines and not yet available on-premises. Some features are available on-premises if you have upgraded to the latest version of TFS.