My opinion is that althought it's possible to write many database-driven web apps without using concurrency, concurrency can still be useful.
Vimagi has some real-time features in that rely heavily on concurrency, but it also helps in a more common scenario: speeding up page loads.
In Vimagi, every time someone views a painting or a user profile, a SQL query is executed to increment the view counter for that page. This is more-or-less what the controller code does:
show(A, Id) ->
Painting = find_id(Id),
This caused a problem. When traffic increased, the 'increment' function, which executes an UPDATE statement in the database, started performing poorly, thereby noticeably slowing down page loads. Occasionally, it even timed out after 5 seconds, showing an error screen to the user.
I increased the timeout to 20 seconds. This helped avoid the error screen, but the response time was still too long.
Erlang made this almost too easy to fix. All I had to do was change
It's darn simple, and it works. Instead of executing the UPDATE statement in the process that's responsible for rendering the page, I spawn a new process and execute the transaction there. Spawning processes in Erlang is dirt-cheap, so I don't have to worry about performance or memory issues. The user gets a quick response, the view counter is incremented, and the problem goes away.