Lumen vs Golang API performance

Published by Dev Kordeš on 07/20/2017

Recently I decided to rewrite backend API for this blog from Laravel (php) to Golang. The performance difference locally seemed huge so I wrote a simple hands-on API to "benchmark" it on production as well.

Live

The Why

I started this blog as a Vue js learning project and since I know Laravel very well I decided to go with that (source) and put a simple API together within a few hours and focused on Vue from there. After successfully implementing authentication, simple image gallery/upload and blog post editor I decided to rewrite the backend in Go. I've started a handful of projects in Go in the past year - a simple birthday reminder, an over-ambitious multiplayer (like it ever got to that point) Hearths card game and an earlier blog - but I never really finished any. Whether it was too ambitious for my poor understanding of core principles or it got to the design phase I had a very good reason not to finish any. Rewriting a simple blog API backend seemed like a good fit.

At some point I had a working frontend and 2 working backend APIs that got their data from the same database. One API was written in Laravel, the other in Go. So I played around and queried them at the same time - and Laravel one took roughly 65ms each time, while the Go one took roughly 5ms each time.

Local

Now let's put that in a (poorly set up, DO $5 droplet) "production" environment.

The How

TLDR: Poorly set up, non scientifically. But hands on! Live

Since I had some small changes to frontend implementation of the blog (auth is now with JWTs, nullable published_at is now a weird 2-value field). I decided to write a new project just for benchmarking this. Since Laravel has a microframework Lumen I decided to use this instead.

Frontend is just a simple Vue js SPA that fetches data from 2 APIs at the same time ish . The implementation favors visualization over correctness.

Database is MySQL on the same droplet.

The Lumen API is served from lumenapi.myprogramming.blog with PHP 7.1 and Apache.

The Go API is served from goapi.myprogramming.blog . The app is built on the server and it serves on port 3001. Apache then proxies incoming requests to this port.

API routes are:

  • /api/first_db_result - fetches 1 row from database
  • /api/all_db_results - fetches all 5 rows from database
  • /api/string_result - simply prints "Lorem ipsum"

Here's the finished product:

The Result

The result was disappointing to say the least. I had no reason to believe that the difference between the two should be in 10x to start with. But due to the huge difference locally I thought it could be at least 2x or something. As you can test live the difference is barely noticable. Maybe 40ms on good attempts.

While I didn't investigate into it any more my guess would be that running Lumen with commandphp -S localhost:8000 -t public really throttles the performance.

The See

Locally

Lumen is served on port 8000 with php -S localhost:8000 -t public. Similar result on every reload.

1 row

Local

5 rows

Local

static text

Local

While npm was installing packages (live)

Only managed to click it once, so this is not representative of anything.

Server

From live version

1 row

Server

5 rows

Server

static text

Server

This website uses  Google Analytics  cookies. Beware.