sendto für tpc ?

Sockets, TCP/IP, (XML-)RPC und ähnliche Themen gehören in dieses Forum
Antworten
l1kegreen
User
Beiträge: 3
Registriert: Freitag 4. Juni 2010, 14:59

Hallo,

Ich versuche gerade ein Chat Programm zu schreiben mit einem GUI.
Es funktioniert im moment so das ich die Clients einzeln verwalte durch das Modul SocketServer.
Jetzt will ich das jeder in der Box die neusten Nachrichten stehen hat.

Bild



z.B.:
[127.0.01] [test1]: blablabla
[192.168.178.41] [test2]: blablablabla

beim Server werden die Nachrichten schon alle ausgegeben nur wie schicke ich die Nachrichten wieder zu jedem verbundenen Client zurück ?
Mit UDP würde ich das so lösen:

Code: Alles auswählen

for x in clients:
    server.socket.sendto(m, x)
Jedoch benutze ich ja TPC. :S
Habt ihr eine Idee ?

Ach ja hier noch die Codes:

Server

Code: Alles auswählen

#! /usr/bin/python

import SocketServer

clients = []

class ChatRequestHandler(SocketServer.BaseRequestHandler):


    def handle(self): 
        addr = self.client_address[0] 
        print "[%s] Verbindung hergestellt" % addr
        clients.append(addr)
        
       
        
        while True: 
            m = self.request.recv(1024) 
            if m: 
                print "[%s] %s" % (addr, m)
                server.socket.send(m)
                
                                            
            else: 
                print "[%s] Verbindung geschlossen" % addr
                clients.remove(addr)
                break

server = SocketServer.ThreadingTCPServer(("", 50000), 
                                         ChatRequestHandler)


server.serve_forever()

Client

Code: Alles auswählen

#! /usr/bin/python

import socket
import sys
from PyQt4 import QtGui
from PyQt4 import QtCore
from main_window import Ui_mainWindow as main
from login_window import Ui_connectWindow as login


class loginWindow(QtGui.QDialog, login):
    def __init__(self):
        QtGui.QDialog.__init__(self)
        self.setupUi(self)

        # Slots
        self.connect(self.connectButton,
                 QtCore.SIGNAL("clicked()"), self.onConnectButton)


    def onConnectButton(self):

        ip = "%s" % self.IP.text()
        nickname = "%s" % self.Nickname.text()
        global nickname
              

        s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        s.connect((ip, 50000))
        

        global s
        
        self.mainw = mainWindow()
        self.mainw.show()
        
        self.close()

class mainWindow(QtGui.QDialog, main):
    def __init__(self):
        QtGui.QDialog.__init__(self)
        self.setupUi(self)

        

        #Slots
        self.connect(self.sendbutton,
                     QtCore.SIGNAL("clicked()"), self.onSendButton)

    def onSendButton(self):
        

        nachricht = self.inputtext.text()
        txt = "[%s]: %s" % (nickname,nachricht)

        try:
            s.send(txt)
            txtforbox = s.recv(1024)
            self.textBox.setText(txtforbox)

        except socket.error:
            login.show()
            self.close()
            


app = QtGui.QApplication(sys.argv)
app.setQuitOnLastWindowClosed(True)
login = loginWindow() 
login.show() 
sys.exit(app.exec_())
s.close()
rads
User
Beiträge: 153
Registriert: Freitag 26. März 2010, 15:51

verdammt schon so spät,
hab ich jetzt lange gebraucht um zu verstehen was du mit tpc meinst.

An sich ist die Socket Kommunikation nicht so furchbar unterschiedlich
bei tcp und udp (ich möchte jetzt bitte keine Belehrung über die essentiellen
Unterschiede von UDP und TCP). An sich bekommst du ja eingehende
Socketverbindunge welche du dir "merken" musst und über welche
du dann Nachrichten empfangen (was ja bei dir schon geht?) und
versenen kannst.

Schau mal ob dir
http://docs.python.org/howto/sockets.html
weiterhilft.

Ansonsten meld dich einfach nochmal, dann kann ich nach einenm Beispiel
schauen.

Ansonsten könntest du dir überlegen, ob dir Python Remote Objects nicht mehr
Freude bereiten würde.
http://www.xs4all.nl/~irmen/pyro3/

Grüße
l1kegreen
User
Beiträge: 3
Registriert: Freitag 4. Juni 2010, 14:59

Also durch SocketServer wird jeder Client ja in einem eigenen Thread behandelt und jeder Client kann jetzt auch schon Nachrichten zum Server schicken. Nun will ich aber das jeder Client der momentan eine Verbindung zum Server hat die Nachrichten die von verschiedenen anderen Clients kommen eben in seiner Box wie oben auf dem Bild sieht. Jedoch kann ich keine Nachrichten vom server zum client zurück senden. Da kommt folgender Fehler:
error: [Errno 10057] Eine Anforderung zum Senden oder Empfangen von Daten wurde verhindert, da der Socket nicht verbunden ist und (beim Senden über einen Datagrammsocket mit einem sendto-Aufruf) keine Adresse angegeben wurde
Ich danke dir trotzdem schon mal für deine Hilfe.
waki
User
Beiträge: 133
Registriert: Dienstag 9. März 2010, 16:41

