Home > other >  How to send request disconnect from server to all clients and server still live (python socket)
How to send request disconnect from server to all clients and server still live (python socket)

Time:12-21

When I disconnect all clients in server, server doesn't continue live. How can I do for living server

import socket, threading, tkinter

Server

import socket, threading, tkinter
import time

def sendDisconnectAll(my_clients):
    for client in my_clients:
        conn = client[0]
        conn.sendall('Disconnect'.encode('utf8'))
        conn.close()
    
def handle_client(conn, addr):
    while True:
        try:
            request_from_clients = conn.recv(1024).decode('utf8') #sample request
            print(request_from_clients)
            if request_from_clients == 'SignIn':
                conn.sendall('Accept Sign in'.encode('utf8'))
        except:
            print('Client has been shutdown')
            break

my_clients = []
def live_server():
    global thr
    global s
    while True:
        try:
            conn, addr = s.accept()
            my_clients.append((conn, addr))
            thr = threading.Thread(target=handle_client, args=(conn, addr))
            thr.daemon = True
            thr.start()
        except:
            print("Error")

HOST = '127.0.0.1'
PORT = 8000
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind((HOST, PORT))
s.listen()
print('HOST: ', HOST)
print('PORT: ', PORT)

thr = threading.Thread(target=live_server)
thr.daemon = True
thr.start()
count_time = time.time()
while True:
    now = time.time()
    if (int(now - count_time)   1) % 10 == 0:       #Disconnect all clients after 10 seconds
        count_time = now
        request = 'Disconnect'
        print('Disconnect all')
        sendDisconnectAll(my_clients)

Clients

import socket, threading
import tkinter as tk
from tkinter import *

def signIn():
    global client
    request = 'SignIn'
    try:
        client.sendall(request.encode('utf8'))
        client.recv(1024).decode('utf8')
    except:
        print('Server has been shutdown')

IP = input("Enter IP: ")
PORT = input("Enter PORT: ")

client = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

try:
    client.connect((IP, int(PORT)))
except:
    print("Can't connect to server")
    client.close()
def live_client():
    global client
    while True:
        print(client.recv(1024).decode('utf8'))
thr = threading.Thread(target=live_client)
thr.daemon = True
thr.start()
app = Tk()
app.title('CLIENT')
but_connect = tk.Button(app, text="SIGN IN",
                            width=20, command=signIn)
but_connect.pack(pady=6)
app.mainloop()

Thank you!

CodePudding user response:

The problem is that you only add clients to the my_clients list. Let's look what happens in server:

  • server starts
  • it receives one client an adds it to my_clients
  • on next disconnect all operation the socket for that client is closed, but the client remains on the list
  • on the following disconnect all operation, the main thread of the server tries to write to a closed socket and raises an exception
  • as all other threads are daemonic, the application ends.

You must clear the my_clients list after closing all the client sockets:

def sendDisconnectAll(my_clients):
    for client in my_clients:
        conn = client[0]
        conn.sendall('Disconnect'.encode('utf8'))
        conn.close()
    my_clients.clear()

Beware: I did not look at client code...

  • Related