Thursday, November 16, 2006

Trac Wiki Macro API Fun

Here is a small snippet of Python code:


import datetime
import time

def execute(hdf, txt, env):
event, when = txt.split(',', 1)
today = datetime.date.today()
future = datetime.date(*time.strptime(when, '%m/%d/%Y')[0:3])
difference = future - today
days = difference.days
if days <= 0:
return event + " has already happened! (" + str(abs(days)) + " days ago.)"
proper = "days"
if days == "1":
proper = "day"
return event + " in " + str(days) + " " + proper + "!"


Small and simple. Dan asked me to write a macro for our Trac wiki that would take in a date (in a string format) and an event name and create a small warning on the page. I've never written any sort of macro for any sort of wiki before, but the macros are written in Python, so I suspected it would be fun and easy. It was both.

The first thing I did was edit the front page of our wiki, adding a call to my soon-to-be macro:

[[CountDown()]]

I saved the changes to the page, and got an error when the page reloaded, which was exactly what I wanted... the api says that you need to restart the webserver, which seemed sort of suspect since you don't need to restart after installing plugins.

I read just enough of the docs to figure out where the macros directory was. Turns out that the macros reside in the rather obvious directory: "/usr/local/share/trac/wiki-macros". I created CountDown.py there and loaded it into vi.

Back to the docs to check out the api. Only function needed in a macro is execute, which takes in an hdf, some text, and an environment. A bare-bones macro looks like this:

def execute(hdf, txt, env):
return "Testing..."

I saved the above and reloaded the page. It worked. Now, for input. Input is passed into execute via the argument txt. Changed the macro call to:

[[CountDown(Tomorrow,11/17/2006)]]

and then changed the macro to:

def execute(hdf, txt, env):
return txt

It returned "Tomorrow,11/17/2006" on the page. I poked around the module docs for datetime and finished the macro as it appears at the top of this post. It was just so painless. Trac has impressed me again.

No comments: