重启后Python Socket客户端崩溃

时间:2014-10-18 13:06:05

标签: python sockets

我使用套接字,select和tkinter创建了一个聊天系统,但是如果客户端重新启动,则在重新启动服务器之前它将无法再次连接。

这是客户端代码:

from tkinter import *
import tkinter.scrolledtext as tkst
import socket
import threading
import time


class myChatProgram(threading.Thread):
    def __init__(self):
        self.root = Tk()
        self.myFrame = Frame(master = self.root)
        self.myFrame.pack(fill='both', expand='yes')
        self.chatArea = tkst.ScrolledText(
        master = self.myFrame,
        wrap   = WORD,
        width  = 50,
        height = 20
        )
        self.chatArea.configure(state='disabled')
        self.chatArea.pack(padx=10, pady=10, fill=BOTH, expand=True)
        self.bottomFrame = Frame(master = self.root)
        self.bottomFrame.pack(fill='x', expand='yes' , side = "bottom")
        self.entryBox = Entry(self.bottomFrame)
        self.entryBox.pack(padx=10, pady=10,fill='x', expand='yes' , side = "left")
        self.entryButton = Button(self.bottomFrame, text = "Send",  command = self.sendText ,padx=10)
        self.entryButton.pack(side = "right")
        self.host = '192.168.1.150'
        self.port = 50003
        threading.Thread.__init__(self)
        self.start()
        self.root.mainloop()     

    def addText(self,message):
        if message != "":
        self.chatArea.configure(state='normal')
        self.chatArea.insert(END, str(message) + "\n")
        self.chatArea.configure(state='disabled')

    def sendText(self):
        message = bytes(self.entryBox.get(),"utf-8")
        self.addText(self.entryBox.get())
        if message:
            self.mySocket.send(message)
            self.entryBox.delete(0, END)


    def run(self):
        self.mySocket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        self.mySocket.connect((self.host,self.port))
        time.sleep(1)
        while True:
            self.addText(str(self.mySocket.recv(4096).decode("utf-8")))
myClass = myChatProgram()

服务器代码是:

import socket
import select
import threading

class server(threading.Thread):
    def __init__(self):
        host = '192.168.1.150'
        port = 50003
        self.server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        self.server.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
        self.server.bind((host,port))
        print("Your ip is {0} ".format(socket.gethostbyname(socket.gethostname())))
        self.server.listen(5)
        self.sockets = []
        self.sockets.append(self.server)
    def main(self):
        while True:
            inputList , outputList , errorList = select.select(self.sockets, [], self.sockets)
            for mySocket in inputList:
                if mySocket == self.server:
                    newClient , addr = self.server.accept()
                    print(addr , " Connected")
                self.sockets.append(newClient)
                else:
                    try:
                        data = mySocket.recv(4096)
                        if data:
                           self.broadcast(mySocket,data)
                        else:
                            print("Connection sent 0 bytes.")
                            mySocket.close()
                            self.sockets.remove(mySocket)
                    except socket.error , e:
                        print("Client disconnected while sending message.")
                        mySocket.close()
                        self.sockets.remove(mySocket)
                        continue
            for mySocket in errorList:
                print("Select flagged client as crashed.")
                mySocket.close()
                self.sockets.remove(mySocket)
                continue


    def broadcast(self,mySocket,message):
        print("sending {0}".format(message))
        for client in self.sockets:
            if client != mySocket and socket != self.server:
                try:
                    client.send(bytes(message,"utf-8"))
                except:
                    client.close()
                    self.sockets.remove(client)
                    continue

myClass = server()          
myClass.main()

错误是:

Exception in thread Thread-1:
Traceback (most recent call last):
  File "C:\Python33\lib\threading.py", line 901, in _bootstrap_inner
    self.run()
  File "F:\Sockets\chatClient.py", line 49, in run
    self.mySocket.connect((self.host,self.port))
ConnectionRefusedError: [WinError 10061] No connection could be made because the target machine    actively refused it

然而,除非客户端重新启动,否则它会正常工作,然后崩溃。有什么想法是错的吗?

1 个答案:

答案 0 :(得分:0)

我猜你必须设置SO_REUSEADDR:

socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)