How to test for operating system in ant build - ant

It seems the only reliably provided property by ant is the "os.name" property. However this name has variants ;lie "Windows 8" "Windows 7" etc
But for my purposes both are "Windows" -
Is there a way to conditionally set a property based on a partial string match of another property value like the pseudo code below? specifically the os.name as the source value? using the default task set provided with a generic ant install?
if(a.property 'contains' "Windows")
another.property = "windows value"
else if(a.property contains 'Linux')
another.property = "linux value"
endif

You can use os family
<condition property="another.property" value="windows value" >
<os family="windows" />
</condition>
<condition property="another.property" value="linux value" >
<os family="unix" name="Linux"/>
</condition>

Related

How to check a property or variable is empty and set a value then test for that value

We are using Ant 1.8. I am not an Ant developer but I have to pretend sometimes.
A new property, ${noReportDSUpgrade}, is intended to be "true" or "false".
By default it is empty (not exist?) which is "false" for our purposes.
If this property is empty it should be set to "false".
A command line using this parameter should set it to true.
1) How do I set ${noReportDSUpgrade} to false if empty and true if supplied?
2) For the target, how to execute only if false?
I have tried several suggestions I've found but can't get it to work.
At the beginning of the script:
<target name="init">
<antcall target="setnoReportDSUpgradeProperty"/>
Further down:
<target name="setnoReportDSUpgradeProperty">
<condition>
<or>
<equals arg1="${noReportDSUpgrade}" arg2=""/>
<not>
<isset property="false"/>
</not>
</or>
</condition>
<echo message="noReportDSUpgrade set to ${noReportDSUpgrade}"/>
</target>
Here's how to set a default property value in Ant:
<property name="noReportDSUpgrade" value="false" />
That's it! Properties are immutable in Ant, so if you set a value via command line or earlier in the script, subsequent <property> tasks won't change it. This won't account for the property being set to a blank value (i.e. ""), but as a general good practice, try to avoid setting properties to blank.
Even though I don't think you need a <condition> task for your goals here, I feel I should clear some things up in your example. The <condition> task doesn't affect the <target> that it's nested in; it simply sets a property, specified by the property attribute. Additionally, the isset condition's property attribute is used to point to the name of the property you're checking, not the value.
<condition property="noReportDSUpgrade">
<or>
<equals arg1="${noReportDSUpgrade}" arg2=""/>
<not>
<isset property="noReportDSUpgrade" />
</not>
</or>
</condition>
But like I said above, don't use that unless you really need to check for a blank value for some reason. Just use <property>.
As for running targets conditionally, the <target> block supports if and unless attributes that control whether or not the entire thing runs. This can be a bit confusing because there are two modes in which this operates.
<target name="myTarget" if="myCondition">
<echo message="Running myTarget" />
</target>
The above target will run if myCondition is set (not if its value is true). So if it evaluates to "true", "false", "asdf", or just blank, the target will still run. Conversely, if we used the unless attribute, it wouldn't run if myCondition is set to anything. This is usually convenient for when you're using the <condition> task to set your properties (since <condition> does not set a value if the boolean evaluates to false).
<target name="myTarget" if="${myCondition}">
<echo message="Running myTarget" />
</target>
Notice the ${} around myCondition. When you expand the property like this, Ant will only run the target if the property's value is "true", "on", or "yes".
Lastly, you typically don't need to make a separate target just for setting conditions. In relatively simple scripts, you can just use the implicite root target (i.e. put the tasks at root level outside of all other targets).
In short, here's the simplest way to write your script.
<project name="myProject">
<property name="noReportDSUpgrade" value="false" />
<target name="myTarget" if="${noReportDSUpgrade}">
<echo message="Running myTarget" />
</target>
</project>
If you really need an initialization target (note the depends attribute):
<project name="myProject">
<target name="init">
<property name="noReportDSUpgrade" value="false" />
</target>
<target name="myTarget" if="${noReportDSUpgrade}" depends="init">
<echo message="Running myTarget" />
</target>
</project>

How to execute war task only if a property equals to a particular value

I have multiple apps in my environment. I want the code in the build.xml such that the war file is to be built only if a property is equal to a particular value. Here I am reading the property=value pair from the console.
For example, I can assign val1, val2, val3 for a property prop1. But if prop1 is equal to val1 then only the war file is to be generated for the application I have hard coded in the build.xml.
Execute the war task in a conditional target:
<condition property="val1.set">
<equals arg1="${prop1}" arg2="val1" />
</condition>
<target name="build-war-val1" if="val1.set">
<war ... />
</target>
See https://ant.apache.org/manual/targets.html for samples.

Mark the build result as Failed OR Successful

