Archive for March, 2009

Beware jquery $.getJSON on IE

Thursday, March 5th, 2009

I usually like simple APIs and interfaces, so I was naturally drawn to the shortcut methods in JQuery – $.getJSON. It didn’t feel right for it to fail quietly, but I put up with it, thinking that I would go back later and change it to $.ajax calls if it really became a problem.

Well, something I hadn’t noticed really until today is that IE will cache the ajax queries from $.getJSON, but FireFox does not. Unfortunately I don’t see a way to pass the cache:false option to getJSON – so as a rule I’m going to default to using .ajax for two reasons:

  1. You can specify whether to cache or not with option cache:false
  2. You can specify both a timeout and error callback

Python csv chokes on unicode

Tuesday, March 3rd, 2009

Another note to myself.

The python csv module has a bit of trouble writing unicode characters through – at least for me in our current setup.  The workaround is to replace the code > 128 with ?, thus:


response = HttpResponse(mimetype="text/csv")
response["Content-Disposition"] = "attachment; filename=choke.csv"
writer = csv.writer(response)

for line in list:
    writer.writerow([line.something.encode("ascii", "replace"),]

Log exception django decorator

Tuesday, March 3rd, 2009

There is probably a better way to do this, but I was able to throw this together in about two minutes, and I’m writing this here so I can easily reference it no matter where I am. I’ve been writing a lot of REST apis using Django lately, and I need a way to save the exceptions and stack traces to the logs while not giving out too much information to the callers.  I can’t use the automatic email admins functionality because the servers are locked down and not allowed to send email.  Adding try/except’s to the existing functions and new ones feels ugly and painful.  So I’m going with the following decorator.  This one just passes the exception through – you’ll want to figure out if that is the right thing for you to do.


def wrap_ex(fn):
    """ Wraps the api function in an exception log. """
    def _dec(view_func):
        def _wrapit(request, *args, **kwargs):
            try:
                return view_func(request, *args, **kwargs)
            except:
                # log
                cla, exc, trbk = sys.exc_info()
                extb = traceback.format_tb(trbk)
                logging.error(u'An error occurred '+unicode(cla)+u': '+unicode(exc)+ u' tb='+unicode(extb))
                raise
        _wrapit.__doc__ = view_func.__doc__
        _wrapit.__dict__ = view_func.__dict__
        return _wrapit
    return _dec(fn)

Usage:


    @wrap_ex
    @api_login_required
    def api_1_0_calculate(request):
        return JsonResponse(...)