Skip to content
Apr 26 / Nizam Sayeed

Database independent Django queries: COALESCE vs. NVL, IFNULL, ISNULL

Most of the time, it is not necessary to write raw SQL from Django. However, there are cases where it can’t be avoided.

One common pattern in SQL that always comes up is to check two fields and get the value of the first non-NULL field. In Oracle I’ve used NVL and in MySQL I’ve used IFNULL to do this. In the MS-SQL world, the equivalent command is ISNULL. E.g., I could write the following query for Oracle:

SELECT NVL(ratings_score.score, 0)
FROM ratings_score
WHERE ratings_score.content_type = 1
AND ratings_score.object_id = 5

Or its equivalent for MySQL:

SELECT IFNULL(ratings_score.score, 0)
FROM ratings_score
WHERE ratings_score.content_type = 1
AND ratings_score.object_id = 5

However, I really don’t feel like writing database dependent SQL queries and have them embedded in my Django code. We’re using MySQL right now but we want to have the flexibility to move to PostgreSQL or Oracle in the future, if needed. So I did some digging around and found out that all the major database platforms support another command which essentially does the same thing as NVL, IFNULL and ISNULL (and more!). The command is called COALESCE and it is supported by:

So using COALESCE seems to be the safest way to check two (or more) fields and return the first non-NULL field from a raw SQL query in Django. I can now sleep easy and have piece of mind that if we move to a different RDBMS in the future, our code will not break. Hopefully.

Apr 10 / Nizam Sayeed

CloudBerry: Freeware tool for S3 and CloudFront

I was searching for some information on S3 and CloudFront and found this little gem mentioned in a comment on a discussion forum somewhere.

CloudBerry Explorer makes managing files in Amazon S3 storage EASY. By providing a user interface to Amazon S3 accounts, files, and buckets, CloudBerry lets you manage your files on cloud just as you would on your own local computer.

Visit the CloudBerry S3 Explorer homepage

I’ve started using this tool in favor of the S3Fox plugin for Firefox. Its simply brilliant! And best of all, its FREE!

Screenshot of CloudBerry S3 Explorer

Apr 9 / Nizam Sayeed

Dallas Django 1.1 Sprint

djangoponyDjangonauts of Dallas rejoice! We are joining forces to have our very first Django Sprint event for the upcoming 1.1 release. For more info:

When:
Saturday, April 18, 2009 at 9:00am to Sunday, April 19, 2009 at 5:00pm

Where:
Cohabitat
2517 Thomas Ave.
Dallas, TX

Facebook Event Page:
http://www.facebook.com/event.php?eid=81320026376&ref=nf

Mar 31 / Nizam Sayeed

jQuery minitabs plugin 1.0 released

The jQUery minitabs plugin allows the quick and easy creation of tabbed widgets anywhere on a page. The plugin includes a detailed example and sample CSS to get you started. The plugin supports:

  • specifying the first active tab
  • specifying transition speed for tab changes
  • a callback hook for when a tab is changed

