diff --git a/docs/python/Networking/_category.json b/docs/python/Networking/_category.json new file mode 100644 index 000000000..2eddd4416 --- /dev/null +++ b/docs/python/Networking/_category.json @@ -0,0 +1,8 @@ +{ + "label": "Networking in Python", + "position": 2, + "link": { + "type": "generated-index", + "description": "In this section, you will learn about Networking in Python. You will explore various libraries and methods to handle networking tasks such as socket programming, HTTP requests, and more." + } +} diff --git a/docs/python/Networking/generics.md b/docs/python/Networking/generics.md new file mode 100644 index 000000000..ac54068d2 --- /dev/null +++ b/docs/python/Networking/generics.md @@ -0,0 +1,88 @@ +--- +id: generics +title: Generics +sidebar_label: Generics +sidebar_position: 4 +tags: [python, generics, type hints, type safety, code flexibility] +description: In this tutorial, you will learn about generics in Python. We will cover how to define functions, classes, or methods that can operate on multiple types while maintaining type safety using type hints and type variables. +--- + +In Python, generics is a mechanism with which you to define functions, classes, or methods that can operate on multiple types while maintaining type safety. With the implementation of Generics enable it is possible to write reusable code that can be used with different data types. It ensures promoting code flexibility and type correctness. + +Generics in Python are implemented using type hints. This feature was introduced in Python with version 3.5 onwards. + +Normally, you don't need to declare a variable type. The type is determined dynamically by the value assigned to it. Python's interpreter doesn't perform type checks and hence it may raise runtime exceptions. + +Python's new type hinting feature helps in prompting the user with the expected type of the parameters to be passed. + +Type hints allow you to specify the expected types of variables, function arguments, and return values. Generics extend this capability by introducing type variables, which represent generic types that can be replaced with specific types when using the generic function or class. + +## Example 1 + +Let us have a look at the following example that defines a generic function − + +```python +from typing import List, TypeVar + +T = TypeVar('T') + +def reverse(items: List[T]) -> List[T]: + return items[::-1] +``` + +Here, we define a generic function called 'reverse'. The function takes a list ('List[T]') as an argument and returns a list of the same type. The type variable 'T' represents the generic type, which will be replaced with a specific type when the function is used. + +## Example 2 + +The function `reverse()` function is called with different data types − + +```python +numbers = [1, 2, 3, 4, 5] +reversed_numbers = reverse(numbers) +print(reversed_numbers) + +fruits = ['apple', 'banana', 'cherry'] +reversed_fruits = reverse(fruits) +print(reversed_fruits) +``` + +It will produce the following output − + +``` +[5, 4, 3, 2, 1] +['cherry', 'banana', 'apple'] +``` + +## Example 3 + +The following example uses generics with a generic class − + +```python +from typing import TypeVar, Generic + +T = TypeVar('T') + +class Box(Generic[T]): + def __init__(self, item: T): + self.item = item + + def get_item(self) -> T: + return self.item +``` + +Let us create objects of the above generic class with `int` and `str` type + +```python +box1 = Box(42) +print(box1.get_item()) + +box2 = Box('Hello') +print(box2.get_item()) +``` + +It will produce the following output − + +``` +42 +Hello +``` \ No newline at end of file diff --git a/docs/python/Networking/networking-programming.md b/docs/python/Networking/networking-programming.md new file mode 100644 index 000000000..8f3ea9c96 --- /dev/null +++ b/docs/python/Networking/networking-programming.md @@ -0,0 +1,31 @@ +--- +id: networking-programming +title: Network Programming +sidebar_label: Network Programming +sidebar_position: 1 +tags: [python, networking, socket programming, TCP, UDP, network protocols] +description: In this tutorial, you will learn about network programming in Python. We will cover the basics of sockets, higher-level network protocols, and the corresponding Python modules for these protocols. +--- + +# Python - Network Programming + +The threading module in Python's standard library is capable of handling multiple threads and their interaction within a single process. Communication between two processes running on the same machine is handled by Unix domain sockets, whereas for the processes running on different machines connected with TCP (Transmission Control Protocol), Internet domain sockets are used. + +![Image](https://www.tutorialspoint.com/python/images/network_programming.jpg) + +Python's standard library consists of various built-in modules that support interprocess communication and networking. Python provides two levels of access to the network services. At a low level, you can access the basic socket support in the underlying operating system, which allows you to implement clients and servers for both connection-oriented and connectionless protocols. + +Python also has libraries that provide higher-level access to specific application-level network protocols, such as FTP, HTTP, and so on. + +## Network Protocols and Corresponding Python Modules + +| Protocol | Common Function | Port No | Python Module | +|----------|-----------------|---------|---------------| +| HTTP | Web pages | 80 | `httplib`, `urllib`, `xmlrpclib` | +| NNTP | Usenet news | 119 | `nntplib` | +| FTP | File transfers | 20 | `ftplib`, `urllib` | +| SMTP | Sending email | 25 | `smtplib` | +| POP3 | Fetching email | 110 | `poplib` | +| IMAP4 | Fetching email | 143 | `imaplib` | +| Telnet | Command lines | 23 | `telnetlib` | +| Gopher | Document transfers | 70 | `gopherlib`, `urllib` | diff --git a/docs/python/Networking/socket-programming.md b/docs/python/Networking/socket-programming.md new file mode 100644 index 000000000..eb47b9959 --- /dev/null +++ b/docs/python/Networking/socket-programming.md @@ -0,0 +1,279 @@ +--- +id: socket-programming +title: Python - Socket Programming +sidebar_label: Socket Programming +sidebar_position: 2 +tags: [python, socket, networking, programming, python socket, client-server] +description: This tutorial covers the basics of socket programming in Python, including how to create server and client sockets, and transfer data between them. +--- + +# Python - Socket Programming + +The `socket` module in the standard library includes functionality required for communication between server and client at the hardware level. This module provides access to the BSD socket interface and is available on all operating systems such as Linux, Windows, and MacOS. + +## What are Sockets? + +Sockets are the endpoints of a bidirectional communications channel. They may communicate within a process, between processes on the same machine, or between processes on different continents. A socket is identified by the combination of an IP address and port number, and should be properly configured at both ends to begin communication. + +![connection image](https://www.tutorialspoint.com/python/images/connection.jpg) + +![ip address image](https://www.tutorialspoint.com/python/images/ip_address.jpg) + +### Connection Types + +Sockets may be implemented over different channel types: Unix domain sockets, TCP, UDP, etc. The `socket` library provides specific classes for handling common transports as well as a generic interface for handling others. + +The term "socket programming" implies programmatically setting up sockets to send and receive data. There are two types of communication protocols: + +1. **Connection-oriented protocol**: TCP (Transmission Control Protocol) +2. **Connection-less protocol**: UDP (User Datagram Protocol) + +| Protocol | Description | +| -------- | ----------- | +| TCP | A reliable connection-oriented protocol. Data is transmitted in packets by the server and assembled in the same order of transmission by the receiver. | +| UDP | A connectionless protocol. It is less reliable because sockets do not require establishing any connection or termination process for transferring data. | + +## The Python `socket` Module + +This module includes the `Socket` class. A socket object represents the pair of hostname and port number. The constructor method has the following signature: + +### Syntax +```python +socket.socket(socket_family, socket_type, protocol=0) +``` + +### Parameters +- `family`: AF_INET by default. Other values - AF_INET6, AF_UNIX, AF_CAN, or AF_RDS. +- `socket_type`: Should be `SOCK_STREAM` (the default), `SOCK_DGRAM`, `SOCK_RAW`, or another `SOCK_` constant. +- `protocol`: Number is usually zero and may be omitted. + +### Return Type +This method returns a socket object. Once you have the socket object, you can use the required methods to create your client or server program. + +## Server Socket Methods + +The socket instantiated on the server is called a server socket. Following methods are available to the socket object on the server: + +| Method | Description | +| ------ | ----------- | +| `bind()` | Binds the socket to specified IP address and port number. | +| `listen()` | Starts server and runs into a listen loop looking for connection requests from clients. | +| `accept()` | When a connection request is intercepted, accepts it and identifies the client socket with its address. | + +### Example: Creating a Server Socket + +```python +import socket + +server = socket.socket() +server.bind(('localhost', 12345)) +server.listen() +client, addr = server.accept() +print("Connection request from: " + str(addr)) +``` + +By default, the server is bound to the local machine's IP address `localhost`, listening at an arbitrary empty port number. + +## Client Socket Methods + +A similar socket is set up on the client end. It mainly sends a connection request to the server socket listening at its IP address and port number. + +| Method | Description | +| -------- | ----------- | +| `connect()` | Takes a two-item tuple (IP address and port number of the server). | +| `send()` | Sends data to the socket it has established a connection with. | +| `sendall()` | Continues to send data from bytes until all data has been sent or an error occurs. | +| `sendto()` | Used in case of UDP protocol. | +| `recv()` | Retrieves data sent to the client. | +| `recvfrom()`| Used in case of UDP protocol. | + +### Example: Creating a Client Socket + +```python +import socket + +obj = socket.socket() +obj.connect(('localhost', 12345)) +message = input("Type message: ") +while message != 'q': + obj.send(message.encode()) + data = obj.recv(1024).decode() + print('Received from server: ' + data) + message = input("Type message: ") +obj.close() +``` + +## Python - Socket Server + +To write Internet servers, we use the `socket` function available in the `socket` module to create a socket object. A socket object is then used to call other functions to set up a socket server. + +### Example: Server Code + +```python +import socket + +host = "127.0.0.1" +port = 5001 +server = socket.socket() +server.bind((host, port)) +server.listen() +conn, addr = server.accept() +print("Connection from: " + str(addr)) +while True: + data = conn.recv(1024).decode() + if not data: + break + data = str(data).upper() + print("From client: " + str(data)) + data = input("Type message: ") + conn.send(data.encode()) +conn.close() +``` + +## Python - Socket Client + +Let us write a simple client program, which opens a connection to a given port (5001) and a given localhost. + +The socket.connect(hosname, port) opens a TCP connection to hostname on the port. Once you have a socket open, you can read from it like any IO object. When done, remember to close it, as you would close a file. + +The following code is a very simple client that connects to a given host and port, reads any available data from the socket, and then exits when 'q' is entered. + +### Example: Client Code + +```python +import socket + +host = '127.0.0.1' +port = 5001 +obj = socket.socket() +obj.connect((host, port)) +message = input("Type message: ") +while message != 'q': + obj.send(message.encode()) + data = obj.recv(1024).decode() + print('Received from server: ' + data) + message = input("Type message: ") +obj.close() +``` + +## Server-Client Interaction + +Run the server code first to start listening. Then start the client code to send a request. The interaction follows these steps: + +1. Server starts and listens for a connection. +2. Client sends a request. +3. Server accepts the request and identifies the client address. +4. Data exchange occurs between server and client. + +![server_client_interaction](https://www.tutorialspoint.com/python/images/server_client_interaction.jpg) + + + +## Python File Transfer with Socket Module + +The following programs demonstrate how socket communication can be used to transfer a file from server to client. + +### Server Code + +```python +import socket + +host = "127.0.0.1" +port = 5001 +server = socket.socket() +server.bind((host, port)) +server.listen() +conn, addr = server.accept() +data = conn.recv(1024).decode() +filename = 'test.txt' +f = open(filename, 'rb') +while True: + l = f.read(1024) + if not l: + break + conn.send(l) + print('Sent', repr(l)) +f.close() +print('File transferred') +conn.close() +``` + +### Client Code + +```python +import socket + +s = socket.socket() +host = "127.0.0.1" +port = 5001 + +s.connect((host, port)) +s.send("Hello server!".encode()) + +with open('recv.txt', 'wb') as f: + while True: + print('Receiving data...') + data = s.recv(1024) + if not data: + break + f.write(data) +f.close() +print('Successfully received') +s.close() +print('Connection closed') +``` + +## The Python `socketserver` Module + +The `socketserver` module in Python's standard library is a framework for simplifying the task of writing network servers. + +| Class | Description | +| ----- | ----------- | +| `TCPServer` | Uses the internet TCP protocol, provides continuous streams of data between the client and server. | +| `UDPServer` | Meant to be used for UDP protocol. | +| `UnixDatagramServer` | Uses Unix domain sockets; not available on non-Unix platforms. | + +### Example: Server Code with `socketserver` + +```python +import socketserver + +class MyTCPHandler(socketserver.BaseRequestHandler): + def handle(self): + self.data = self.request.recv(1024).strip() + host, port = self.client_address + print("{}:{} wrote:".format(host, port)) + print(self.data.decode()) + msg = input("Enter text: ") + self.request.sendall(msg.encode()) + +if __name__ == "__main__": + HOST, PORT = "localhost", 9999 + with socketserver.TCPServer((HOST, PORT), MyTCPHandler) as server: + server.serve_forever() +``` + +### Example: Client Code + +```python +import socket + +HOST, PORT = "localhost", 9999 + +while True: + with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as sock: + sock.connect((HOST, PORT)) + data = input("Enter text: ") + sock.sendall(bytes(data + "\n", "utf-8")) + received = str(sock.recv(1024), "utf-8") + print("Sent: {}".format(data)) + print("Received: {}".format(received)) +``` + +Run the server code in one terminal and the client code in multiple terminals to simulate concurrent communication between the server and multiple clients. + +## Conclusion + +In this tutorial, we covered the basics of socket programming in Python, including how to create server and client sockets, transfer data, and use the `socketserver` module for simplifying network server tasks. + +Next, we'll delve into more advanced topics in socket programming. \ No newline at end of file diff --git a/docs/python/Networking/url-processing.md b/docs/python/Networking/url-processing.md new file mode 100644 index 000000000..1a958b697 --- /dev/null +++ b/docs/python/Networking/url-processing.md @@ -0,0 +1,250 @@ +--- +id: url-processing +title: URL Processing +sidebar_label: URL Processing +sidebar_position: 3 +tags: [python, urllib, url processing, networking, parsing, request, error handling] +description: In this tutorial, you will learn about URL processing in Python using the urllib package. We will cover parsing URLs, handling URL requests, managing errors, and more. +--- + +# Python - URL Processing + +In the world of the Internet, different resources are identified by URLs (Uniform Resource Locators). The `urllib` package, bundled with Python's standard library, provides several utilities to handle URLs. It has the following modules: + +- `urllib.parse`: Used for parsing a URL into its parts. +- `urllib.request`: Contains functions for opening and reading URLs. +- `urllib.error`: Defines the exceptions raised by `urllib.request`. +- `urllib.robotparser`: Parses the `robots.txt` files. + +## The `urllib.parse` Module + +This module serves as a standard interface to obtain various parts from a URL string. The module contains the following functions: + +### `urlparse(urlstring)` + +Parse a URL into six components, returning a 6-item named tuple. Each tuple item is a string corresponding to the following attributes: + +| Attribute | Index | Value | +|-----------|-------|--------------------------------| +| scheme | 0 | URL scheme specifier | +| netloc | 1 | Network location part | +| path | 2 | Hierarchical path | +| params | 3 | Parameters for the last path element | +| query | 4 | Query component | +| fragment | 5 | Fragment identifier | +| username | - | User name | +| password | - | Password | +| hostname | - | Host name (lower case) | +| port | - | Port number as integer, if present | + +#### Example + +```python +from urllib.parse import urlparse + +url = "https://example.com/employees/name/?salary>=25000" +parsed_url = urlparse(url) +print(type(parsed_url)) +print("Scheme:", parsed_url.scheme) +print("Netloc:", parsed_url.netloc) +print("Path:", parsed_url.path) +print("Params:", parsed_url.params) +print("Query string:", parsed_url.query) +print("Fragment:", parsed_url.fragment) +``` + +Output: + +``` + +Scheme: https +Netloc: example.com +Path: /employees/name/ +Params: +Query string: salary>=25000 +Fragment: +``` + +### `parse_qs(qs)` + +This function parses a query string given as a string argument. Data is returned as a dictionary where the keys are unique query variable names and the values are lists of values for each name. + +#### Example + +```python +from urllib.parse import urlparse, parse_qs + +url = "https://example.com/employees?name=Anand&salary=25000" +parsed_url = urlparse(url) +dct = parse_qs(parsed_url.query) +print("Query parameters:", dct) +``` + +Output: + +``` +Query parameters: {'name': ['Anand'], 'salary': ['25000']} +``` + +### `urlsplit(urlstring)` + +This is similar to `urlparse()`, but does not split the params from the URL. This should generally be used instead of `urlparse()` if the more recent URL syntax allowing parameters to be applied to each segment of the path portion of the URL is wanted. + +### `urlunparse(parts)` + +This function is the opposite of `urlparse()`. It constructs a URL from a tuple as returned by `urlparse()`. The parts argument can be any six-item iterable, returning an equivalent URL. + +#### Example + +```python +from urllib.parse import urlunparse + +parts = ['https', 'example.com', '/employees/name/', '', 'salary>=25000', ''] +new_url = urlunparse(parts) +print("URL:", new_url) +``` + +Output: + +``` +URL: https://example.com/employees/name/?salary>=25000 +``` + +### `urlunsplit(parts)` + +Combine the elements of a tuple as returned by `urlsplit()` into a complete URL as a string. The parts argument can be any five-item iterable. + +## The `urllib.request` Module + +This module defines functions and classes which help in opening URLs. + +### `urlopen()` + +This function opens the given URL, which can be either a string or a `Request` object. The optional `timeout` parameter specifies a timeout in seconds for blocking operations. This function works for HTTP, HTTPS, and FTP connections. + +It returns an object that can work as a context manager and has the properties `url`, `headers`, and `status`. + +For HTTP and HTTPS URLs, this function returns an `http.client.HTTPResponse` object, slightly modified. + +#### Example + +The following code uses `urlopen()` function to read the binary data from an image file and writes it to a local file. You can open the image file on your computer using any image viewer. + +```python +from urllib.request import urlopen + +obj = urlopen("https://www.tutorialspoint.com/static/images/simply-easy-learning.jpg") +data = obj.read() +with open("img.jpg", "wb") as img: + img.write(data) +``` + +### The `Request` Object + +The `urllib.request` module includes the `Request` class. This class is an abstraction of a URL request. The constructor requires a mandatory string argument, a valid URL. + +#### Syntax + +```python +urllib.request.Request(url, data=None, headers={}, origin_req_host=None, method=None) +``` + +#### Parameters + +- `url`: A string that is a valid URL. +- `data`: An object specifying additional data to send to the server. This parameter can only be used with HTTP requests. Data may be bytes, file-like objects, and iterables of bytes-like objects. +- `headers`: Should be a dictionary of headers and their associated values. +- `origin_req_host`: Should be the request-host of the origin transaction. +- `method`: Should be a string that indicates the HTTP request method. One of GET, POST, PUT, DELETE, and other HTTP verbs. Default is GET. + +#### Example + +```python +from urllib.request import Request, urlopen + +obj = Request("https://www.tutorialspoint.com/") +resp = urlopen(obj) +data = resp.read() +print(data) +``` + +### Sending Data + +If you define the `data` argument to the `Request` constructor, a POST request will be sent to the server. The data should be any object represented in bytes. + +#### Example + +```python +from urllib.request import Request, urlopen +from urllib.parse import urlencode + +values = {'name': 'Madhu', 'location': 'India', 'language': 'Hindi'} +data = urlencode(values).encode('utf-8') +obj = Request("https://example.com", data) +resp = urlopen(obj) +``` + +### Sending Headers + +The `Request` constructor also accepts a `headers` argument to push header information into the request. It should be in a dictionary object. + +#### Example + +```python +headers = {'User-Agent': 'Mozilla/5.0'} +obj = Request("https://example.com", headers=headers) +``` + +## The `urllib.error` Module + +Following exceptions are defined in `urllib.error` module: + +### `URLError` + +`URLError` is raised because there is no network connection (no route to the specified server), or the specified server doesn't exist. In this case, the exception raised will have a 'reason' attribute. + +#### Example + +```python +from urllib.request import Request, urlopen +import urllib.error as err + +obj = Request("http://www.nosuchserver.com") +try: + urlopen(obj) +except err.URLError as e: + print(e.reason) +``` + +Output: + +``` +[Errno 11001] getaddrinfo failed +``` + +### `HTTPError` + +Every time the server sends an HTTP response, it is associated with a numeric "status code". This code indicates why the server is unable to fulfill the request. The default handlers will handle some of these responses for you. For those it can't handle, `urlopen()` function raises an `HTTPError`. Typical examples of `HTTPErrors` are '404' (page not found), '403' (request forbidden), and '401' (authentication required). + +#### Example + +```python +from urllib.request import Request, urlopen +import urllib.error as err + +obj = Request("http://www.python.org/fish.html") +try: + urlopen(obj) +except err.HTTPError as e: + print(e.code) +``` + +Output: + +``` +404 +``` + +--- + +This concludes the comprehensive guide on URL processing in Python using the `urllib` module. \ No newline at end of file