Unfortunately, there's no good all round solution for upsert in current postgres versions. For our use case (one logger daemon feeding results off a message queue in to a table in an idempotent way) this approach was the simplest and worked the best.
Could have done but coming from a mysql background (i.e. where replace statement is supported), just crafting a simple replace rule was easier/faster to grok and implement. Also helped that the table schema was very unlikely to change much in the future - so we didn't have to worry too much about remembering to keep the rule up to date (and the fact the id column was defined as VARCHAR NOT NULL and had no default assigned to it).