I want to mark the build as successful when the file exist(when I mark ) OR failed when file does not exist (when I mark var name="build-result" value="FAILED" />).
I want to update build status after reading build-result OR by using "build.status" which I am updating depending on build-result as
<var name="build-result" value="SUCCEEDED" />
<echo message="Sending mail status- ${build-result}"/>
<propertyfile file="${build-status.file}">
<entry key="build.status" value="${build-result}" />
</propertyfile>
Currently I am doing in the way:
<isset variable="build-result" value="FAILED" />
</condition>
</fail>
But is giving the message as: BUILD FAILED
D:\projects\Self\AntExample\build.xml:51: isset doesn't support the "variable" attribute
which I want should be like "Build Failed as File Does not Exist"
Always refer to the on line documentation. <isset> takes the parameter property and not variable. Ant doesn't have the concept of variables -- just properties. What the <var/> task does is that it allows you to change a property once it is set. You should not be using <var> except in rare circumstances. As it says on the <var> task's page: In general, use of this task is DISCOURAGED, and the standard Ant Property should be used if possible.
In fact, now that you have <local/> in the list of standard Ant tasks, I find that you no longer really need <var/>.
If you want to fail your build if a file does not exist, look at the <available> test:
<fail message="This build is an utter and complete failure".>
<condition>
<not>
<available file="${result.file}" type="file"/>
</not>
</condition>
</fail>
<echo message="This build is a smashing success! We're so proud!"/>
The <fail> task will execute if the file ${result.file} is not found. Otherwise, the <echo> message will print.
<isset> accepts only one attribute- property and checks whether the specified property has been set or not (i.e. has been provided a value, including null)
See HERE for <isset>
what you may use is <equals> which compares the values of two arguments:
<equals arg1="${build-result}" arg2="FAILED">
See HERE for <equals>
as you've mentioned: I want to mark the build as successful when the file exist you may also want to look at the <available> task,
<available property="result" file="your_file_location" />
See HERE for <available>

Ant: How to set the different value to a property depending on user's input

I am taking user's input using below input task:
<input message="Select the provisioning profile to be used for packaging i.e. old or new" addproperty="provProfileSelected" validargs="o,n" defaultvalue="o" />
Then, I want to set different values to one property depending on the the user's input. I am able to get the user's input. But how to conditionally set the value to the property?
I don't want to use Antt-Contrib in my build script.
Here's something that might work for you. You save the input into one property, then conditionally you set additional properties based the response. You use up 2 extra properties but shouldn't be a problem. old and new targets will be conditionally executed based on the existence of the new property.
Hope this helps!
<project name="testing" basedir="." default="all">
<target name="all" depends="input, old, new"/>
<target name="input">
<input message="Select the provisioning profile to be used for packaging i.e. old or new" addproperty="provProfileSelected" validargs="o,n" defaultvalue="o" />
<echo>${provProfileSelected}</echo>
<condition property="newSelected">
<equals arg1="n" arg2="${provProfileSelected}"/>
</condition>
<condition property="oldSelected">
<equals arg1="o" arg2="${provProfileSelected}"/>
</condition>
</target>
<target name="new" if="newSelected">
<echo>New provisioning selected</echo>
</target>
<target name="old" if="oldSelected">
<echo>Old provisioning selected</echo>
</target>
</project>

Ant condition block

I have an ant condition like this:
<condition property="create_stub">
<and>
<available file="${create_stub_command_file}" property="stub_script.present" />
<isset property="packaged_stub_file"/>
</and>
</condition>
My understanding is: If create_stub_command_file is present then set stub_script.present=true. But I am not sure about
<isset property="packaged_stub_file"/>
What is this doing? And how does it change the overall condition. i.e In which case would the condition block evaluate to true?
A slight mistake?
<condition property="create_stub">
<and>
<available file="${create_stub_command_file}" property="stub_script.present" />
<isset property="packaged_stub_file"/>
</and>
</condition>
I don't believe that property="stub_script.present" is doing anything. It should be:
<condition property="create_stub">
<and>
<available file="${create_stub_command_file}"/>
<isset property="packaged_stub_file"/>
</and>
</condition>
All that condition statement is doing is setting a property called create_stub. It will set the property if both a file or directory called whatever {$create_stub_command_file} exists, and if the property packaged_stuf_file is set to any value. The property packaged_stub_file can be set to false, to a null string, to true, to YES! YES! YES! or to anything, as long as it is set.
So now you can use this property as a test for a target:
<target name="package_stub"
if="create_stub">
<blah...blah...blah/>
<yadda...yadda...yadda/>
</target>
This target, package_stub will only execute if the property package_stub is set. And it will only be set if that <condition> above is true.
That <condition> statement should be outside of any targets, so it will be executed first before any targets are executed.
Equivolent pseudo code:
if (File($create_stub_command_file).exists) then
property["stub_script.present"] := true
end
if (File($create_stub_command_file).exists AND property["property["stub_script.present"] != NULL) then
property["create_stub"] := true
end
Forgive any errors... I find condition blocks tricky and they need lots of testing. You're best advised to keep them simple. ANT is not a programming language.

Resources