Domanda

Quelle due biblioteche condividono la filosofia simile e le decisioni di progettazione simili di conseguenza. Ma Questo popolare benchmark wsgi dice che eventlet è il modo più lento di gevent. Cosa farà le loro prestazioni così diverse?

Come so che le differenze chiave tra loro sono:

    .
  • gevent dipende intenzionalmente ed è accoppiato a libev (libevent, in precedenza) mentre eventlet definisce l'interfaccia indipendente del reattore e implementa adattatori particolari utilizzando select, epoll e reattore contorto dietro. L'interfaccia reattore aggiuntiva crea i successi critici?

  • gevent è per lo più scritto in cython mentre eventlet è scritto in Py Py Python. è nativamente compilato cython così più veloce del Pure Python, per i programmi non tali-tanti-computazionali ma IO?

  • primitivi di gevent emula le interfacce delle librerie standard mentre i primitivi generacodictagcode differiscono dallo standard e fornisce uno strato aggiuntivo per emularlo. Fa ulteriore strato di emulazione rende eventlet più lentamente?

  • è l'implementazione di eventlet che peggiore di eventlet.wsgi?

    Mi chiedo davvero, perché sembrano così simili per me.

È stato utile?

Soluzione

Bene, Gevent non è "per lo più" scritto in cython, anche se alcune sezioni critiche sono.

cython fa un'enorme differenza. Le ottimizzazioni del processore funzionano molto meglio con il codice compilato. La previsione del ramo, ad esempio, si distingue nei sistemi basati su VM perché l'indiretta della ramificazione a un livello di esecuzione VM è opaco ad esso. L'impronta della cache è più stretta. Il codice compilato fa una grande differenza qui, e io può essere molto sensibile alla latenza.

In una vena simile, la libev è molto veloce. Stesse ragioni.

Non sembra che WinDlet avrebbe dovuto usare l'hub Select (Python 2.6 di solito predefiniti per EPOLL). Se è stato bloccato su Select, però, ciò renderebbe lento (perché Python deve convertire la selezione FD_SET avanti e indietro su un'elenco Python, quindi diventa brutto quando è nel mezzo di A Loop).

Non ho fatto alcun profilazione, ma sarei disposto a scommettere che Libev / Libevent Plus cython fa la grande differenza. In particolare, alcuni dei primitivi dei threading sono in cython a Gevent. Questo è un grosso problema perché un sacco di codice li tocca indirettamente attraverso Io e persino la libreria standard in alcuni punti.

Per quanto riguarda lo strato di emulazione aggiuntivo di Eventlet, sembra che ci sia molto più buttafuga. A Gevent, il percorso del codice sembra costruire callback e lasciare chiamare l'hub. Eventlet sembra fare più della contabilità che il mozzo sta facendo a Gevent. Di nuovo, però, non l'ho profilato. Per quanto riguarda la scimmia stessa, sembrano abbastanza simili.

Il server WSGI è un altro difficile. In particolare, l'intestazione che analizza in Gevent è rinviata alla Biblioteca Standard, mentre lo implementano in Eventlet. Non sono sicuro se questo è un grande impatto o meno, ma non sarebbe una sorpresa se c'era qualcosa in agguato lì dentro. La maggior parte del quale il server di Eventlet è basato su una versione monkeypatched della Biblioteca standard Beachttsserver. Non riesco a immaginare che questo sia molto ottimale. Gevent implementa un server che è a conoscenza dell'emulazione.

Altri suggerimenti

Scusa per la risposta tardiva.

Ci sono due principali ragioni di grande differenza di prestazioni in tale benchmark :

    .
  • Come affermato prima, i percorsi critici di Gevent sono fortemente ottimizzati
  • che il benchmark fa lo stress test. Non è più legato, perché cerca di rendere la macchina per correre il maggior numero possibile di richieste. Ed è lì che il codice cythonizzato brilla.

    "nel mondo reale" che succede solo durante gli esplosioni di traffico "Slashdot". Il che è importante e uno dovrebbe essere pronto, ma quando succede, reagirai aggiungendo più server o disabilitare le funzionalità pesanti delle risorse. Non ho visto un punto di riferimento che effettivamente aggiunge più server quando il carico aumenta.

    Se, d'altra parte, il benchmark simularebbe un carico "normale giorno" (che varia da un sito Web a un altro) ma generalmente potrebbe essere approssimato per richiedere, pausa casuale, ripetere. Meno che metti in pausa: più il traffico che stiamo simulando. Anche il lato client del benchmark dovrebbe simulare la latenza. Su Linux, questo potrebbe essere fatto utilizzando NetEm impressionante [1], altrimenti, mettendo piccoli ritardi prima del recv / Invia chiamate (che sarebbero molto difficili perché i benchmark di solito utilizzano librerie di livello superiore).

    Ora se quelle condizioni sono soddisfatte, analizzeremmo in realtà i problemi legati a IO. Ma i risultati non sarebbero troppo fantastici: tutti i candidati hanno servito con successo 10, 50 e anche 200 carichi QPS. Noioso, giusto? Quindi potremmo misurare la distribuzione della latenza, il tempo di servire le richieste del 99%, ecc. Gevent mostrerebbe ancora risultati migliori. Ma la differenza sarebbe difficilmente impressionante.

    [1] simulare pacchetti ritardati e caduti su Linux < / P >.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top