2016-09-09 11 views
0

Я играю с сокетом и пытался создать простой чат-сервер только с одним клиентским соединением. Код и вывод следующим образом.Как исправить сломанную трубу на сервере чата, используя сокет в Python после первого запроса?

echo_server.py

import socket 

host = '' 
port = 4538 
backlog = 5 
size = 1024 

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 
s.bind((host,port)) 
s.listen(backlog) 
print "Starting Server" 

while 1: 
    client, address = s.accept() 
    try: 
     data = client.recv(size) 
     if data is not None: 
     if data is 'q': 
     print "I received request to close the connection" 
     client.send('q') 
       continue 
     print "I got this from client {}".format(data) 
      client.send(data) 
      continue 
      if data == 0: 
       client.close() 
    finally: 
     client.close() 

echo_client.py

import socket 

host = '' 
port = 4538 

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 
s.connect((host,port)) 

try: 
    while 1: 
     message = filename = raw_input('Enter a your message: ') 
    s.send(message) 
    data = s.recv(1024) 
     if data is 'q': 
     print "You requested to close the connection" 
      break 
    print "Received from socket {}".format(data) 
finally: 
    s.close() 

Теперь я попытался с SendAll() тоже, но это не работает. Ниже приведен результат с обеих сторон

клиент:

Enter a your message: hello 
Received from socket hello 
Enter a your message: world 
Received from socket 
Enter a your message: hi 
Traceback (most recent call last): 
    File "echo_client.py", line 12, in <module> 
    s.send(message) 
socket.error: [Errno 32] Broken pipe 

А на сервере

Starting Server 
I got this from client hello 

Как вы можете видеть, сервер не получает второе сообщение (мир). И ничего не отвечает и когда я отправляю третий запрос на сервер с привет, клиент завершается Broken Pipe Как мне его исправить?

EDIT 1:

Я изменил код теперь он следующий. S.accept() застревает во втором запросе. Ниже приведен код. echo_server.py

import socket 

host = '' 
port = 4538 
backlog = 5 
size = 1024 

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 
s.bind((host,port)) 
s.listen(backlog) 
print "Starting Server" 

try: 
    while 1: 
    print "BEFORE REQUEST" 
     client, address = s.accept() 
    print "AFTER REQUEST" 
     data = client.recv(size) 
     if data: 
     if data is 'q': 
       print "I received request to close the connection" 
      client.send('q') 
     print "I got this from client {}".format(data) 
      client.send(data) 
     else: 
     print "CLOSING IN ELSE" 
      client.close() 
except: 
    print "CLOSING IN except" 
    client.close() 

Ниже приводится выход.

BEFORE REQUEST 
AFTER REQUEST 
I got this from client hello 
BEFORE REQUEST 

Как вы можете видеть второй раз accept() никогда не возвращается. Как заставить его работать?

+0

Исправить ваши отступы. Этот код не будет работать. –

+2

Вы всегда закрываете соединение на сервере - всегда выполняется условие 'finally' блока' try' (исключение или нет) ... Похоже, вы хотите закрыть соединение и разбить цикл с помощью 'except' вместо этого ... –

+0

Ваш отступ по-прежнему не отображается должным образом. Удалите вкладки из кода и оттащите его. –

ответ

1

recv возвращает пустую строку, когда клиент закрывает соединение, а не None или 0. Поскольку пустая строка является ложным условием, просто используйте if data: или if not data:.

И, как @JonClements отметил, использовать except вместо finally на сервере, или положить while внутри try и if not data: break, чтобы выйти из while и выполнить finally.

+0

Я сделал упомянутые изменения. Но теперь, когда я отправляю второе сообщение, он застревает. Выход ниже клиента: - Введите Ваше сообщение: Здравствуйте Получено от сокета Привет Введите ваше сообщение: World сервер: - Запуск сервера Я получил от этого клиента Привет Он не получает второе сообщение (World) @mark –

+0

Получил это. Я поместил data = client.recv (размер) и некоторые строки после этого в 1:, и тогда он работал, как ожидалось. –