Passing release variables between two agent phases - tfs

I'm working with TFS on-premise.
My issue is that during a release I have two agent phases separated by a manual intervention.
In the first agent phase, I set a variable with:
Write-Verbose $("##vso[task.setvariable variable={0};]{1}" -f $variablename, $variable)
Problem is that in the second agent phase, this variable doesn't exist anymore, even if the same agent is used for the second release phase.
How may I pass a variable between two agent phases during the same release?

There is no way to persist variables (no matter powershell variables or VSTS user defined variables) between two agent phases (and environments) for now.
And there is a related issue Variables set via logging commands are not persistent between agents, you can follow up.
The work around for now is define the variable again in next agent phase.

You can share a variable between the agent phases by using the TFS Rest API and creating a new variable in the release.
You can create a helper module to facilitate this task.
Get the release by using the environment variable $Env:Release_ReleaseId.
Add a NoteProperty, using Add-Member, to the variables hashtable of the release returned in step 1, where the name is your desired variable name and the value is a ConfigurationVariableValue.
Save the release with the added variable.
In order to use this approach, you would set the variable in your first agent. Then, in the second agent, you can simply read the TFS variable using the $(VariableName) semantic.

I've used the "Variable dehydration task" to write the value to my artifact folder in a build pipeline. I then read the json with inline-powershell. Currently, I'm reading it on every task in my release pipeline, which seems mental to me, but it sort of works. You ought to be able to set a global or env? variable and use that instead. Supposedly fixed in 2017, but I'm using 2015.

The right way to do it is using Variablegroups to persist between pipelines: https://learn.microsoft.com/en-us/azure/devops/pipelines/library/variable-groups?view=azure-devops&tabs=yaml

Related

Use user-defined variables in build definition demands

In TFS 2015 and later, is it possible to resolve a user-defined variable in the build definition demands?
Context
A build definition requires certain software A on its build agent, so I set the an custom agent capability A = path/to/A.
I want to use this path in my build definition and make sure that the build definition uses the correct path before starting a build.
Since TFS does not support referencing the values of agent capabilities inside steps of a build definition or release definition, I'm trying to create a workaround. I don't want to use the custom environment variable on the build machine since I want to avoid the additional build step which is required to pass the env variable to TFS build steps.
The planned workaround
Having a variable SoftwareA in build definition containing path/to/A which can be used by the build steps.
In build definition -> general -> demands check if A equals $(SoftwareA).
However $(SoftwareA) seems not to be resolved by TFS and instead is taken literally.
No, unfortunately the variable is never expanded outside the build/release environment.
So you need to change the demand value manually to match the path you defined in agent capabilities.
That means add demands A equals path/to/A.
There is a user voice here to suggest this feature, but it's archived. You can submit a new user voice again to suggest this feature.

How to export windows batch variables as build parameters to following steps in Jenkins?

In Jenkins, is it possible to export windows batch variables as build parameters? I know using build parameters inside windows batch blocks is, I use it a lot.
For example, I have a windows batch block that creates a variable, say A, like
SET A="MyVar"
Is it possible to use it in running MSBuild, passing it like it was a build parameter, in the (working) syntax of /p:AssemblyName=%A% or /p:AssemblyName=${A} ?
Neither of these seem to work (my variable is always empty).
Update: #Tuffwer suggested using the EnvInject plugin. I have been trying, but so far without success. Here's a sample I created to illustrate my original intent:
I want to create a variable which contents will be determined based on a condition applied in one of the build parameters. Then, I want to use that variable as a parameter to the MsBuild command line, using the /p:[Key]=[Value] syntax (which requires the Jenkins MsBuild plugin, if I am not wrong).
I still can't get this to work, now using EnvInject. I need to reference the value of a windows batch variable inside a further build step.
Update II: I turned into Environment Script Plugin, which did the job for me.
Tuffwer suggested using the EnvInject plugin, I tried did not succeed attaining what I intended. I edited my post including my EnvInject attempt, but in the meantime went searching again for other solutions.
This time I came across the Environment Script Plugin, which did the job for me.
Steps:
Mark Generate environment variables from script
For each variable you want to "export", you need to issue an echo [varName]=[value] statement.
That's all.
My build then creates an assembly named either TRUE.exe or FALSE.exe, depending on the build parameter MyBool value.

