Search code examples
ant

Defining a task -- or macro -- in ant-script


We have a large build.xml file with some tasks repeated verbatim in multiple targets -- such as a long-winded <echo>, which updates the log-file(s) with contents of an object:

<echo file="foo.log" message="${run.name} completed with status ${run.status}. Errors: ${run.errors}, warnings: ${run.warnings}, processed ${run.processed}"/>

Can this be turned into something like <logrun file="file.log" run=${run}"/> -- in the XML? That is, without us writing Java-code to implement the new logrun-task?


Solution

  • The short answer is yes, using the Ant <macrodef> task.

    Something like this:

    <macrodef name="logrun">
       <attribute name="file"/>
       <attribute name="name"/>
       <attribute name="status"/>
       <attribute name="errors"/>
       <attribute name="warnings"/>
       <attribute name="processed"/>
      <sequential>
        <echo file="@{file}"
              message="@{name} completed with status @{status}. Errors: @{errors}, warnings: @{warnings}, processed @{processed}${line.separator}"/>
      </sequential>
    </macrodef>
    
    <logrun file="foo.log" name="foo.name" status="foo.status" errors="foo.errors" warnings="foo.warnings" processed="foo.processed" />
    

    Notice the way named macro parameters are referenced in the "body" of the macro using @-prefix. I added a ${line.separator} at the end of the message parameter, so that the line written to the file is terminated. You might want to use append="true" in the echo task, in order that the file is not completely overwritten each time the macro is called.

    A macro might cater for all your attribute edge cases, depends how complex they are.