This plugin is based on simpleTabs (http://supercanard.phpnet.org/jquery-test/simpleTabs/) which was originally developed by Jonathan Coulet. This version is simplified a bit and requires simpler HTML.

This is my first foray into the world of writing jQuery plugins so feedback is greatly appreciated.

Download from: http://plugins.jquery.com/project/minitabs

Mar 30 / Nizam Sayeed

UUID template tag for Django

A while back, I had posted a template tag on djangosnippets which generates UUIDs on the fly. I figured that I’d share the same snippet here and explain why I did it.

My rationale for writing this: I needed a quick way to generate random IDs to assign to dynamically generated HTML elements and then use jQuery to wire them all up.

from django.template import Library, Node, TemplateSyntaxError
from uuid import uuid4

register = Library()

class UUIDNode(Node):
    """
    Implements the logic of this tag.
    """
    def __init__(self, var_name):
        self.var_name = var_name
        
    def render(self, context):
        context[self.var_name] = str(uuid4())
        return ''

def do_uuid(parser, token):
    """
    The purpose of this template tag is to generate a random
    UUID and store it in a named context variable.
    
    Sample usage:
        {% uuid var_name %}
        var_name will contain the generated UUID
    """
    try:
        tag_name, var_name = token.split_contents()
    except ValueError:
        raise TemplateSyntaxError, "%r tag requires exactly one argument" % token.contents.split()[0]
    return UUIDNode(var_name)

do_uuid = register.tag('uuid', do_uuid)
Mar 29 / Nizam Sayeed

Using svn:externals for external Django module dependencies

After working on building a fairly complex Django application for the last year or so, I have ended up using a few of the open source Django modules that are out there. Why re-invent the wheel after all?

Most of these projects are thankfully hosted on Google Code which uses Subversion as the source control system. A great feature of SVN is the support for externals definitions. It made my life easier as far as not having to bundle the code for these modules when deploying my app or to store a copy in my own code repository.

So enough with the talk, how do we do this? Easy. Here are the steps:

  • Create a sub-directory under at the root of your Django application called externals or whatever suits your needs.
  • Create a file called svn.externals in this directory.
  • Edit it and create mappings for the external modules and their local checkouts. Example:
    notification http://django-notification.googlecode.com/svn/trunk/notification
    

    The first column is the local directory to checkout to and the second column is the checkout URL. The mappings may point to trunk, any tagged versions or branches.

  • From the externals sub-directory, issue the following command:
    svn propset svn:externals -F svn.externals .
    

    This modifies the svn:externals property for this directory and loads the mapping from the file we created.

  • Issue the following command:
    svn up
    

    To have svn go out and fetch the external modules.

  • I have modified my manage.py script to look like this:
    #!/usr/bin/env python
    from os.path import abspath, dirname, join
    from site import addsitedir
    import sys
    
    # add externals to PYTHONPATH
    sys.path.insert(0, abspath(join(dirname(__file__), 'externals')))
    
    from django.core.management import execute_manager
    try:
        import settings
    except ImportError:
        import sys
        sys.stderr.write("Error: Can't find the file 'settings.py' in the directory containing %r. It appears you've customized things.nYou'll have to run django-admin.py, passing it your settings module.n(If the file settings.py does indeed exist, it's causing an ImportError somehow.)n" % __file__)
        sys.exit(1)
    
    if __name__ == "__main__":
        execute_manager(settings)
    

    Notice that I have added the externals directory to sys.path.

That’s pretty much it. Now, anytime you do an svn up, the specified version from the module maintainer’s code repo.

I would highly recommend checking externals directory as well as the svn.externals file into your local repo. If you add a new mapping later on, you can modify the file and re-issue the svn propset command to update the mappings within svn.

Jan 13 / Nizam Sayeed

Django Gotcha: Never set a variable called ‘user’ in your RequestContext

Okay. So I was working on some view code in a Django project and I noticed something weird. The view started rendering as if the user was no longer logged in. Odd thing was that it was only doing that for that one view. I banged my head for a while and then I realized that I had populated a variable called ‘user’ in the RequestContext for render_to_response. E.g.,

def my_view(request):
    ...
    user_obj = User.objects.get(id = user_id)
    data = { 'user': user_obj }
    ...
    return render_to_response(template, data, context_instance = RequestContext(request))

This caused the default user object that gets set in the request context by django.core.context_processors.auth to be overridden. So stuff like user.is_authenticated stopped working in the templates.

This was my first major Django gotcha.

Jan 6 / Nizam Sayeed

Using Django templates with jQuery AJAX

I recently discovered a neat way of displaying data retrieved using jQuery AJAX in concert with Django’s template engine. You can create a view in Django which simply uses the render_to_response shortcut function to render the results server-side and then just use jquery.load to dynamically fetch the results.

Eventhough, returning some raw JSON data is much more efficient as far as bandwidth is concerned, this method is a lot simpler.

I have been using jQuery for over a year now. I have found that its built-in DOM manipulation features are a bit limited, especially for manipulating tables (e.g., adding rows dynamically). This method is much cleaner than doing all that DOM manipulation.

Here is all the jQuery code to handle the search and AJAX spinner display:

$(document).ready(function() {
	$('#searchSubmit').click(function() {
		q = $('#q').val();
		$('#results').html(' ').load('{% url demo_user_search %}?q=' + q);
	});
});

$(document).ajaxStart(function() {
	$('#spinner').show();
}).ajaxStop(function() {
	$('#spinner').hide();
});

Here is the Django view function that does the heavy lifting on the server-side:

def ajax_user_search(request):
    if request.is_ajax():
        q = request.GET.get('q')
        if q is not None:            
            results = User.objects.filter( 
                Q(first_name__contains = q) |
                Q(last_name__contains = q) |
                Q(username__contains = q)).order_by('username')
            
            template = 'results.html'
            data = {
                'results': results,
            }
            return render_to_response(template, data, 
                context_instance = RequestContext(request))

Here are some screenshots of the results:

AJAX operation in progress

AJAX operation in progress

Returned results

Returned results

No results

No results

The sample Django project is included for your perusal and is released under the MIT license. I used the excellent Aptana Studio IDE when working on this demo so it can be imported straight into it as an Aptana project.

Download ajax_user_list.zip

Dec 26 / Nizam Sayeed

xterm font sizing problems in Cygwin/X 1.5.3

I just installed the latest copy of Cygwin/X X Server on my laptop. I fired up xterm and tried to Ctrl-Right Click to change the font size and lo and behold, it didn’t work!

I searched the web for any one having the same issue but did not find anyone else mention it. My solution (and I am not sure if this is the right one or not) was to create a shortcut to xterm and use the following for the command line options:

C:\Cygwin\bin\run.exe -p /usr/X11R6/bin xterm -display 127.0.0.1:0.0 -ls -bg darkblue -fg azure -fn '*12*'

I like to use a dark blue background with a light blue-ish foreground color in my xterm windows. Anyway, the trick is to add the -fn option at the end. I just used any font of size 12.

Restarted xterm and voila, I can now change the font size as usual. Not sure what was wrong with the base set up but this worked for me.

Dec 22 / Nizam Sayeed

Amazon EC2 test drive

I just tried out Amazon’s Elastic Compute Cloud (EC2) service for the first time today. Its been around for a while and a lot of tech startups have leveraged cloud-based services such as EC2, S3 and others from Amazon to scale up quickly and cheaply.

So far, my experience with EC2 has been quite good. I am evaluating it for a couple of projects I am working on. I love the fact that they recently added (beta) support for Windows server. Sometimes, some client may ask for a .NET-based application and now I have the perfect place to deploy such an app.

What you need to get started

That’s pretty much it. I followed the instructions from the tutorial and everything worked as expected. However, there was one caveat. I had to install the full PuTTy distribution on my Windows system otherwise stuff like the key pair generation and SSH access would not work at all and Elasticfox would not give you any indication as to why not. This little factoid was not mentioned in the tutorial.

I was able to get a Windows server instance up and running in about 15 minutes or so. Thanks Amazon!

Dec 15 / Nizam Sayeed

Hello World!

This is my first blog post, ever. I am kind of a late adopter to the whole blogging thing. So for my first post, I will be testing out the neat syntax highlighting plugin for WordPress. in classic computer science fashion, I will write the quintessential ‘Hello World’ example in some popular programming languages to test this baby out.

Python

print "Hello World"

PHP

echo "Hello World!";

C#

public class HelloWorld
  public static void Main() {
    System.Console.WriteLine("Hello, World!");
  }
}