Vai più veloce di Rust?

Jan 07 2023
Per favore qualcuno corregga il mio codice o qualcosa del genere, perché sono molto deluso da Rust. Non sparare nemmeno al messaggero qui (sentiti libero di spararmi se è colpa dei miei codici errati).

Per favore qualcuno corregga il mio codice o qualcosa del genere, perché sono molto deluso da Rust. Non sparare nemmeno al messaggero qui (sentiti libero di spararmi se è colpa dei miei codici errati).

So che quasi tutti i confronti delle prestazioni tra Go e Rust mostrano che Rust si comporta meglio, ma lo fa sempre? Non sembra, e in effetti i risultati che condividerò sono prestazioni piuttosto scarse di Rust e con tutto l'hype sono molto deluso.

I risultati di Go sono stati eseguiti congo build && ./go_test

wrk -t 25 -c 100 -d 60s --timeout 8s http://127.0.0.1:8080/test_top25
Running 1m test @ http://127.0.0.1:8080/test_top25
  25 threads and 100 connections
  Thread Stats   Avg      Stdev     Max   +/- Stdev
    Latency     2.37s   399.13ms   4.75s    81.81%
    Req/Sec     2.76      3.37    30.00     86.68%
  2474 requests in 1.00m, 378.22MB read
Requests/sec:     41.18
Transfer/sec:      6.30MB

wrk -t 25 -c 100 -d 60s --timeout 8s http://127.0.0.1:8000/test_top25
Running 1m test @ http://127.0.0.1:8000/test_top25
  25 threads and 100 connections
  Thread Stats   Avg      Stdev     Max   +/- Stdev
    Latency     3.30s   560.20ms   6.08s    76.31%
    Req/Sec     2.75      3.88    30.00     84.61%
  1769 requests in 1.00m, 272.14MB read
Requests/sec:     29.43
Transfer/sec:      4.53MB

Tutti i test delle prestazioni che ho trovato sono con una sorta di dati falsi, le prestazioni di Rust in un'impostazione dell'applicazione del mondo reale non sono così eccezionali come fanno tutti? Sono le casse/librerie utilizzate? Non ne sono sicuro, quindi diamo un'occhiata...

use actix_web::{web, App, HttpResponse, HttpServer};
use sqlx::postgres::PgPoolOptions;
use sqlx::types::JsonValue;

#[derive(sqlx::FromRow, serde::Serialize)]
struct Snapshot {
    Resource: serde_json::Value
}

#[actix_web::main]
async fn main() -> std::io::Result<()> {
    let pool = PgPoolOptions::new()
        .max_connections(25)
        .min_connections(25)
        .connect("<postgres_url>").await
        .expect("Failed to create pool.");

    HttpServer::new(move || {
        App::new()
            .wrap(actix_web::middleware::Compress::default())
            .app_data(web::Data::new(pool.clone()))
            .route("/test_top25", web::get().to(|pool: web::Data<sqlx::PgPool>| async move {
                let rows = sqlx::query_as::<_, Snapshot>("SELECT <query> LIMIT 25")
                    .fetch_all(&**pool).await.unwrap();
                HttpResponse::Ok().json(serde_json::json!({ "message": rows }))
            }))
    })
    .client_request_timeout(std::time::Duration::from_secs(60))
    .bind(("0.0.0.0", 8000))?
    .run().await
}

package main

import (
 "context"
 "fmt"
 "net/http"

 "github.com/gin-gonic/gin"
 "github.com/jackc/pgx/v5"
 "github.com/jackc/pgx/v5/pgxpool"
)

func setupRouter() *gin.Engine {
 r := gin.Default()

 psqlInfo := "<postgres_url>"

 config, err := pgxpool.ParseConfig(psqlInfo)
 config.MaxConns = 25
 config.MinConns = 25

 pool, err := pgxpool.NewWithConfig(context.Background(), config)

 r.GET("/test_top25", func(c *gin.Context) {
  res, err := pool.Query(context.Background(), "SELECT <query> LIMIT 25")

  rows, err := pgx.CollectRows(res, pgx.RowTo[any])

  c.JSON(http.StatusOK, gin.H{
   "message": rows,
  })
 })

 return r
}

func main() {
 r := setupRouter()
 r.Run(":8080")
}

Qualcuno veloce, correggi il mio codice Rust, perché secondo TUTTI gli altri questo non dovrebbe accadere. Pensavo di essere abbastanza decente almeno con Rust, e non ho mai scritto una riga di Go nella mia vita prima d'ora, quindi il fatto che sono stato in grado di ottenere prestazioni migliori da una lingua che sto appena iniziando a imparare è deludente.

Come nota, ho provato questo test con diversi parametri; diverso numero di thread, diverso numero di connessioni, diversi intervalli di tempo, ecc., ma Rust ha battuto Go solo in una serie di circa 15 test.