I have pipeline where running template as one of steps.
I need execute template with two different scopes of parameters depends on value of one of pipeline variable.
For example, if pipeline variable 'mode' has value 'dev', I need run template with one scope, if value is 'stage', another scope.
- ${{ if eq(parameters.mode, 'dev') }}:
- template: ../template.yaml
parameters:
mode: dev
namespace: dev-namespace
fqdn: dev-fqdn
- ${{ if eq(variables.mode, 'staging') }}:
- template: ../template.yaml
parameters:
mode: staging
namespace: staging-namespace
fqdn: staging-fqdn
You should use this syntax ${{ if eq(variables['mode'], 'staging') }}:
It depends at what time the variables will be read in at and used. There are more then possible answer.
If using these for the future execution of a template I'd recommend using condition and defining the parameters you have in separate yml variable files.
condition: eq('${{ variables.mode}}', 'staging)
That way the call would be just
job:
condition: eq('${{ variables.mode}}', 'staging')
variables: staging.yml
- template: ../template.yaml
parameters:
mode: ${{ variables.mode }}
namespace: ${{ variables.namepsace }}
fqdn: ${{ variables.fqdn }}
And staging.yml would look like:
variables:
mode: staging
namespace: staging-namespace
fqdn: staging-fqdn
This way it is a little less decoupled and scalable not having to hard code it every time.
1.If you're using runtime parameters, you can use this format:
trigger:
- master
parameters:
- name: mode
displayName: Choose mode
type: string
default: dev
values:
- dev
- staging
pool:
vmImage: 'windows-latest'
steps:
- ${{ if eq(parameters.mode, 'dev') }}:
- template: template.yml
parameters:
mode: dev
- ${{ if eq(parameters.mode, 'staging') }}:
- template: template.yml
parameters:
mode: staging
For more details you can check Parameters to select a template at runtime.
2.If you're using variables defined in yaml directly, check my another sample:
trigger:
- master
variables:
mode: staging
pool:
vmImage: 'windows-latest'
stages:
- stage: Dev
condition: eq(variables.mode, 'dev')
jobs:
- job:
steps:
- template: template.yml
parameters:
mode: dev
- stage: Staging
condition: eq(variables.mode, 'staging')
jobs:
- job:
steps:
- template: template.yml
parameters:
mode: staging
I would recommend runtime parameters way cause it's more convenient and much more flexible.
Update1:
Here's my simple template.yml file which is just for test:
parameters:
- name: mode
type: string
default: default
steps:
- script: echo ${{ parameters.mode }}
Related
This is my first time working with azure pipelines, I started creating my azure-pipeline.yml. I am trying to execute the azure DevOps pipeline. However I am getting to errors where the variable are not referenced as declared.
deploy.sh deploy_azr ${{ variables.subPref }} ${{ variables.rgType }} ${{ variables.location }} ${{ variables.config }}
Here is the start of my template
# Starter pipeline
# Start with a minimal pipeline that you can customize to build and deploy your code.
# Add steps that build, run tests, deploy, and more:
# https://aka.ms/yaml
trigger:
branches:
include:
- main
paths:
include:
- 'bicep/*'
- 'azure-pipelines.yml'
exclude:
- '*'
pool:
vmImage: ubuntu-latest
variables:
${{ if eq(variables['Build.SourceBranchName'], 'test_branch') }}:
deployTarget: tst
subscription: testsubscription
subscriptionId: 26455-trt31-******
rgType: tstrg
subPref: *****
config: tstjson
location: eastus2
${{ if eq(variables['Build.SourceBranchName'], 'main') }}:
deployTarget: prd
subscription: prdsub
subscriptionId: ***********************
rgType: prdrg
subPref: ******
config: prd.json
location: eastus2
stages:
- stage: Deploylib
jobs:
- deployment: lib
environment: ${{ variables.subscription }}
strategy:
runOnce:
deploy:
steps:
- checkout: self
- task: AzureCLI#2
inputs:
azureSubscription: ${{ variables.subscription }}
scriptType: 'bash'
scriptLocation: 'inlineScript'
inlineScript: |
set -e
set -x
sudo apt install -y gridsite-clients
cd 'bicep'
echo "starting the lib deployment"
deploy.sh deploy_azr ${{ variables.subPref }} ${{ variables.rgType }} ${{ variables.location }} ${{ variables.config }}
any help would be appreciated.
I think the problem is that you need to specify the correct environment name on this line,
jobs:
- deployment: lib
environment: <environment name>
You can create an environment on the DevOps page, see the reference here, then copy the name to the YAML above.
The concept of environment here represents a collection of resources you will deploy your code. Once you have run a deployment, you should be able to see the history of deployment in the target environment.
/azure-pipelines.yml (Line: 42, Col: 22): Unexpected value ''
Test the same YAML sample and reproduce the same issue.
The cause of the issue is that you are using the format: ${{ variables.subscription }} in YAML sample.
The variable will be processed at compile time.
To solve this issue, you can change to use the format: $(subscription)
For example:
jobs:
- deployment: lib
environment: $(subscription)
Result:
For more detailed info, you can refer to this doc: Runtime expression syntax
I want to customize environment attribute to choose programmatically environment for approval (dev, preprod, prod). When I try to launch pipeline, I see this error. Is there an alternative?
Job : Environment $(environment) could not be found. The environment does not exist or has not been authorized for use.
variables:
environment: dev
jobs:
- deployment: test
displayName: test
timeoutInMinutes: 0
# creates an environment if it doesn't exist
environment: $(environment)
strategy:
runOnce:
deploy:
steps:
- checkout: self
clean: true
displayName : Checkout repository
- task: NodeTool#0
inputs:
versionSpec: '16.x'
checkLatest: true
For this use case you should use parameters. This is because variables are not available during the initial parsing stage of the pipeline.
parameters:
- name: "environment"
type: string
default: "development"
And then environment: ${{ parameters.environment }}
Or if you want to get fancy, you could do something like this:
parameters:
- name: "environments"
type: object
default:
- name: development
param1: value
param2: value
- name: test
param1: value
param2: value
# This will look through the environment parameter and create a job for each environment.
- ${{ each environment in parameters.environments }} :
jobs:
- deployment: test
#read in vars from a file in variables/development.yml
variables: variables/${{ environment.name }}.yml
displayName: test
timeoutInMinutes: 0
# creates an environment if it doesn't exist
environment: ${{ environment.name }}
strategy:
runOnce:
deploy:
steps:
- checkout: self
clean: true
displayName : Checkout repository
- task: NodeTool#0
inputs:
versionSpec: '16.x'
checkLatest: true
I have three environments: dev, hml and qa.
In my pipeline depending on the branch the stage has a condition to check whether it will run or not:
- stage: Project_Deploy_DEV
condition: eq(variables['Build.SourceBranch'], 'refs/heads/dev')
dependsOn: Project_Build
- stage: Project_Deploy_HML
condition: eq(variables['Build.SourceBranch'], 'refs/heads/hml')
dependsOn: Project_Build
I'm doing the qa stage, and I'd like to put a condition, depending on the branch, the dependson parameter will change:
- stage: Project_QA
condition:
${{ if eq(variables['Build.SourceBranchName'], 'dev') }}:
dependsOn: 'Project_Deploy_DEV'
${{ if eq(variables['Build.SourceBranchName'], 'hml') }}:
dependsOn: 'Project_Deploy_HML'
However, the condition above is not working, would anyone know the best way to perform this condition?
Thanks
From your YAML sample, it seems that there is a format issue. When you use if expression, there is no need to add condition field in YAML.
You can try the following sample and check if it can work.
stages:
- stage: A
jobs:
- job: test
steps:
- xxx
- stage: B
jobs:
- job: test
steps:
- xxx
- stage: C
${{ if eq(variables['Build.SourceBranchName'], 'main') }}:
dependsOn: A
${{ if eq(variables['Build.SourceBranchName'], 'dev') }}:
dependsOn: B
jobs:
- job: test
steps:
- xxx
I'm trying to pass the environment parameter to a template and then to another template (line webAppName: 'my-webapp-${{parameters.environment}}')
I get the error : A template expression is not allowed in this context. Is it not possible to do that ?
main pipeline (just the necessary code for clarity)
- stage: deploy
displayName: 'Deploy Dev Stage'
dependsOn: build
condition: succeeded()
jobs:
- deployment: deploymentjob
displayName: deployment job
environment: dev
variables:
- template: variables/dev.yml
strategy:
runOnce:
deploy:
steps:
- template: templates/pipeline-deploy/master.yml
parameters:
environment: 'dev'
master.yml
parameters:
environment: ''
steps:
- template: webapp.yml
parameters:
webAppName: 'my-webapp-${{parameters.environment}}'
then webapp.yml
parameters:
webAppName: ''
steps:
- task: AzureRmWebAppDeployment#4
displayName: 'Deploy my app'
inputs:
azureSubscription: '(#some id)'
WebAppName: ${{parameters.webAppName}}
packageForLinux: '$(workFolder)/my-package.zip'
I don't believe you're allowed to use variable substitution in ARM template parameters. But you ARE allowed to do so in variables.
So in master.yml, define a variables section, and compose your webAppName as a variable. Then pass that variable into webapp.yml instead of using a parameter.
The problem was the indentation in one of my YAML files, which was not correct. Adding an extra tab solved it.
I'm trying to set the variable group according to one varible that exists in the pipeline. The yaml looks like this:
But i'm getting the following error when i'm running the pipeline:
If i remove the "- group : QA" or "- group : PROD" the pipeline runs without any problem. What am I doing wrong?
This is slightly different solution but you may achieve your goal - which is if I understood conditional selection of variable group.
You can use runtime parameters:
parameters:
- name: environment
displayName: Environment
type: string
default: QA
values:
- QA
- PROD
stages:
- stage:
displayName: 'Build and Restore'
variables:
- group: ${{ parameters.environment }}
jobs:
- job:
steps:
- script: echo $(name)
than running a build you can select your envrionment:
Note: I have defined two variable groups QA and PROD with variable name in both groups.
Try with below schema:
variables:
isProd: true
stages:
- stage: Test
displayName: Build and restore
variables:
- ${{ if eq(variables['isProd'], 'false') }}:
- group: QA
- ${{ if eq(variables['isProd'], 'true') }}:
- group: PROD
jobs:
- job: A
steps:
- bash: echo $(groupname)
Note: You may receive some red warning when you defining above YAML scipt. Ignore that confused warning and continue to run it.