October, 2008


22
Oct 08

Tip: Tracing execution by raising exceptions

This is a quick tip which I have found to be very useful when adding SQLite support to a PHP application which was running on PostgreSQL.

It is nice to have different levels of debugging which can be enabled and disabled independently. Currently I have three debugging facilities:

  • Echoing text messages to a log file. It is nicer than just spitting out text. Also, a file can be easily followed with the help of grep, tail and the plethora of Unix command line tools.
  • Logging of SQL queries and their results. This one is extremely useful to know what the database manager is receiving as input and its raw results. I usually have this disabled, but can avoid serious headache when touching the database schema.
  • Re-raise unhandled exceptions instead of silently logging them. A traceback is sometimes a valuable resource, but you do not want your users to see them when deploying your application.

I have just added the third feature today, and a pair of lines saved me from some hours debugging the exact place where a database error which appeared when using SQLite was triggered. Of course once the application enters production phase, all the debugging code can be disabled by just changing a single variable for each of them :-)

Those were my two cents for today.


17
Oct 08

Intrepid upgrade

So I am right now running Ubuntu 8.10 “Intrepid” in my workstation. In general, the update was smooth, but I have a word of warning: if you use OpenBox as window manager in the GNOME desktop environment, it will stop working. If you try to log in from GDM using the “GNOME/OpenBox” session kind, you will be kicked back to the login screen. As a workaround you can execute openbox --replace from the “Execute” dialog from a regular session as a workaround.


9
Oct 08

On shell builtins

Today I will explain a «misfeature» of the Bash shell which may puzzle you at first sight, but which has its own internal logic. Take the following example:

f () {
  echo "I return false"
  return 1
}

g1 () {
  local v=$(f)
  echo "Exit status is $?"
}

g2 () {
  local v
  v=$(f)
  echo "Exit status is $?"
}

g1
g2

This script would produce the following output:

Exit status is 0
Exit status is 1

You may wonder why the call to g1 does not print 1. The reason is that local is no more than a shell built-in command: first, the command expansion executes and the exit status variable $? is set to 1, but then the local built-in executes and succeeds, and the exit status variable gets set to zero before we inspect it!

The bottom line is: never ever expand a command in the same line where you declare variables.