Многопоточное клиент-серверное приложение

Последнее обновление: 03.05.2023

Многопоточность позволяет одновременно выполнять несколько различных действий в различных потоках. Применение многопточности в серверном приложении позволяет обрабатывать одновременно несколько клиентов. Рассмотрим, как создать многпоточное клиент-серверное приложение.

В Python многопоточность обеспечивается функциональностью модулей _thread и threading. В частности, для запуска нового потока мы можем использовать функцию start_new_thread() из модуля _thread, которая имеет следующее определение:

_thread.start_new_thread(function, args[, kwargs])

Эта функция запускает поток, который выполняет функцию из первого параметра function, передавая ей в качестве аргументов кортеж args. Опционально можно передать словарь дополнительных параметров через третий параметр kwargs

Например, определим в файле server.py следующий код сервера

import socket
from _thread import *

# функция для обработки каждого клиента
def client_thread (con):
    data = con.recv(1024)           # получаем данные от клиента
    message = data.decode()         # преобразуем байты в строку
    print(f"Client sent: {message}")
    message = message[::-1]         # инвертируем строку
    con.send(message.encode())      # отправляем сообщение клиенту
    con.close()                     # закрываем подключение

server = socket.socket()            # создаем объект сокета сервера
hostname = socket.gethostname()     # получаем имя хоста локальной машины
port = 12345                        # устанавливаем порт сервера
server.bind((hostname, port))       # привязываем сокет сервера к хосту и порту
server.listen(5)                    # начинаем прослушиваение входящих подключений

print("Server running")
while True:
    client, _ = server.accept()     # принимаем клиента
    start_new_thread(client_thread, (client, ))     # запускаем поток клиента

Здесь при подключении каждого нового подключения функция start_new_thread() запускает для его обработки функцию client_thread() и передает ей текущего клиента, который хранится в переменной client. В функции client_thread() для примера получаем от клиента строку, инвертируем ее и отправляем обратно клиенту.

Для тестирования сервера определим следующий код клиента:

import socket

client = socket.socket()            # создаем сокет клиента
hostname = socket.gethostname()     # получаем хост локальной машины
port = 12345                        # устанавливаем порт сервера
client.connect((hostname, port))    # подключаемся к серверу
message = input("Input a text: ")   # вводим сообщение
client.send(message.encode())       # отправляем сообщение серверу
data = client.recv(1024)            # получаем данные с сервера
print("Server sent: ", data.decode()) 
client.close()                      # закрываем подключение

Клиент ожидает ввод с консоли строки, которая отправляется серверу. Ответ сервера выводится на консоль.

Запустим сервер, затем запустим клиент. Пример работы. Сервер:

c:\python>python server.py
Server running
Client sent: hello

Клиент:

c:\python>python client.py
Input a text: hello
Server sent:  olleh

c:\python>
Помощь сайту
Юмани:
410011174743222
Перевод на карту
Номер карты:
4048415020898850