如何在发送响应后让服务器接受请求?

时间:2017-10-30 00:18:38

标签: python sockets

我有一个连接到服务器套接字的客户端程序,并在server.py文件中发送要评估的字符串。评估完成后,服务器将发回响应。客户端获取响应并显示它,然后将另一个字符串发送到服务器。但是,服务器在评估后不接受任何其他请求。这是server.py文件:

import socket
import logging

logging.basicConfig(level=logging.ERROR)
def binomial(n,m):
    b = 1
    for i in range(0,m):
        b = b * (n-i) // (i+1)
    return b

# 1. Create Socket
port= 12345
listner=socket.socket()

# 2. Bind with ip address and port number
listner.bind(("", port))
# 3. Generate listener
listner.listen(0)
# 4. Waits for a connection request

while True:
    (sock, address)=listner.accept()   # waits for a connection request
                                    # When successful, it returns a socket
                                    # and an address to use to communicate
                                    # with the client
# 4.1 Get data from the client
    print(address)
    logging.info("Connection established with"+str(address))
    bytes = sock.recv(2048)
    client_data=""

    while len(bytes)>0:
        client_data+=bytes.decode()     #UTF-8
        bytes=sock.recv(2048)
# 4.2 Parse the data from the client
    list_of_parts=client_data.split(" ")
    # "12 6"    => ["12", "6"]
    # "12  6"   => ["12", "", "6"]
    # "twelve six" => ["twelve" "six"]
    if len(list_of_parts)!=2:
        # signal an error
        # error response
        response_status="E"
        response_message="Incorrect number of parameters sent"
        logging.error("Incorrect number of parameters sent")
    else:
        try:
            # 4.3 Compute the binomial function
            # try to convert the two elements to numeric
            # compute and generate response
            result=binomial(int(list_of_parts[0]), int(list_of_parts[1]))
            response_status="B"
            response_message=str(result)
        except:
            # signal a coversion problem or computation problem
            # error response
            response_status = "E"
            response_message = "Conversion or computation error"

    # 4.4 Create a response
    message=response_status+response_message
    response_byte=message.encode()
    # 4.5 Send the response to the client
    sock.sendall(response_byte)
    # 4.6 Signal close of the writing side of the socket
    sock.shutdown(1) # signal close of the writing side of the socket

    # 5. close the socket and terminate program
    sock.close()

我收到此错误:

BrokenPipeError: [WinError 10058] A request to send or receive data was disallowed because the socket had already been shut down in that direction with a previous shutdown call

我怎样才能使服务器在第一次响应后接受另一个请求?

1 个答案:

答案 0 :(得分:0)

尝试将接收/发送数据的过程放在循环中。试试这个:

import socket
import logging

logging.basicConfig(level=logging.ERROR)
def binomial(n,m):
    b = 1
    for i in range(0,m):
        b = b * (n-i) // (i+1)
    return b

# 1. Create Socket
port= 12345
listner=socket.socket()

# 2. Bind with ip address and port number
listner.bind(("", port))
# 3. Generate listener
listner.listen(1)
# 4. Waits for a connection request

while True:
    (sock, address) = listner.accept()   # waits for a connection request
                                    # When successful, it returns a socket
                                    # and an address to use to communicate
                                    # with the client
# 4.1 Get data from the client
    print(address)
    logging.info("Connection established with"+str(address))

    while True:
        bytes = sock.recv(2048)
        client_data = ""

        while len(bytes) > 0:
            client_data += bytes.decode()  # UTF-8
            bytes = sock.recv(2048)
            # 4.2 Parse the data from the client
        list_of_parts = client_data.split(" ")
        # "12 6"    => ["12", "6"]
        # "12  6"   => ["12", "", "6"]
        # "twelve six" => ["twelve" "six"]
        if len(list_of_parts) != 2:
            # signal an error
            # error response
            response_status = "E"
            response_message = "Incorrect number of parameters sent"
            logging.error("Incorrect number of parameters sent")
        else:
            try:
                # 4.3 Compute the binomial function
                # try to convert the two elements to numeric
                # compute and generate response
                result = binomial(int(list_of_parts[0]), int(list_of_parts[1]))
                response_status = "B"
                response_message = str(result)
            except:
                # signal a coversion problem or computation problem
                # error response
                response_status = "E"
                response_message = "Conversion or computation error"

        # 4.4 Create a response
        message = response_status + response_message
        response_byte = message.encode()
        # 4.5 Send the response to the client
        sock.sendall(response_byte)
    # 4.6 Signal close of the writing side of the socket
    sock.shutdown(1)  # signal close of the writing side of the socket
    # break this loop when you want
    # 5. close the socket and terminate program
    sock.close()

我希望这有帮助!