CodeGym /Courses /Python SELF EN /Socket Module

Socket Module

Python SELF EN
Level 24 , Lesson 1
Available

7.1 What are sockets?

Let's dig a little deeper. First, we learned how to work with request, then http.client, then proxies. What's next? Next, we’ll look under the hood of all these libraries...

A socket (literally — a plug) is a point in the network through which data is sent and received. You can think of a socket as the endpoint of a two-way communication channel between two programs running on the same or different machines.

Sockets support various network protocols, but the two most commonly used are:

  • TCP (Transmission Control Protocol): A reliable protocol that ensures connection establishment, data integrity, and correct sequencing.
  • UDP (User Datagram Protocol): A connectionless protocol that doesn't guarantee data delivery but is faster and more efficient for certain types of applications.

Sockets are identified using an IP address (which identifies a device in the network) and a port (which identifies a specific application or service on the device).

Important! An IP address and port uniquely identify a program on the network. It's like a house address and apartment number. The house address (IP address) is your computer's address on the network, and the port is the apartment number that a program uses to send and receive messages.

You can learn more about what an IP address and port are in lectures dedicated to network infrastructure.

Main stages of working with sockets in a program:

  1. Socket creation: The program creates a socket by specifying the protocol type (TCP or UDP).
  2. Binding to an address: The socket is bound to an IP address and port to be available for connections or to send/receive data.
  3. Listening and establishing connection (for TCP):
    • Listening: The server-side socket is set to listening mode, waiting for incoming connections.
    • Establishing connection: The client initiates a connection with the server. The server accepts the connection, creating a new socket for interacting with the client.
  4. Data exchange: Data is exchanged between the client and server. In the case of TCP, data is transferred reliably.
  5. Closing the connection: After completing the data exchange, the connection is closed.

Advantages of using sockets:

  • Flexibility: Sockets allow applications to exchange data regardless of their location and platform.
  • Performance: Sockets provide a fast and efficient way to transfer data, especially when using UDP.
  • Reliability (in the case of TCP): The TCP protocol ensures reliable data delivery with integrity checks and lost packet recovery.

7.2 Creating a socket server

Working with sockets in Python is done using the built-in module socket, which provides an interface for low-level network programming.

Using sockets, you can create a socket server — an application/object that will receive requests from clients and respond to them. Also, a socket client — an application/object that will send requests to the socket server and receive responses from it.

To create a socket server, you need to do three things:

  1. Create a socket server object.
  2. Bind (bind) it to some IP and port.
  3. Enable listening mode (listen) for incoming messages.

This is what the code will roughly look like:


import socket

# Creating a socket
server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    
# Binding the socket to an address and port
server_socket.bind(('localhost', 12345))
    
# Listening for incoming connections
server_socket.listen(5)
print("Server is waiting for a connection...")

Here, socket.AF_INET indicates that we are using IPv4 for the network protocol, and socket.SOCK_STREAM means we are using TCP. These parameters are most commonly used for creating network applications.

After an incoming message arrives, you need to do four more things:

  1. Accept (accept) the connection with the client.
  2. Receive (receive) the request (data) from the client.
  3. Send (send) a response — some data — to the client.
  4. Close (close) the connection.

This code looks something like this:


# Accepting a new connection
client_socket, client_address = server_socket.accept()
print(f"Connection established with {client_address}")

# Receiving data from the client
data = client_socket.recv(1024)
print(f"Received: {data.decode('utf-8')}")

# Sending data to the client
client_socket.sendall(b'Hello, client!')

# Closing the connection with the client
client_socket.close()

The sendall() method is used instead of send() because it ensures that all the data is sent. The send() method might send only part of the data if the buffer fills up.

The number 1024 in recv(1024) indicates the maximum number of bytes that can be received at one time. This helps control the volume of data processed in one operation.

The code from the last example is typically executed in an infinite loop — the server processes a request, then waits for a new one, processes it, and so on continuously.

If you want to run it on your own or just see a complete example, I'll provide it here:


import socket

# Creating a socket
server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        
# Binding the socket to an address and port
server_socket.bind(('localhost', 12345))
        
# Listening for incoming connections
server_socket.listen(5)
print("Server is waiting for a connection...")
        
while True:
    # Accepting a new connection
    client_socket, client_address = server_socket.accept()
    print(f"Connection established with {client_address}")
        
    # Receiving data from the client
    data = client_socket.recv(1024)
    print(f"Received: {data.decode('utf-8')}")
        
    # Sending data to the client
    client_socket.sendall(b'Hello, client!')
        
    # Closing the connection with the client
    client_socket.close()

7.3 Creating a socket client

We created a socket server, now let's write a socket client that will connect to the server and receive data back from it.

To do this, you need to perform five actions:

  1. Create a socket client object.
  2. Establish a connection (connect) with the IP address and port of our socket server.
  3. Send (send) a message to the server.
  4. Receive (receive) data from the server.
  5. Close (close) the connection.

It's actually simpler than it sounds. Here's what the code will look like:


import socket

# Creating a socket
client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    
# Establishing a connection with the server
client_socket.connect(('localhost', 12345))
    
# Sending data to the server
client_socket.sendall(b'Hello, server!')
    
# Receiving data from the server
data = client_socket.recv(1024)
print(f"Received from the server: {data.decode('utf-8')}")
    
# Closing the socket
client_socket.close()

If there is no socket server running on the other side or the connection is lost, a socket.error exception will be raised. So make sure to handle exceptions.

That's it for working with sockets today.

When working with networks, you will repeatedly encounter hosts, ports, IP addresses, connection establishment, request listening, and so on. Understanding how this works deep down will greatly simplify your life and help you piece together disparate knowledge into a coherent picture.

2
Task
Python SELF EN, level 24, lesson 1
Locked
Creating a Socket Server
Creating a Socket Server
2
Task
Python SELF EN, level 24, lesson 1
Locked
Creating a socket client
Creating a socket client
Comments
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION