Avec python socketserver comment puis-je passer une variable dans le constructeur de la classe de gestionnaire
Je voudrais passer ma connexion à la base de la EchoHandler classe, cependant je ne peux pas comprendre comment le faire ou accéder à la EchoHandler classe à tous.
classe EchoHandler(SocketServer.StreamRequestHandler): def poignée(self): imprimer soi-même.client_address, "connecté" si __name__ == '__principaux__': conn = MySQLdb.connect (host = "10.0.0.5", user = "utilisateur", passwd = "pass", db = "base de données") SocketServer.ForkingTCPServer.allow_reuse_address = 1 serveur = SocketServer.ForkingTCPServer(('10.0.0.6', 4242), EchoHandler) print "Serveur écoute sur localhost:4242..." essayez: serveur.allow_reuse_address serveur.serve_forever() sauf KeyboardInterrupt: print "\nbailing..."
Vous devez vous connecter pour publier un commentaire.
Malheureusement, il n'y a vraiment pas un moyen facile d'accéder aux gestionnaires directement à partir de l'extérieur du serveur.
Vous avez deux options pour obtenir de l'information à la EchoHandler instances:
server.conn = conn
avant d'appelerserver_forever()
) et ensuite accéder à la propriété dans EchoHandler.gestionnaire parself.server.conn
.finish_request
et attribuer la valeur on (vous auriez à passer au constructeur de EchoHandler et écraser EchoHandler.__init__). C'est un loin messier solution et c'est à peu près vous oblige à stocker la connexion sur le serveur de toute façon.Mon optionon de votre meilleur pari:
Marque T a ceci à dire sur le python archive de la liste de
Dans la classe de gestionnaire, de soi.le serveur se réfère à l'objet serveur, de sorte que la sous-classe
le serveur et le remplacer init à prendre en charge tous les paramètres de serveur
et de les stocker dans des variables d'instance.
super().__init__(...)
au lieu deMyServer.__init__
?Une autre façon, que je crois de plus pythonic, est de faire ce qui suit:
Vous pouvez maintenant donner un instance de votre gestionnaire de la TCPServer:
La TCPServer normalement crée une nouvelle instance de EchoHandler par la demande, mais dans ce cas, le __appel__ méthode sera appelée à la place du constructeur (c'est déjà un exemple.)
Dans le appel méthode, j'ai choisi de faire une copie de l'actuel EchoHandler et la passer au super constructeur pour se conformer à la logique initiale de "un gestionnaire d'instance par requête".
Il vaut la peine d'avoir un coup d'oeil à la SocketServer module de comprendre ce qui se passe ici: https://github.com/python/cpython/blob/2.7/Lib/SocketServer.py
J'étais en train de résoudre le même problème, mais j'ai utilisé légèrement différente de la solution, je pense que c'est un peu plus sympa et plus générale (inspiré par @aramaki).
Dans le
EchoHandler
vous avez juste besoin de remplacer__init__
et d'indiquer lesCreator
méthode.Alors vous pouvez simplement appeler la
Creator
méthode et passer quelque chose dont vous avez besoin.Principal avantage est que de cette façon, vous ne créent pas plus d'instances que nécessaire et vous étendez la classe de façon plus facile à gérer - vous n'avez pas besoin de changer le
Creator
méthode plus jamais.