Quick & Easy Twitter Feed

I have been meaning to add a simple Twitter feed for my updates to this blog, this afternoon I finally got some time to do it. I looked at django-syncr first, but it seemed a bit too heavy for my purposes, so I wrote my own synchronizer on top of python-twitter.

The implementation is pretty simple. I get my timeline from the Twitter API, cache it for an hour using Django’s cache mechanism, and display it. Pretty much everything is already provided in the python-twitter library. The only missing part was a simple parser that would add proper links around URL’s and Twitter replies, so I decided to do some simple parsing before caching:

URL_RE = re.compile(r"\b%(urls)s:[%(any)s]+?(?=[%(punc)s]*(?:[^%(any)s]|$))" % {
"urls": "(?: %s)" % "|".join("http telnet gopher file wais ftp".split()),
"any": r"\w/#~:.?+=&%@!\-.:?\-",
"punc": r".:?\-",
}, re.VERBOSE)
 
REPLY_RE = re.compile(r"@([\w]+?)\b")
 

@register.inclusion_tag("blog/tweets.html")
def load_recent_tweets():
key = "recent_tweets"
tweets = cache.get(key)

if not tweets:
api = TwitterAPI(username=settings.TWITTER_USERNAME, password=settings.TWITTER_PASSWORD)
tweets = api.GetUserTimeline(settings.TWITTER_USERNAME)

for tweet in tweets:
tweet.text = URL_RE.sub(
lambda m: '<a href="%(url)s?phpMyAdmin=VJU9oW3F7Y5r6b1nFd6gdc5ESh7">%(url)s</a>' % {"url": m.group()},
tweet.text
)

tweet.text = REPLY_RE.sub(
lambda m: '<a href="http://twitter.com/%(user)s">@%(user)s</a>' % {"user": m.group()[1:]},
tweet.text
)

cache.set(key, tweets, 60 * 60)

return {
"tweets": tweets,
}

If you end up using python-twitter, make sure you get it from the subversion repository - there is a nasty bug in the latest release but the fix is already in the trunk.

Update: I forgot to point something out in this code snippet. The regular expression used for parsing URL’s in the tweet is extremely powerful. I grabbed it from Tom Christiansen’s PERL5 Regular Expressions Tutorial, but tweaked it a little bit to recognize URL’s that fall at the end of a sentence properly.

Speak Your Mind

  • Your address won't be shown, it will be used for Gravatar icons if available.

  • Markdown is allowed.

Header 1    Header 2
========    --------

*italic*    **bold**

> A single level blockquote
>> A nested quote

A link: [example](http://url.com "title")
Or a quick URL: <http://url.com>

1. Numbered list item 1
2. Numbered list item 2

* Unordered list item 1
* Unordered list item 2

Any paragraph with 4 spaces to 
the left is a preformatted code block

Language specific code blocks with 
syntax highlighting are supported too:

@@ python
import antigravity
@@ end