DEV Community

All About Python
All About Python

Posted on

Real-Time Chat Application In Python


What's up Pythoneers ! This is Vishesh Dvivedi and in this blog post I am gonna show you how you can create a real-time chat application in python, using tkinter module and socket programming.

This blog will discuss about socket programming, tkinter module and how you can integrate them both.

About the application

The repository of this application consists of two python files, server.py and client.py. server.py is the script that runs the server, which all the clients will use to communicate to each other. And client.py will be used by the client to connect to server and send messages to other clients.

So we will start off by server.py script

Creating server.py

First off, we will import all the required modules of server.py

import socket
import threading
Enter fullscreen mode Exit fullscreen mode

We would need socket module to communicate with clients and threading module to create a thread that would keep listening for messages from clients.

Next we will set up some variables

HOST = '127.0.0.1'
PORT = 1234 
LISTENER_LIMIT = 5
active_clients = []
Enter fullscreen mode Exit fullscreen mode

HOST and PORT here determines the host and port at which the server will run, LISTENER_LIMIT stores the amount of clients that will be able to connect to a server at a time. And finally, active_clients will store all the users that will be connected to the server at any instance

Next we will create the listen_for_messages function

def listen_for_messages(client, username):

    while 1:

        message = client.recv(2048).decode('utf-8')
        if message != '':

            final_msg = username + '~' + message
            send_messages_to_all(final_msg)

        else:
            print(f"The message send from client {username} is 
empty")
Enter fullscreen mode Exit fullscreen mode

This function will keep listening for messages from the connected clients. In case if it received a message, it will call the send_message_to_all function to send the received message to all currently connected clients.

Next we create the send_message_to_client function

def send_message_to_client(client, message):

    client.sendall(message.encode())
Enter fullscreen mode Exit fullscreen mode

This function is used to send message to a single client

Next we create the send_message_to_all function

def send_messages_to_all(message):

    for user in active_clients:

        send_message_to_client(user[1], message)
Enter fullscreen mode Exit fullscreen mode

This function will send a message to all connected clients by calling the send_message function for each connected client.

Next we create the client_handler function

def client_handler(client):

    # Server will listen for client message that will
    # Contain the username
    while 1:

        username = client.recv(2048).decode('utf-8')
        if username != '':
            active_clients.append((username, client))
            prompt_message = "SERVER~" + f"{username} added to 
the chat"
            send_messages_to_all(prompt_message)
            break
        else:
            print("Client username is empty")

    threading.Thread(target=listen_for_messages, args=(client, 
username, )).start()
Enter fullscreen mode Exit fullscreen mode

This function will use the client object (explained later in this blog) which we get when we connect to a client, to get username from a client, add the client to the list of active clients, and start a listener thread which will keep listening for new messages from the client.
Note: This function is also executed as a thread, for each new connected client.

def main():

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


    try:
        server.bind((HOST, PORT))
        print(f"Running the server on {HOST} {PORT}")
    except:
        print(f"Unable to bind to host {HOST} and port 
{PORT}")

    server.listen(LISTENER_LIMIT)

    while 1:

        client, address = server.accept()
    print(f"Successfully connected to client {address[0]} {address[1]}")

    threading.Thread(target=client_handler, args=(client, )).start()


if __name__ == '__main__':
    main()
Enter fullscreen mode Exit fullscreen mode

And finally we have the main function, which performs the work of:

  1. Creating a socket (that acts as the server)
  2. Binding IP and Port to the server
  3. Setting up listener limit
  4. Accept any upcoming connection from clients
  5. Calling the client handler for any new connected client

That's all for the server side code, The server side code is a bit long to explain in a single blog, so I have created this playlist on YouTube, where I explain all the code, both server and client side code. So do check out this playlist to understand the client side code as well.

Link to playlist: How To Create A Real-Time Chat App In Python Using Socket Programming

Discussion (0)