Skip to main content

Command Palette

Search for a command to run...

Fiber (Go) vs. Nickel.rs (Rust): A Performance Showdown in 'Hello World'

Updated
4 min read
Fiber (Go) vs. Nickel.rs (Rust): A Performance Showdown in 'Hello World'
E

Cloud Native Pilgrim | Kubernetes Enthusiast | Serverless Believer | Customer Experience Architect @ Pulumi | (he/him) | CK{A,AD} |

Introduction

In this article, I want to compare the performance of two different web frameworks for Rust and Go. Both frameworks are very similar in their design (all are inspired by Express.js) and both claim to be the fastest web framework (blazing fast). Both frameworks are easy to use, which is a big plus for me (I am not the smartest guy in the world, so easy is good).

The Competitors in detail

Nickele.rs (Rust)

For Rust, I have chosen the Nickel.rs framework. It is a minimal and lightweight framework for web apps in Rust. It is inspired by Express.js and provides a lot of features like flexible routing, middleware, JSON handling, and more. And it's blazingly fast!

Fiber (Go)

As a contender for Go, I have chosen the Fiber framework. This framework is also inspired by Express.js and is built on top of Fasthttp. It has a lot of features like middleware, routing, WebSockets, and more. And it claims to have extreme performance and a small memory footprint.

The Battle 🥊

The specs of my machine are Apple M1 Max (10 Core CPU) with 32GB of RAM.

The Tests will be written in bombardier and will be executed for 50, 100 and 500 concurrent users with executing 5M requests.

I use the following versions:

  • Go: go1.20.3 darwin/arm64

  • Rust: rustc 1.65.0 (897e37553 2022-11-02)

The Test Code

Nickel.rs (Rust)

#[macro_use]
extern crate nickel;

use nickel::Nickel;

fn main() {
    let mut server = Nickel::new();

    server.utilize(router! {
        get "**" => |_req, _res| {
            "Hello world!"
        }
    });

    server.listen("127.0.0.1:6767").unwrap();
}

Fiber (Go)

package main

import "github.com/gofiber/fiber/v2"

func main() {
    app := fiber.New()

    app.Get("/", func(c *fiber.Ctx) error {
        return c.SendString("Hello, World 🐹!")
    })

    app.Listen(":3000")
}

The Results

50 concurrent users

Fiber (Go)Nickel.rs (Rust)
Time taken140s47s
Request per second35378.09106293.29
Mean response time1.41 ms0.39396 ms
Median response time0.845 ms0.049 ms
90th percentile3.44 ms0.110 ms
Max response time107.07 ms33.91 s
CPU35%18%
Memory11.102 MB4 MB

100 concurrent users

Fiber (Go)Nickel.rs (Rust)
Time taken184s51s
Request per second27073.5597200.03
Mean response time3.69 ms0.92 ms
Median response time2.90 ms0.04 ms
90th percentile7.94 ms0.09400 ms
Max response time136.02 ms29.91 s
CPU35%18%
Memory13 MB4 MB

500 concurrent users

Fiber (Go)Nickel.rs (Rust)
Time taken189s1m
Request per second26359.0583084.80
Mean response time18.97 ms5.00 ms
Median response time18.27 ms0.04 ms
90th percentile31.78 ms0.085 ms
Max response time185.04 ms32.25 s
CPU35%17%
Memory29 MB4 MB

Conclusion 🎉

Based on the data provided, Nickel.rs (Rust) is the winner. There are several reasons for this:

  1. 🚀 Faster response times: Nickel.rs (Rust) has lower mean, median, and 90th percentile response times across all levels of concurrent users compared to Fiber (Go).

  2. ⚡ Higher request per second: Nickel.rs (Rust) can handle more requests per second than Fiber (Go) in each test.

  3. 🌡️ Lower CPU usage: Nickel.rs (Rust) uses less CPU (about half) compared to Fiber (Go) in all tests.

  4. 🧠 Lower memory usage: Nickel.rs (Rust) uses significantly less memory (about 3 to 7 times less) compared to Fiber ( Go) in all tests.

In conclusion, 🏆 Rust (specifically Nickel.rs) outperforms Go (Fiber) in terms of response times, request handling, CPU usage, and memory consumption, making it the winner in this comparison.

Resources

H

Interesting benchmark! Just wondering if you have any context for why the max response time for Nickel.rs can go up to 30s?

E

I can only explain it, that my web server can't handle all the requests/s and timeout. I see some timeouts in the result of bombardier:

Bombarding http://127.0.0.1:6767 with 5000000 request(s) using 50 connection(s)
 5000000 / 5000000 [==================================================================================================================================================================================================================================================================================] 100.00% 106194/s 47s
Done!
Statistics        Avg      Stdev        Max
  Reqs/sec    106292.69   44491.73  224577.53
  Latency      393.78us    91.33ms     33.91s
  Latency Distribution
     50%    43.00us
     75%    63.00us
     90%   103.00us
     95%   170.00us
     99%   642.00us
  HTTP codes:
    1xx - 0, 2xx - 4999962, 3xx - 0, 4xx - 0, 5xx - 0
    others - 38
  Errors:
    dial tcp 127.0.0.1:6767: connect: operation timed out - 38
  Throughput:    21.90MB/s
1
H

Engin Diri It's interesting that the max delay is much lesser in Fiber, thanks for the info! :D