views:

397

answers:

3

I am attempting to remove all lines that begin with log if a macrodef attribute is set to prod (example below). I plan on using replaceregexp to remove all lines beginning with log. However, I am not sure how to test if an attribute is set to a specific value, besides using the if task. I would like to not introduce any non-core Ant tasks to perform this, but I can't come up with any other solutions. Do I have any other options besides using the if-task?

Thanks

<macrodef name="setBuildstamp">
    <attribute name="platform" />
    <sequential>
        <if>
            <equals arg1="platform" arg2="prod" />
            <then>
                <replaceregexp match="^log\(.*" value="" />
            </then> 
        </if>
    </sequential>
</macrodef>
+2  A: 

They may be a couple of ways to solve this, but none are as straightforward as using the ant-contrib element. I'm not sure if this will get you what you need for your application, but you could try the following:

Using conditional targets. If you can replace your macrodef with a target to call, this may work for you. Note that this will set the property globally, so it might not work for your application.

<target name="default">
  <condition property="platformIsProd">
    <equals arg1="${platform}" arg2="prod" />
  </condition>
  <antcall target="do-buildstamp" />
</target>
<target name="do-buildstamp" if="platformIsProd">
  <echo>doing prod stuff...</echo>
</target>

Handle the 'else' case. If you need to handle an alternate case, you'll need to provide a few targets...

<target name="default">
  <property name="platform" value="prod" />
  <antcall target="do-buildstamp" />
</target>
<target name="do-buildstamp">
  <condition property="platformIsProd">
    <equals arg1="${platform}" arg2="prod" />
  </condition>
  <antcall target="do-buildstamp-prod" />
  <antcall target="do-buildstamp-other" />
</target>
<target name="do-buildstamp-prod" if="platformIsProd">
  <echo>doing internal prod stuff...</echo>
</target>
<target name="do-buildstamp-other" unless="platformIsProd">
  <echo>doing internal non-prod stuff...</echo>
</target>

Using an external build file. If you need to make multiple calls with different values for your property, you could isolate this in another build file within the same project. This creates a bit of a performance hit, but you would not need the additional library.

in build.xml:

<target name="default">
  <ant antfile="buildstamp.xml" target="do-buildstamp" />
  <ant antfile="buildstamp.xml" target="do-buildstamp">
    <property name="platform" value="prod" />
  </ant>
  <ant antfile="buildstamp.xml" target="do-buildstamp">
    <property name="platform" value="nonprod" />
  </ant>
</target>

in buildstamp.xml:

<condition property="platformIsProd">
  <equals arg1="${platform}" arg2="prod" />
</condition>
<target name="do-buildstamp">
  <antcall target="do-buildstamp-prod" />
  <antcall target="do-buildstamp-other" />
</target>
<target name="do-buildstamp-prod" if="platformIsProd">
  <echo>doing external prod stuff...</echo>
</target>
<target name="do-buildstamp-other" unless="platformIsProd">
  <echo>doing external non-prod stuff...</echo>
</target>

Add ant-contrib to your project. Of course, if you can add a file to your project, the easiest thing would be to just add the ant-contrib.jar file. You could put it under a "tools" folder and pull it in using a taskdef:

<taskdef resource="net/sf/antcontrib/antlib.xml" classpath="${basedir}/tools/ant-contrib.jar" />
jheddings
I decided to take your advice and added the ant-contrib library.
Steve
+2  A: 

You should use a reference to a parameter, like this @{platform}.

Also, your replaceregexp task is missing a few parameters.

I think that in your particular case it is better to use linecontainsregexp filter reader. Here is modified code ( note negate argument to linecontainsregexp ).

<macrodef name="setBuildstamp">
  <attribute name="platform" />
  <sequential>
    <if>
      <equals arg1="@{platform}" arg2="prod" />
      <then>
        <copy todir="dest-dir">
          <fileset dir="src-dir"/>
          <filterchain>
            <linecontainsregexp
              regexp="^log\(.*"
              negate="true"
            />
          </filterchain>
        </copy>
      </then> 
    </if>
  </sequential>
</macrodef>
Alexander Pogrebnyak
Good input on the filtering... I was trying to concentrate on the "using core tasks" portion of the question.
jheddings
A: 

It looks like when you are building your project specifically for your Production environment - you are stripping out code you don't want to run in Production. Thus you are creating a different binary than what will run in your Dev or Testing environment.

How about using an environment variable or property file at run-time instead of build-time which determines whether or not logging happens? This way when you're having trouble in Production and you want to use the same exact binary (instead of determining the revision, checking out the code, rebuilding with a different environment flag) you just re-deploy it to your Dev or Test environment and turn on debugging in a properties file or environment variable?

spilth
We are actually developing a Javascript TV Widget application that has some serious performance restrictions, so we are trying to remove any extra stuff we can.
Steve
Ah, for JavaScript I can see wanted to keep your functions small and lean.
spilth