Also ich nutze immer ein ganz einfaches Gerüst, mit welchem ich mehrere Clients verwalten kann und Nachrichten schreiben + Empfangen....

Server

Code: Alles auswählen

import socket 
import select

server = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 
server.bind(("", 50000)) 
server.listen(1)

clients = []

try: 
    while True: 
        lesen, schreiben, oob = select.select([server] + clients, 
                                              [], [])

        for sock in lesen: 
            if sock is server: 
                client, addr = server.accept() 
                clients.append(client) 
                print "+++ Client %s verbunden" % addr[0] 
            else: 
                nachricht = sock.recv(1024) 
                ip = sock.getpeername()[0] 
                      if nachricht:
                      print "[%s] %s" % (addr, nachricht)
                server.socket.send(nachricht)

                else: 
                    print "+++ Verbindung zu %s beendet" % ip 
                    sock.close() 
                    clients.remove(sock) 
finally: 
    for c in clients: 
        c.close() 
    server.close()

Client

Code: Alles auswählen

import socket
import sys
from PyQt4 import QtGui
from PyQt4 import QtCore
from main_window import Ui_mainWindow as main
from login_window import Ui_connectWindow as login



class loginWindow(QtGui.QDialog, login):
    def __init__(self):
        QtGui.QDialog.__init__(self)
        self.setupUi(self)

        # Slots
        self.connect(self.connectButton,
                 QtCore.SIGNAL("clicked()"), self.onConnectButton)


    def onConnectButton(self):
        global ip
        global nickname
        ip = "%s" % self.IP.text()
        nickname = "%s" % self.Nickname.text()
  
             
       
        self.mainw = mainWindow()
        self.mainw.show()
       
        self.close()


class mainWindow(QtGui.QDialog, main):
    def __init__(self):
        QtGui.QDialog.__init__(self)
        self.setupUi(self)

       

        #Slots
        self.connect(self.sendbutton,
                     QtCore.SIGNAL("clicked()"), self.onSendButton)

    def onSendButton(self):
       

        nachricht = self.inputtext.text()
        txt = "[%s]: %s" % (nickname,nachricht)

        try:
            sock.send(txt)
            txtforbox = s.recv(1024)
            self.textBox.setText(txtforbox)

        except socket.error:
            login.show()
            self.close()

sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 
sock.connect((ip, 50000))

try: 
    while True: 
        app = QtGui.QApplication(sys.argv)
        app.setQuitOnLastWindowClosed(True)
        login = loginWindow()
        login.show()
        sys.exit(app.exec_())
        s.close()
finally: 
    sock.close()
so und per sock.recv() und sock.send() kannst du dann mit denen dann Nachrichten verschicken.
habs jetzt eifnfach mal schnell dein script eingebaut, ich übernhem keine garatie das es so funktioniert, aber so ungefähr müsste es klappen ^^
Zuletzt geändert von waki am Dienstag 27. Juli 2010, 14:35, insgesamt 7-mal geändert.
l1kegreen
User
Beiträge: 3
Registriert: Freitag 4. Juni 2010, 14:59

Werd ich gleich testen ! :D
Ich danke dir (;
waki
User
Beiträge: 133
Registriert: Dienstag 9. März 2010, 16:41

hab mal deinen code oben eingefügt, aber nur auf die schnelle, keine ahnung ob er funktioniert...
ms4py
User
Beiträge: 1178
Registriert: Montag 19. Januar 2009, 09:37

waki hat geschrieben:hab mal deinen code oben eingefügt, aber nur auf die schnelle, keine ahnung ob er funktioniert...
Beim Server stimmt was nicht mit der Einrückung...
„Lieber von den Richtigen kritisiert als von den Falschen gelobt werden.“
Gerhard Kocher

http://ms4py.org/
Dav1d
User
Beiträge: 1437
Registriert: Donnerstag 30. Juli 2009, 12:03
Kontaktdaten:

ms4py hat geschrieben:
waki hat geschrieben:hab mal deinen code oben eingefügt, aber nur auf die schnelle, keine ahnung ob er funktioniert...
Beim Server stimmt was nicht mit der Einrückung...
Da ist wohl GalileoComputing dran schuld: http://openbook.galileocomputing.de/pyt ... a363939704
the more they change the more they stay the same
waki
User
Beiträge: 133
Registriert: Dienstag 9. März 2010, 16:41

nope ich, konnte wenn ich hier im editor den code verendert hab, die tab taste nicht verwenden, also hab ich einfach paar leerzeich verwendet...
aber das sollte er selber beheben können.


€: Server sollte so funktionieren, client aknn ich nicht testen, hab die ui_dateien nicht.
Antworten