Within a TeamCity project running on a windows agent, I would like to read the contents of a file and then create a directory based on the file contents.
Performing this operation as a command line build step seems logical. I have tried creating a local variable "VERSION" as well as a custom teamcity parameter, but I can't get either to work. It does not seem that windows cmd variables are playing nicely with the TeamCity defined env and system variables. I am using the following custom script:
echo "Distributing"
set VERSION=< component_version.txt
echo %VERSION%
echo "Copying files to dir \path\to\dir\%VERSION%\"
mkdir \path\to\dir\%VERSION%\
Any suggestions on how I can achieve this?
You need to escape the variable with %% so it isn't treated as a TeamCity variable.
echo "Distributing"
set VERSION=< component_version.txt
echo %%VERSION%%
echo "Copying files to dir \path\to\dir\%%VERSION%%\"
mkdir \path\to\dir\%%VERSION%%\
Try creating a .bat file or Powershell file that accepts a parameter, and executes the steps you have outlined above.
Then switch your Build step to run an "executable with parameters", and pass the %VERSION% in as a parameter.
Related
In TeamCity 2017.2.2 I am using parameters like %host% and when deploying TeamCity replaces those parameters by what I specified on the parameters section - at least when I paste my Powershell script right into the "Script source" box (setting Script: "Source code").
When I use the setting Script: "File" instead and pick the same .ps1 file from my repository, then TeamCity will run the script as before but leaves parameters like %host% untouched.
How do I use parameters with scripts from my repo?
The file is not altered from your vcs with a token replacement from: %host% to your value when you use the File input.
You should specify parameters for your script, and inside the "Script Arguments" section on TeamCity, you can specify the parameters like this:
-Host: %host% -SomeCustomValue: %extraArgs%
This will cause the script to be executed with the parameters transformed with proper values.
In my Jenkins post build email (using extended email plugin), I want to use a variable identified in a build step (windows batch) using the EnvInject plugin. The plugin requires a properties file to be created using a shell script. I am having difficulties converting the following batch lines to shell:
svn log --limit 1 > Change_Request.txt
set "ChangeRequest="
for /f "skip=3 delims=" %%i in (Change_Request.txt) do if not defined ChangeRequest set "ChangeRequest=%%i"
echo ChangeRequest=%ChangeRequest% > export.properties
The situation: There is a Jenkins plugin named EnvInject that allows variables to be passed from a build step to a post build step. The variable was not being passed between the steps.
Perceived issue at the time: After reading the error log message and instructions on using the plugin, I thought the plugin only worked with a shell script.
Real issue: I was trying to read the properties file from a different location than where it was written.
Solution: Initially resolved by using a shell script to write the variable to a properties file:
echo ChangeRequest=$(svn log --limit 1|sed '4q;d')>export.properties
This resolved the issue as it created the properties file in the expected location.
But if I had properly identified the issue, it could have been resolved in the initial batch script.
When updating the Jenkins job to pass a second variable, I realized the real reason my initial effort failed. I updated my first batch script to pass the variables to a properties file, in the expected location. I ran my svn command from the repository directory, then returned to my job's workspace directory to write the properties file.
svn log --limit 1 > ..\..\..\Change_Request.txt
for /f "skip=3 delims=" %%i in (..\..\..\Change_Request.txt) do if not defined >ChangeRequest set ChangeRequest=%%i
for /f "delims=: tokens=1,2" %%a in ('svn info %Repository_URL%') do (
if "%%a"=="Revision" (
set /a RevisionNumber=%%b
)
)
CD D:\Jenkins\workspace\JOB_Folder\
echo ChangeRequest=%ChangeRequest% > export.properties
echo RevisionNumber=%RevisionNumber% >> export.properties
Having no svn I can't test this, but it might work.
Coming from windows I'm quite new to shell/bash.
First version quite simmilar:
svn log --limit 1 > Change_Request.txt
ChangeRequest=$(sed '4q;d' Change_Request.txt)
echo ChangeRequest=$ChangeRequest>export.properties
Shorter no var:
svn log --limit 1 > Change_Request.txt
echo ChangeRequest=$(sed '2q;d' Change_Request.txt)>export.properties
Shortest no intermediate file (maybe required)
echo ChangeRequest=$(svn log --limit 1|sed '4q;d')>export.properties
PowerShell variant
svn log --limit 1 > Change_Request.txt
"ChangeRequest=$((gc Change_Request.txt)[4])" > export.properties
My goal is copying an .exe file from a bin folder of solution A to another solutions B resource folder on the post build event of solution A.
I created the necessary xcopy command and tried it out in powershell: It works perfectly.
Whenever I add any command to the actions in VS build fails with: "#command# exited with code 1", where #command# is, for example, the xcopy command.
I tried running VS as admin and currently I tried just running a .bat file that contains "#echo off #exit 0". That too leads to "#command# exited with code 1".
Have some example of what I tried out as VS post/pre-build command:
call "projdir\test.bat"
call projdir\test.bat
"projdir\test.bat"
projdir\test.bat... I tried projdir as "$(ProjectPath)" and manual path.
I put output to verbose and found the following:The command "C:\Users\Traubenfuchs\AppData\Local\Temp" is written incorrectly or couldn't be found. (That folder actually exists but I don't know what it wants to do it.)The same thing happens when I put an xcopy command in pre/post build.
Anyone knows what I am doing wrong?
Recently I met similar problem.
About your "hello world" post-build event :
try to call powershell directly
powershell -command "write-output 'hello world'; exit 0"
=================
My pre-build event looks like :
powershell -file scriptPath.ps1
My scriptPath.ps1 looks like :
<my epic powershell code>
...
exit 0
Note that without "exit 0" at the end I recieved return code 1 from my script.
We had this issue because of a "Software Restriction Policy" set up in a domain GPO. It appears that pre and post builds create a .cmd batch file in the temp folder. Here's what the logging showed me:
cmd.exe (PID = 8456) identified
C:\Users\brian\AppData\Local\Temp\tmp733425d2c0604973a90a0a175c13353e.exec.cmd
as Disallowed using default rule, Guid =
{11015445-d282-4f86-96a2-9e485f593302}
To fix this we modified the GPO that controlled the SRP so that it did not include .cmd files. After all, the goal of SRP is to block executable malware, not batch files. I may get some security blowback because of this. Hopefully someone knows a better way to fix this issue.
One possible issue is that you have to use $(ProjectDir) instead of $(ProjectPath)
When you use $(ProjectPath) it is actually: "C:\Users\....\Project\MyProject.csproj"
Versus $(ProjectDir) which is: "C:\Users\....\Project\"
Notice, that the first version is actually pointing to your project solution file... which would cause everything to fail.
Another is that that $(ProjectDir) automatically adds the trailing slash to the path. i.e. "$(ProjectDir)\test.bat" would actually translate to: "C:\Users\....\Project\\test.bat"
Also you have to make sure that you enclose all your file paths in double quotes
So the correct call would look like this:
call "$(ProjectDir)test.bat"
Other things to check out would be to make sure that the directory that the script is executing from is correct. See SO: visual studio 2012, postbuild event, bat file not creating new file (not executing)
Have you checked out the suggestions in this StackOverflow? Post Build exited with code 1
Edit
Try this:
echo Hello World
#exit 0
You need to end any commands with #exit 0 otherwise it doesn't think that it finished properly
Edit 2
Why do we use #exit 0 instead of exit 0? #Sunny has a good explanation of the At symbol - # here:
The # symbol tells the command processor to be less verbose; to only
show the output of the command without showing it being executed or
any prompts associated with the execution. When used it is prepended
to the beginning of the command, it is not necessary to leave a space
between the "#" and the command.
Essentially if you call xyz.bat by default every command in the .bat file is echoed back along with the actual output of the command. e.g.:
test.bat
echo Hello World
exit 0
Will output:
C:\>call test.bat
C:\>echo Hello World
Hello World
C:\>exit 0
C:\>
When we add a # in front of the commands, we only get the output of the commands themselves.
test2.bat
#echo Hello World
#exit 0
Will output:
C:\>call c.bat
Hello World
C:\>
#echo off is also a way to turn this off for the rest of the script. We typically do this simply to make the logs easier to read, as the text of the commands muddies the log output.
I am trying to create a Jenkins build on a windows box, and am running into a situation where I am completely unsure of what to do.
I have the following shell script which I need to convert to a windows batch script for when the build runs. I have I believe gotten the set correct for the variables, just not sure what to do with the rest of it:
#set POWERUSER=DTCURTISS
#set POWERPASS=password
set POWERUSER=auto
set POWERPASS=password
set TAG=$BUILD_NUMBER
set PATH=.env/bin:$PATH
set SAUCEUSER=DarthOpto
set ACCESSKEY=accesskey
set IGNOREPAGEHEADERLOCATION=True
set MAINMENUCLICKTILES=False
set LOGDIR=logs
source ../.env/bin/activate
cd trunk/automation/selenium/src
#pip install -r pip-requires.txt
rm -rf logs
nosetests --nocapture --with-xunitmp -a valallmod --processes=$THREADS --process- timeout=5000
You are not going to get far if you don't know batch-file. Besides, simply "translating" bash to batch is not going to magically make it work on Windows.
Variables are referenced as %VARNAME%, not $VARNAME. Fix that first.
Windows uses \ as path separator, not /. Change all your paths to use \
When you want to append to PATH variable in Windows, you've got to make sure you don't destroy the existing PATH. You do this through set PATH=%PATH%;C:\whatever\yourpath\
Something similar to source would be batch's call followed by another batch file name. However you can't just pass it ../.env/bin/activate as that is not a batch file. You would need to convert that file to batch as well. And don't forget to convert the path separator to \. This is also where my second point comes into play. The file you pasted is rather simple. I've got no idea what's inside that other file or whether it can be "translated".
The # is not a valid comment in batch, you need to use REM or better yet ::
rm and it's flags is not a Windows command. An equivalent would be rmdir /s /q
Finally, nosetests is neither bash nor batch. It's an external program. You've got to make sure it is available in Windows. As a pre-emptive step before your next question, read this: 'nosetests' not recognized on Windows after being installed and added to PATH
How do I run a BAT script without changing directories?
I am in ./a and the script cd's into ./a/bc. If I need to terminate my script for whatever reason I am now in bc instead of a. How do I run the script and not have my folder change?
Also, I don't like how it asks me if I'd like to terminate my script. Can I disable that and let it terminate?
The setlocal command is useful for this. Any directory changes after setlocal are just local to the batch script. BTW this also applies to any environment variables (set commands).
For example, after running this batch script:
cd /d c:\temp
setlocal
cd /d c:\windows
the directory will be c:\temp since the second cd in the script is just local to the script.
If you don't need to propagate environment variable changes into the current environment and cannot touch the batch file (to use the pushd/popd variant which I usually use), you can still spawn a new instance of cmd:
cmd /c myBatch.cmd arg1 arg2 ...
Also has the nice property of leaving your original batch file running even if the called batch throws up errors. I do that in my batch unit testing framework, for example, to ensure that a failing batch file won't stop the tests from executing.
You can run your script with start yourscript.bat. This makes it run in a new command window, and therefore does not affect the working directory of the command prompt that started the script.
Another possibility is to not use cd and use absolute paths instead.
The first question is: why do you need to change the directory? Can you simply work with paths relative to the one of your batch file? (e.g. using %~dp0\a\bc to reference the directory)
But if you really, really need to do that, you can do the following:
REM change the current directory
pushd ..\a\bc
.. do your stuff here
REM restore the old "current directory"
popd