Ottimizza apache / php / mysql in esecuzione su VPS per carichi pesanti


17

Domanda sull'ottimizzazione di un server apache / mysql su un VPS con 512m di RAM. A carico normale tutto funziona veloce, nessun ritardo di connessione. Tuttavia, quando riceviamo giorni di traffico intenso (oltre 50.000 visite), il sito esegue la scansione e ci vogliono 30 secondi + per recuperare i contenuti da Apache.

Il sito è in esecuzione su Expression Engine (CMS) (in PHP) e ho seguito la loro guida all'ottimizzazione dei carichi pesanti. Ho cercato su Google e ne ho seguiti parecchi per apache con un po 'di fortuna, portandolo dove si trova ora, ma ho bisogno di ottenere tempi di risposta costanti.

Suppongo che questo sia diverso dalla domanda "ottimizza per memoria insufficiente" qui, poiché ho abbastanza RAM (per quello che sto cercando di fare), ho solo bisogno che il server non si blocchi con un carico pesante.

Qualche raccomandazione?


1
Solo un seguito: passato a Lighttpd e già la differenza è sorprendente, gestendo il carico molto meglio. Ne conseguiranno altre ottimizzazioni, ma questo mi ha aiutato molto. E stavo usando eaccelerator, che avevo raccolto su APC, da quando mi era stato chiesto.
Parrots,

Risposte:


18

Per PHP ci sono 2 cose importanti che aumenteranno la capacità:

  1. Advanced PHP Caching (APC) come menzionato. Questo è ciò che usiamo su Yahoo !. Ci sono altri progetti simili, ma questo è il bambino di Rasmus.
  2. FastCGI invece di mod_php. C'è un dibattito su questo tema poiché mod_php è di solito il più veloce. Tuttavia, suppongo che tu abbia un singolo server Apache che fornisce sia contenuto PHP dinamico che risorse statiche (JS, CSS, flash, immagini, PDF, ecc.). Le richieste di tali risorse statiche non devono consumare tanta memoria, ma poiché PHP è un modulo è presente in ogni thread di Apache.

Per Apache:

  1. Usa MPM lavoratore
  2. Abilita KeepAlive

Puoi anche andare fino a considerare di passare da Apache a Lighttpd o Nginx . Adoro Apache. Uso il pazzo di molte delle sue funzionalità avanzate. Accetto le sue spese generali perché ho bisogno di ciò che offre. Per lo stack LAMP comune, è più del necessario e uno spreco di risorse.

Per MySQL:

  1. I tuoi sforzi di ottimizzazione pagheranno 10 volte una volta spesi analizzando e correggendo le query, invece di modificare i tuoi valori my.cnf. Non sto dicendo che non è importante che la cache, le connessioni, ecc. Siano corrette ... ma per la maggior parte delle persone è solo il 9% del problema.
  2. Durante il QA, attiva il log delle query generali sul tuo staging / dev mysqld per acquisire tutte le query inviate. (NON farlo sul tuo server mysql di produzione!)
  3. Utilizzare EXPLAIN per analizzare le query. Soprattutto se stai usando un framework con un ORM (estrae il DB e ti impedisce di scrivere il tuo SQL) dovrai eliminare JOINs estranei, SELECT senza clausole WHERE, ORDER BY che inducono "usando filesort" e query che non usano indici.
  4. Se stai usando MySQL 5.1, approfitta del query profiler .

Altri strumenti che vale la pena considerare sono mk-visual-spiegato

Ho citato 10 grandi riferimenti. Queste cose dovrebbero farti canticchiare. Per favore, facci sapere come va.


6

Sposta i tuoi file di sessione PHP su un tmpfs , usa APC (o altro) e rimuovi tutti i moduli PHP che non ti servono. Rimuovi tutti i moduli Apache non necessari / utilizzati.

Per creare un tmpfs (una directory nella RAM!)

mkdir /tmpfs; chmod 777 /tmpfs
mount -t tmpfs -o size=256M tmpfs /tmpfs

In / etc / fstab aggiungi la riga seguente per crearla al riavvio!

tmpfs     /tmpfs    tmpfs   size=256m,mode=0777    0       0

In /etc/apache2/php.ini regolare per memorizzare le sessioni in RAM (tmpfs)!

session.save_handler = files
session.save_path = "/tmpfs"

Nota: con i tuoi file PHP E i file di sessione nella RAM, tocchi a malapena il disco!

Usa expires_module in apache in modo che i browser memorizzino nella cache la maggior parte delle cose.

ExpiresActive On
ExpiresDefault "access plus 90 days"
ExpiresByType image/gif "access plus 90 days"
ExpiresByType image/ico "access plus 90 days"
ExpiresByType image/png "access plus 90 days"
ExpiresByType image/jpeg "access plus 90 days"
ExpiresByType image/x-icon "access plus 90 days"
ExpiresByType text/css "Access plus 90 days"
ExpiresByType text/html "Access plus 90 days"
ExpiresByType application/x-shockwave-flash "Access plus 90 days"
ExpiresByType application/x-javascript "Access plus 90 days"

Non utilizzare i file .htaccess ! Invece, codificali nel file di configurazione vhost! Eliminerà / ridurrà drasticamente i controlli del disco per tutte le richieste http ... si somma davvero.

Options FollowSymLinks 
AllowOverride None

Esempio di .htaccess utilizzato nel file vhost.conf ...

<Directory /home/user/www/site.com/secure>
    Order Allow,Deny
    Deny from All
