Pourquoi voudriez-vous jamais définir MaxKeepAliveRequests sur autre chose que illimité?

11

Apache KeepAliveTimeoutexiste pour fermer une connexion persistante si une nouvelle demande n'est pas émise dans un délai donné. À condition que l'utilisateur ne ferme pas son navigateur / onglet, ce délai (généralement 5 à 15 secondes) ferme éventuellement la plupart des connexions persistantes et empêche le gaspillage des ressources du serveur en conservant les connexions indéfiniment.

Maintenant, la MaxKeepAliveRequestsdirective limite le nombre de requêtes HTTP qu'une seule connexion TCP (laissée ouverte en raison de KeepAlive) servira. La définition de ce paramètre 0signifie qu'un nombre illimité de demandes sont autorisées.

Pourquoi voudriez-vous jamais régler cela sur autre chose que "illimité"? À condition qu'un client fasse toujours activement des demandes, quel mal y a-t-il à les laisser se produire sur la même connexion permanente? Une fois la limite atteinte, les demandes arrivent toujours, juste sur une nouvelle connexion.

À mon avis, il est inutile de limiter cela. Qu'est-ce que je rate?

Jonathon Reinhart
la source

Réponses:

4

Fondamentalement, car Apache n'a pas été conçu pour cela. Le problème est l'utilisation de la mémoire du serveur. Dans de nombreuses configurations, la génération de contenu se fait dans le même processus que la livraison de contenu, de sorte que chaque processus atteindra la taille de la plus grande chose qu'il gère. Imaginez un processus s'étendant à 64 Mo en raison d'un script php lourd, puis ce processus gonflé assis et servant des fichiers statiques. Multipliez maintenant cela par 100. De plus, s'il y a des fuites de mémoire quelque part, les processus se développeront sans limite.

Les paramètres de keepalive doivent être équilibrés en fonction du type de votre contenu et de votre trafic. Généralement, la configuration optimale a MaxKeepAliveRequests haut (100-500) et KeepAliveTimeout bas (2-5) pour les libérer rapidement.

Dirigeable
la source
2

Je sais que c'est une vieille question, mais j'ai fait du débogage, et il semble que (et ce n'est pas seulement vrai pour Apache) MaxKeepAliveRequestsfonctionne indépendamment KeepAliveTimeout.

Cela signifie que la directive timeout ne compte que pour les connexions persistantes inactives (pas de lecture ou d'écriture) - si vous continuez à demander en dessous du délai, vous pouvez virtuellement faire un nombre illimité de requêtes sur la même connexion.

Cela pourrait ne pas être bon pour certaines raisons, y compris les connexions TCP à long terme qui sont tuées au hasard? Dans tous les cas, les clients http ne sont pas si stupides et peuvent très bien gérer un MaxKeepAliveRequestsparamètre "bas" , par exemple, il est relativement facile dans le langage de programmation de détecter si une connexion TCP a été fermée par le serveur et donc de s'y reconnecter à nouveau. De plus, la plupart des clients http auront leurs propres limites (par exemple, les navigateurs fermeraient une connexion permanente après 300 secondes environ).

lifeofguenter
la source
1

L'une des raisons serait l'équilibrage de charge. Une fois qu'une connexion persistante ou persistante http 1.1 est établie, l'équilibreur de charge ne le déplace pas vers un nouvel hôte jusqu'à sa fermeture. Si vous avez un client effectuant un grand nombre de demandes sur sa seule connexion, vous risquez de ne pas obtenir un bon équilibre entre les serveurs.

dtauzell
la source
Mais pourquoi est-ce important? Pour moi, il ne semble pas souhaitable de répartir la connexion d'un seul utilisateur sur plusieurs serveurs. L'équilibrage de charge consiste à gérer un nombre élevé d'utilisateurs, et non des connexions d'un seul utilisateur. En fait - si un seul utilisateur martèle un service, vous préférez qu'il soit confiné à un seul serveur (où il se limiterait effectivement aux taux).
Jonathon Reinhart
1
Bons points. Quelques réflexions: 1. toute autre personne sur ce serveur serait également martelée. 2. Pour les équilibreurs de charge qui fonctionnent en dessous du niveau HTTP: lorsque vous retirez un serveur du pool d'équilibreurs de charge, il ne ferme pas la connexion HTTP existante. Cela rend un peu plus difficile le déplacement de personnes vers un autre serveur avec juste l'équilibreur de charge. La raison 2 est la façon dont je suis arrivé sur cette page en cherchant ce que les gens avaient à dire sur ce paramètre.
dtauzell
1
Une troisième raison: si votre serveur / application se trouve dans un mauvais état et fait une erreur, cet épinglage peut entraîner une erreur de toutes les demandes jusqu'à ce que la situation soit corrigée, tandis que si vous limitez le nombre de chances qu'ils soient équilibrés sur un nouveau serveur .
dtauzell
Je n'ai pas rencontré d'équilibreur de charge qui fonctionne comme ça. Un équilibreur de charge a généralement un paramètre de «collage» qui définit si toutes les demandes du client (déterminées par IP par exemple) dans la session en cours doivent être acheminées vers le même en amont, ou réparties entre les amonts. L'option utile dépend de l'application qui fonctionne en amont.
Manuel
1

En partie, pour empêcher un seul utilisateur de monopoliser tous les emplacements de connexion. Sans limite, un client malveillant ou mal écrit pourrait prendre en charge toutes les connexions disponibles et les conserver indéfiniment. Cependant, ce n'est pas une bonne atténuation par rapport à quelque chose comme une limite de connexion par IP.

Surtout l'équilibrage de charge, mais spécifiquement en ce qui concerne la maintenance. Si vous souhaitez mettre un serveur hors ligne, vous le déposez à 0 connexions mais autorisez les connexions existantes à se terminer pendant un certain temps. Le fait de limiter le nombre de requêtes keepalive signifie que les utilisateurs créeront progressivement une nouvelle connexion et seront déplacés vers un nouveau serveur principal. Il serait probablement préférable de signaler au serveur qu'il devrait cesser d'accepter les Keepalives pendant le processus de vidange, mais pour autant que je sache, une telle fonctionnalité n'existe pas.

Elliott
la source