Ce que j'essaie de résoudre: avoir un serveur Erlang TCP qui écoute sur un port spécifique (le code doit résider dans une sorte d'interface / API externe) et chaque connexion entrante doit être gérée par un Gen_Server < / code> (c'est même le gen_tcp: accepter code> doit être codé à l'intérieur du gen_server code>), mais je ne souhaite pas réellement apparaître un nombre prédéfini de processus acceptant une connexion entrante). Est-ce une en quelque sorte possible? P>
4 Réponses :
Le problème avec gen_tcp: accepter code> est-il en blocs, donc si vous l'appelez dans un Gen_Server code>, vous bloquez le serveur de recevoir d'autres messages. Vous pouvez essayer d'éviter cela en passant un délai d'attente, mais cela constitue finalement une forme de scrutin qui est mieux évitée. Au lieu de cela, vous pouvez essayer GEN_NB_SERVER Kevin Smith à la place; Il utilise une fonction interne non documentée prim_inet: async_accept code> et d'autres prim_inet code> fonction pour éviter le blocage. P>
Mais si je peux comprendre un moyen de relancer le gen_tcp: accepter code> dans son propre Gen_Server que je ne me soucierais pas qu'il bloque. Mais je suppose qu'il n'est pas possible de savoir d'avance (dire de gen_tcp: écouter code>) que vous avez une connexion entrante que vous devez accepter. Merci pour le pointeur de gen_nb_server code>! L'avez-vous utilisé en production?
Je ne pense pas que vous ayez besoin de gen_nb_server code> pour ce que vous faites. Votre cas est vraiment simple.
Je n'ai jamais utilisé gen_nb_server code> dans la production mais avez utilisé prim_inet: async_accept code> dans la production.
J'ai recommandé gen_nb_server code> car la question initiale indiquée gen_server code> comme exigence. Je suis d'accord en utilisant un processus proc_lib code> pourrait être meilleur et plus facile; C'est exactement la façon dont nous reproduisons les accepteurs de Yaws .
Vous devez utiliser "prim_inet: async_accept (listen_socket, -1)" Comme indiqué par Steve. Maintenant, la connexion entrante serait acceptée par votre raccord de guidon_info (En supposant que votre interface est également un Gen_Server) comme vous avez utilisé une asynchrone Accepter l'appel. P>
sur l'acceptation de la connexion, vous pouvez frayer un autre ger_server (je recommanderais GEN_FSM) et faites cela comme le "processus de contrôle" en appelant "GEN_TCP: Controling_process (Clisocket, PID du processus SPWned)". P>
Après que toutes ces données de la prise soient reçues par ce processus plutôt que par votre code d'interface. Comme celui-là un nouveau processus de contrôle serait engendré pour une autre connexion. P>
Juste couper et coller d'ailleurs sans attribution.
Oui, je l'ai coupé et collé de ma propre application Erlang. Dois-je prendre la permission de moi-même pour cela?
Désolé, cela ressemblait à un fragment dans une liste de diffusion de la liste de diffusion sur la première vue.
Sa ok peer..vous avait répondu à une question de mienne pour la même application. :)
Vous devez avoir un processus statique (implémenté sous la forme d'un Remarque: em> strong> vous doit le faire dans cet ordre, sinon le nouveau processus peut utiliser la prise avant que la propriété ait été remis. Si cela n'est pas terminé, l'ancien processus peut obtenir des messages liés à la prise lorsque le nouveau processus a déjà été repris, ce qui entraîne des paquets abandonnés ou mal manipulés. P>
blockQuote>
Le processus d'écoute ne devrait avoir qu'une seule responsabilité, et c'est le frai des travailleurs pour de nouvelles connexions. Ce processus bloquera lors de l'appelant Vous pouvez avoir plusieurs processus en attente avec Une autre optimisation serait de prédéfinir des prises pour minimiser davantage la latence après avoir accepté la nouvelle prise. P> LI>
troisième et finale serait de rendre vos processus plus légers en mettant en œuvre les principes de conception OTP dans vos propres processus personnalisés à l'aide de Gen_Server code> ou d'un processus personnalisé) qui effectue la procédure suivante: p>
gen_tcp: Accepter / 1 Code> li>
Gen_Server code> processus) LI>
GEN_TCP: Controling_Process / 2 Code> une> avec la prise nouvellement retournée et que PID li>
Gen_TCP: Accepter / 1 CODE>, qui va bien, car les travailleurs démarrés géreront des connexions en cours simultanément. Le blocage d'Accepter Assurez-vous du temps de réponse le plus rapide lorsque de nouvelles connexions sont initiées. Si le processus doit faire d'autres choses comprises entre, gen_tcp: Accepter / 2 code> pourrait être utilisé avec d'autres actions entrelées entre les délais d'attente. P>
Échelle h2>
GEN_TCP: Accepter / 1 CODE> sur une seule prise d'écoute, augmenter de plus en plus la concurrence et minimiser la latence d'acceptation. P> LI>
proc_lib code> ( Plus d'infos ). Cependant, cela ne devrait faire que si vous indiquez de référence et que vous allez en conclure que c'est le comportement gen_server code> qui vous ralentit. P> li>
ul>
Merci, je vais essayer cette approche comme il semble que le plus réalisable
Vous voudrez peut-être consulter http://github.com/oscarh/gen_tcpd et utiliser le Manipul_connection Fonction Pour convertir le processus que vous arrivez à un Gen_Server. p>