Is possible to pass a variable from a Build to a Release in TFS 2017?

A Build definition has a custom variable that can be set when a build is queued.
Is possible to have access to that variable from a Release in the same way that is possible to have access to variables like Build.DefinitionId, Build.DefinitionName, Build.BuildNumber ?
I've managed to do this with an extension from the TFS marketplace, called 'Variable (de|re)Hydration Tasks', from naked Agility Ltd. This extension provides build- and release tasks with which you basically can save your build variables and restore them in your release.
It does this by prefixes, so you can save/restore all default build variables that are prefixed with 'BUILD-', but if you prefix your own variables with i.e. 'ABC_' you can also save them from your build and restore them in your release.
A custom build variable couldn't be used in your release definition. Here is an user voice that similar to your problem: https://visualstudio.uservoice.com/forums/330519-team-services/suggestions/14515326-project-level-build-release-variables. You could vote and add comment below.
As a workaround, you could copy those build variables and their values to a Variable groups. Then add the Variable group to your release definition.
This is a new feature in TFS 2017 Update1.
Have you tried just passing the variable into the task definition like $(MyVariable) (where MyVariable is the custom variable name)?

how to get upstream project info on a downstream project - Jenkins

In Jenkins, if we use Post-Build Trigger to start another build
What are ENVs available to the new build.
I need to identify, parent builds Name, Build Number, Last Successful Artifacts' URL etc.,
In simple words, how to get upstream project info on a downstream project
Is that possible
You can use the Parameterized Trigger Plugin to pass variables from one build to the next. It is used in much the same way as the Post Build Trigger plugin you mentioned you're using already.
It defines some variables that are passed through to the next job, but you are free to define your own in the box provided, e.g:
ARTEFACT_URL=www.example.com/builds/$BUILD_NUMBER #using another variable from this build
SOMETHING=VALUE
UPSTREAM_BUILD_NAME=myProject
UPSTREAM_BUILD_NUMBER=$BUILD_NUMBER
#note that you shouldn't override any properties likely to be set in subsequent builds!

How to configure Jenkins in order to build project using ant and custom args

There's too much routine with building next project version using ant. The routine is in several properties files that must be edited before running ant task. I took a look at Jenkins as a system to make builds (including night ones) but I have a problem with changing properties.
Is it possible (if yes, how can I do it) to type parameters in Jenkins configuration before build in order they will be passed to ant?
What I really mean is the following schema (I used in manual builds):
there're 2 properties files that contain data about build version, src destination, emails to notify about new build and so on.
corresponding properties' keys are used in Ant tasks and these properties are changed manually before build.
some properties are read by Java util and used for their own part during build.
there're also 3 or 4 ant XMLs that a imported in build.xml, and these xmls also read properties from mentioned files.
What I want to do is:
change key properties in Jenkins
press build project
my data will overwrite data in properties files OR will be passed as ant vars values straight to the ant's task(s).
as a result I receive new build with corresponding notifications (they're made through ant)
Are there mechanisms that allow one to make such schema work via Jenkins?
Thank you in advance.
In Jenkins, you can use the parameterised build feature to specify those parameters you need to substitute into your build.
For example, if specify a parameter called server and, when clicking "Build Now", you enter test, the build will be executed with an environment variable you can access called ${server}.
Then, in your "Invoke Ant" build step, if you press Advanced..., this reveals a "Properties" field. Here you can enter my.ant.property=${server}.
That's equivalent to calling ant -Dmy.ant.property=${server}, and will be expanded to ant -Dmy.ant.property=test.
Another option : Set environment variables for the scope of the build using this Env plugin. So if the properties you are using are environment variables or can be set as them then you want to use this one. Though it might involve some effort in changing the build scripts, but it can be a good option :
Q : Why would I use this one as I already have parametrized build plugin
A : Because the parametrized build plugin requires human interaction if there is more than 1 choice. For example building for Release 1 or Release 2 or Test branch.
While in the Env plugin, you can set the property once for each choice and then create a respective job for each. Then just schedule the job(s) thereby eliminating the human factor.

Resources