</Directory>

5

Mi vengono in mente un paio di cose.

La cache Opcode è sempre una buona idea. Preferisco http://eaccelerator.net/ rispetto a APC. Se non hai sviluppato APC lungo la strada, provare ad aggiungerlo è quasi sempre doloroso. L'acceleratore, sebbene non altrettanto sofisticato, sembra funzionare.

Anche un proxy inverso è una buona idea, ma è necessario controllare l'utilizzo della RAM. Trovo che Apache 2.2 con mpm-worker occupi da solo una buona quantità di RAM. Nel tuo caso, consiglierei qualcosa di più leggero come Nginx ed eseguo Apache con PHP come FASTCGI o lo lascio semplicemente come da processo. L'idea di usare Varnish, Squid, Nginx, ecc. È di far sì che servano contenuti statici, gestiscano le connessioni degli utenti e trasmettano le richieste PHP ad Apache che trattate come un server delle applicazioni.

Se stai utilizzando una versione abbastanza recente di Mysql 5.1, come almeno 5.1.24, ora hai accesso a registri secondari lenti. Vorrei iniziare long_query_time a 1 o 2 e poi ridurlo a 0,5 man mano che ottieni una maniglia su quelli veramente lunghi. Ci sono anche molte informazioni di tuning generali in rete per Mysql, ma non hai la RAM per fare molto. Hai aumentato le impostazioni di default? La maggior parte dei file my.cnf predefiniti sono configurati per utilizzare circa 64 MB di RAM. Perlomeno vorrei aumentare il key_buffer da 16 MB a 64 MB.

Inoltre stai usando le tabelle Myisam o Innodb? Se stai mantenendo la sessione nel DB ti consigliamo di cambiare la tabella di sessione in Innodb (o invece di crearla come cookie) anziché lasciarla una tabella Mysiam che esegue il blocco a livello di tabella anziché il blocco a livello di riga. Fondamentalmente qualsiasi tabella che è più del 20% in scrittura all'80% in lettura è un candidato per passare a Innodb. Ricorda che dovrai bilanciare la quantità di RAM tra le tabelle Myisam e le tabelle Innodb perché i buffer per ciascuna sono configurati separatamente.

E infine, altri 512 MB di RAM farebbero molto per la configurazione o addirittura un altro VPS da 512 MB per eseguire Mysql se è più economico o all'incirca allo stesso prezzo. In realtà mi spingerei verso una seconda istanza perché raddoppierà l'IO del disco disponibile. Uno dei problemi con i server VPS è che il tuo IO non è protetto da altre persone sullo stesso server fisico.

Hmmm il mio post è un po 'confuso, ma ti dà molti posti in cui cercare. In bocca al lupo.


2
  • Usa una cache opcode per php come apc.
  • Usa un acceleratore http come calamari o vernici.

1

In una situazione di memoria insufficiente (512 Mb è basso, per un server a traffico elevato) vale la pena considerare la scelta del server Web e del motore DB.

Lighttp è più leggero di quanto Apache possa normalmente essere realizzato dopo molte modifiche e ci sono anche opzioni più leggere di così. Questo ovviamente non è possibile se ci sono funzionalità Apache da cui dipendi che non sono supportate in altri server.

sqlite è molto più stretto di mySQL e più veloce anche in molte condizioni. Controlla se il motore che stai utilizzando supporta questo e se lo prova.

L'altra opzione, l'opzione facile, è quella di ottenere più RAM nella VM se te lo puoi permettere.


1

Oltre ai grandi suggerimenti qui, va notato che tutti i VPS non sono creati uguali. Nella mia esperienza, PHP si è rivelato pesante per la CPU.

Un benchmark Wordpress AB (ab -n 500 -c 25 http://domain.com/index.php ) di nginx / apc / phpfpm / mysql (local) su EC2 ha portato a ~ 2 richieste / secondo sul loro livello di entrata "2GB RAM / 1 Compute Unit Server ".

Lo stesso benchmark viene eseguito sullo stesso stack esatto (distribuito dallo script su un sistema operativo identico) su un Rackspace Cloudserver da 512 MB restituisce ~ 80 req / secondo. Quindi 4x meno RAM, prestazioni 40x in questo rudimentale esperimento.

Guardando in alto durante l'AB si nota che EC2 semplicemente non è in grado di gestire la concorrenza e colpisce immediatamente il 100% del carico della CPU e si blocca. Visualizzando la parte superiore sul server da 512 MB (CPU quad core virtualizzata) con lo stesso benchmark, i core raggiungono il carico del 60% circa e gestiscono senza problemi il benchmark.

I VPS sono estremamente facili da girare e spegnere senza alcun impegno, non fa male mettere alla prova l'infrastruttura della tua VM / VPS!

EDIT 1: Inoltre, l'istanza piccola "High CPU" di EC2 è stata in grado di produrre solo ~ 10 / secondo secondo, con la CPU ancora il collo di bottiglia. La mia conclusione è stata che sacrifichi le prestazioni per stabilità / robustezza con EC2 e, naturalmente, ci sono molti casi d'uso che richiedono un tale ambiente.


inoltre, considera nginx (v.1 rilasciato oggi). wordpress.com ha sostituito la sua configurazione litespeed con nginx, quindi è chiaramente un server web capace.
iainlbc,

Nginx è davvero impressionante. Vorrei solo che potesse leggere le regole di mod_rewrite dai file .htaccess.
Martijn Heemels,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.