RFC 3339 formatting in Python

Update This post is outdated now; I changed a few things in rfc3339.py since this post. I created a page for rfc3339. It contains an up-to-date version & documentation.


For those who don't know, RFC 3339 is a date format aiming to be simple and unambiguous:

1985-04-12T23:20:50.52Z

The date and hour use the ISO format and T is a marker to indicate where the time starts. The Z at the end indicates that the time is expressed in UTC

Non-UTC timezone are expressed like this:

1996-12-19T16:39:57-08:00

The RFC 3339 is used in Atom a feed format, I am planning to implement it for Weblog. I tried to find a function to convert date/time into RFC 3339 strings in Python, and what I found was disappointing:

In the end I decided to write my own RFC 3339 conversion function. Simple, still powerful and documented! Dammit!

Here is a simple use case:

>>> import datetime
>>> import rfc3339
>>> rfc3339.rfc3339(datetime.datetime(2008, 9, 4, 12, 34))
'2008-09-04T12:34:00-07:00'

Download the file: rfc3339.py (See rfc3339.)

Here is the documentation (yes, that's rough), generated via pydoc rfc3339.

Help on module rfc3339:

NAME rfc3339

FILE /home/henry/weblog/weblog/rfc3339.py

DESCRIPTION The function rfc3339 formats dates according to the :RFC:3339. rfc3339 tries to have as much as possible sensible defaults.

FUNCTIONS rfc3339(date, utc=False, use_system_timezone=True) Return a string formatted according to the :RFC:3339. If called with utc=True, it normalizes date to the UTC date. If date does not have any timezone information, uses the local timezone::

        >>> date = datetime.datetime(2008, 4, 2, 20)
        >>> rfc3339(date, utc=True, use_system_timezone=False)
        '2008-04-02T20:00:00Z'
        >>> rfc3339(date) # doctest: +ELLIPSIS
        '2008-04-02T20:00:00...'
    
    If called with `user_system_time=False` don't use the local timezone and
    consider the offset to UTC to be zero::
    
        >>> rfc3339(date, use_system_timezone=False)
        '2008-04-02T20:00:00+00:00'
    
    `date` must be a a `datetime.datetime` or a timestamp as returned by
    `time.time()`::
    
        >>> rfc3339(0, utc=True, use_system_timezone=False)
        '1970-01-01T00:00:00Z'
        >>> rfc3339(datetime.date.today())
        Traceback (most recent call last):
        ...
        TypeError: excepted datetime, got date instead
        >>> rfc3339('foo bar')
        Traceback (most recent call last):
        ...
        TypeError: excepted datetime, got str instead

DATA all = ('rfc3339',) author = 'Henry Precheur <henry@precheur.org>' license = 'Public Domain'

AUTHOR Henry Precheur <henry@precheur.org>

The source code is in the Public domain