Building Plugin Distributions with Ant

I use Ant to build the plugin archives that can be downloaded from my site. Why Ant? Well, while I can manage to get make to compile a couple files, I have more experience with Ant, mostly because that is what we use at work right now.

I keep the build.xml file in a directory named plugins/ off of my home directory on my development machine (a FreeBSD box for those following along at home). It will export the tagged release for the given plugin into a plugins/plugin-envelope-name/ directory, replace all instances of @VERSION@ in the plugin with the version number, move any files in plugins/plugin-envelope-name/php/ to php/plugins/, builds the .tar.gz and .zip files for distribution, and scp's them to my server for download, And to do all that, once I tag a release for a particular plugin, all I have to do is the following:

ant -Dversion=version.number plugin-name

And just for reference, here is a sampling of the MultiBlog repository to show what this script expects:

  • trunk/
    • multiblog.pl
    • lib/
    • php/
    • tmpl/
  • tags/
    • 1.1.1/
    • 1.99.2b/

It may not be perfect, and it is far from complete, but it certainly works well enough for me right now. In the not too distant future, I plan on adding the actual release tagging procedure and automatic updating of the plugin pages with the new version number. At some point, I would like to investigate other build tools, but like I said earlier, this works well enough for me for the time being.

Here is the build.xml file:

<?xml version="1.0"?>
<project default="deploy" basedir=".">

  <property name="svn-exec" value="/usr/local/bin/svn" />
  <property name="svn-proto" value="svn+ssh" />
  <property name="svn-host" value="rayners.org" />
  <property name="svn-base" value="/home/rayners/repos/" />
  <property name="svn-tag-base" value="tags/" />

  <property name="scp-user" value="rayners" />
  <property name="scp-host" value="hostname" />
  <property name="scp-dir" value="/home/rayners/www/plugins/" />

  <property name="ssh-key" value="/home/rayners/.ssh/id_dsa" />
  <property name="ssh-key-pass" value="" />
  <property name="plugin-dir" value="${basedir}/${plugin}" />

  <property name="remote-move-dest-base" value="/home/rayners/www/plugins/" />

  <macrodef name="export-plugin">
    <attribute name="plugin" default="NOT SET" />
    <attribute name="envelope" default="NOT SET" />
    <attribute name="version" default="NOT SET" />
    <sequential>
      <delete dir="${basedir}/@{plugin}" />
      <mkdir dir="${basedir}/@{plugin}/export/plugins" />
      <exec dir="${basedir}/@{plugin}/export" executable="${svn-exec}">
        <arg line="--force export ${svn-proto}://${svn-host}${svn-base}@{plugin}/${svn-tag-base}@{version} plugins/@{envelope}" />
      </exec>
      <replace dir="${basedir}/@{plugin}/export/plugins/@{envelope}" token="@VERSION@" value="@{version}">
        <include name="**/*" />
      </replace>
      <move file="${basedir}/@{plugin}/export/plugins/@{envelope}/php" tofile="${basedir}/@{plugin}/export/php/plugins" />
    </sequential>
  </macrodef>

  <macrodef name="build-plugin-archives">
    <attribute name="plugin" default="NOT SET" />
    <attribute name="version" default="NOT SET" />
    <sequential>
      <zip destfile="${basedir}/@{plugin}/@{plugin}-@{version}.zip"
           basedir="${basedir}/@{plugin}/export/"
      />
      <tar destfile="${basedir}/@{plugin}/@{plugin}-@{version}.tar"
           basedir="${basedir}/@{plugin}/export/"
      />
      <gzip src="${basedir}/@{plugin}/@{plugin}-@{version}.tar"
            destfile="${basedir}/@{plugin}/@{plugin}-@{version}.tar.gz"
      />
      <delete file="${basedir}/@{plugin}/@{plugin}-@{version}.tar" />
    </sequential>
  </macrodef>

  <macrodef name="deploy-archives">
    <attribute name="plugin" default="NOT SET" />
    <attribute name="version" default="NOT SET" />
    <sequential>
      <scp todir="${scp-user}@${scp-host}:${scp-dir}@{plugin}" 
           keyfile="${ssh-key}"
           passphrase="${ssh-key-pass}"
           trust="true">
        <fileset dir="${basedir}/@{plugin}">
          <include name="@{plugin}-@{version}.*" />
        </fileset>
      </scp>
    </sequential>
  </macrodef>

  <macrodef name="deploy-plugin-version">
    <attribute name="plugin" default="NOT SET" />
    <attribute name="envelope" default="NOT SET" />
    <attribute name="version" default="NOT SET" />
    <sequential>
      <export-plugin plugin="@{plugin}"
                     envelope="@{envelope}"
                     version="@{version}" />
      <build-plugin-archives plugin="@{plugin}"
                             version="@{version}" />
      <deploy-archives plugin="@{plugin}"
                       version="@{version}" />
    </sequential>
  </macrodef>

  <target name="multiblog">
    <deploy-plugin-version plugin="multiblog"
                           envelope="MultiBlog"
                           version="${version}" />
  </target>

  <target name="workflow">
    <deploy-plugin-version plugin="workflow"
                           envelope="Workflow"
                           version="${version}" />
  </target>

  <target name="parentcategoryrebuild">
    <deploy-plugin-version plugin="parentcategoryrebuild"
                           envelope="ParentCategoryRebuild"
                           version="${version}" />
  </target>

  <target name="feedburner">
    <deploy-plugin-version plugin="feedburner"
                           envelope="FeedBurner"
                           version="${version}" />
  </target>

  <target name="dropcash">
    <deploy-plugin-version plugin="dropcash"
                           envelope="Dropcash"
                           version="${version}" />
  </target>

</project>

2 Comments

Hi David,

Your multiblog plugin is great. However, I have a question. Right now, it orders the entries on my front page by the blog id in ascending order, whereas I want it to display it chronologically, i.e. the one on top should be the most recent posting, regardless of the blog id. Is this possible in the current version?

Thanks, Ayesha

Hi David

A quick question? I just downloaded multiblog 1.99 from your site and it doesn't contain a .cgi file. Has it been obsoleted? Because after unpacking the files, multiblog doesn't show up in the plugins list on my MT3.17

Thanks!

-bilal

Leave a comment

About Me

I am a software developer for Six Apart living outside of Baltimore, MD. I have written a number of plugins for Movable Type, including the award winning MultiBlog, which has (as of MT 4) been integrated into the base application....
More...

Recent Entries

  • The Olympics Make Me Want To Complete Again

    Every time the Olympics come around (most the summer ones) I always start to delude myself into thinking I could complete once again in the...

  • Minimalist plugins are fun!

    Last night I whipped up one of the smallest plugins I’ve ever written. It is so small in fact that I was able to stuff...

  • Feedburner Widget on MT News

    Movable Type News A WordPress 2.5 Upgrade Guide: And of course there are lots of third-party plugins for the MT dashboard, to integrate statistics and...

  • AD&D Monster Stats for the Presidential Canditates

    Charles Stross (scifi author, D&D nerd, and former perl columnist) posted Politics as she is Played with 3d6: The recent death of Gary Gygax, who...

  • Feedburner Widget 0.3

    At this point, I am really tempted to drop the ‘Widget’ from the name of the plugin, since it is doing so much more...

Close