服务器只与一个客户端连接,Python Socket

时间:2016-03-27 15:35:23

标签: python multithreading sockets client-server

首先,我希望我写的不是太多。我是新人,我希望没有人怀疑,一切都将为读者清楚。我希望有人可以帮助我。

我已经在套接字服务器和客户端工作了几个星期。随着时间的推移,我添加更多功能。最初,它只是有一个 echo服务器。之后,我做了一个服务器,它返回客户端询问的时间,随机数或其他特定内容。最后,我添加了脚本,因此服务器可以接受2个客户端,以便他们可以在它们之间进行通信。但是,客户端无法写出他想要的消息,因为他总是要等到第二个客户端回答。当我遇到这个问题时,我了解了线程

所以我想要添加的下一个功能就是两个或三个星期之间停留的地方是两个客户端可以不停地发送给彼此的消息而不需要像他们需要的那样等待的部分。

我有一个服务器脚本:

import socket
import threading
from datetime import datetime
from random import randint

global num
num = 0

class serverThread(threading.Thread):
    def __init__(self):
        global num
        num = num + 1
        self.id = num
        threading.Thread.__init__(self)
        client, address = server.accept()
        self.client = client
        self.address = address
        print "serverThread init finished-" + str(self.id)

    def run(self):
        print "r1 num-" + str(self.id)
        size = 1024
        while True:
            #try:
                print "r2*************-" + str(self.id)
                data = self.client.recv(size)
                print "r3..... " + data
                print "r4-" + str(self.id)
                if data:
                    print "r5-" + str(self.id)
                    response = data

                    self.client.send(response)
                    print "r6-" + str(self.id)
                else:
                    print "r7-" + str(self.id)
                    raise Exception('Client disconnected-' + str(self.id) )
            #except:
               # print "Except"
               # self.client.close()
               # return

def create(ipHost, port):
    server = socket.socket()
    server.bind((ipHost, port))
    print "The server was created successfully."
    return server

def listen(server):
    server.listen(5)
    c1 = serverThread()
    c1.start()
    c2 = serverThread()
    c2.start()
    print "finished both threads created"

    while c1.isAlive() and c2.isAlive():
        continue

server = create("0.0.0.0", 1729)
listen(server)

正如您所看到的,我没有使用tryexcept因为我不知道如何使用它们。

我的第二个脚本,客户端:

import socket
import threading

class sendThread(threading.Thread):
    def __init__(self, ip, port):
        threading.Thread.__init__(self)
        self.client = socket.socket()
        self.port = port
        self.ip = ip
        self.client.connect((self.ip, self.port))
        print "[+] New send thread started for "+ip+":"+str(port) + "...Everything went successful!"

    def run(self):
        while True:
            data = raw_input("Enter command:")
            self.client.send("Client sent: " + data)

class receiveThread(threading.Thread):
    def __init__(self, ip, port):
        threading.Thread.__init__(self)
        self.client = socket.socket()
        self.ip = ip
        self.port = port
        self.client.connect((str(self.ip), self.port))
        print "[+] New receive thread started for "+ip+":"+str(port) + "...Everything went successful!"

    def run(self):
        print "Entered run method"
        size = 1024
        while True:
            data = self.client.recv(size)
            if data != "" or data:
                print "A client sent " + data
def client():
    port = 1729
    ip = '127.0.0.1'
    print "Connection from : "+ip+":"+str(port)

    receive = receiveThread(ip, port)
    print "b1"
    receive.start()
    print "b2"
    send = sendThread(ip, port)
    print "b3"
    send.start()
    while send.isAlive() and receive.isAlive():
        continue
    print "-----END of While TRUE------"
    print "Client disconnected..."

client()

我认为描述我的脚本是一个好主意,在我的代码中一步一步地进行,也许它会有所帮助,因此它会更具可读性。

服务器脚本

我创建一个套接字服务器,并调用bind方法。我呼吁使用listen方法并开始接收客户端。我为每个客户创建一个线程,我将接受(accept())和接收(recv)数据。创建每个客户端线程后,我打印一条消息,表明它们已成功创建。当我启动客户端线程时,他们等待接收发送的消息(recv)并发送它。如果我没错,我只需要send方法,而不是告诉发送它。

客户端脚本

客户端将有两个线程。一个用于发送消息(尽可能多),一个用于始终等待另一个客户端发送的消息。

问题

当我想在运行两个客户端之前运行服务器时,它会打印

The server was created successfully.

我运行2个客户端并打印:

Connection from : 127.0.0.1:1720
[+] New receive thread started for 127.0.0.1:1720...Everything went successful!
b1
Entered run method
b2
[+] New send thread started for 127.0.0.1:1720...Everything went successful!
b3
Enter command:

但是,第二个客户端与服务器之间的连接存在问题。当服务器收到客户端发送的消息时,我会这样做,它会将消息作为输出打印在服务器中。但是,当第一个客户端发送消息时,它会打印它。但不是在第二个客户发送时。

我甚至尝试复制客户端脚本并将其放在一个新文件中,因此这两个客户端来自两个不同的文件,可能会发现问题。但是,它没有帮助。我试图运行第一个文件,然后运行第二个文件,反之亦然。第二个客户端始终遇到服务器问题。 (顺便说一句,我也想知道客户端文件为什么不打印他自己发送的消息(他仍然会从服务器接收它)但这是次要问题。)

我希望我没有做太久或太远,希望有人可以帮助我在代码中找到问题。

如果您告诉代码中的问题,我会更高兴,而不是给我一个您创建或找到的问题!

2 个答案:

答案 0 :(得分:1)

我认为可能是因为你有2个线程试图同时接受连接?

您创建第一个线程,然后该线程的init函数接受与socket.accept()的连接。然后,在收到连接之前,您立即创建另一个服务器线程,ALSO在套接字上调用accept()。我的猜测是第二次接听电话未注册,因为1个线程已经锁定了#3;那个对象。

不是立即创建2个线程,也许只有在有人连接到套接字时才尝试创建一个线程?

client = socket.accept()
serverThread1 = serverThread(client)
serverThread2.start()
client = socket.accept()
serverThread2 = serverThread(client)
serverThread2.start()

serverThread类现在将客户端套接字作为构造函数参数。

答案 1 :(得分:0)

您同时使用两个客户端访问服务器。所以要解决这个问题,只需增加一个延迟时间即可。

time.sleep(1)