Also, I use Pypy a lot, and at best I get about a 40-50% speedup. If we factor that into the profiling where I'm showing IO taking up about 5% of the time, that still produces an application that is very much CPU bound.
If there's any point to take from the post, its the historical underpinnings of non-blocking IO, that we use it to poll a bunch of sleeping connections, where we have hundreds or thousands of them. It was never intended to be used on a small set of database connections and I think even if the database calls are slow, it will be very seldom that you'd see asynchronous context switching handling concurrency better than native threads.
There are legitimate usage cases for async patterns, but I have seen them used even in situations where they made things slower.