Requests forces the host to access in HTTPS even tho its HTTP. Is this a security issue?

Updated: Feb 02, 2025

Requests forces the host to access in HTTPS even tho its HTTP. Is this a security issue?

When using the Requests library in Python to make HTTP requests, you can specify the use of HTTPS by passing the https parameter as True in the session() or get() functions. However, if you don't explicitly specify HTTP or HTTPS in your request, Requests will attempt to use HTTPS by default if the URL starts with https://. If the URL is actually meant to use HTTP but is being served over an HTTPS connection (for example, through an SSL terminator or a reverse proxy), this can result in unexpected behavior and potential security issues.

The primary security concern with this behavior is that the HTTP request will be automatically upgraded to HTTPS, which may not be what the user intended. This could lead to issues with SSL/TLS certificate validation, as the certificate presented by the server may not match the expected domain name for the HTTP request. Additionally, if the server supports both HTTP and HTTPS but does not properly handle the automatic upgrade, it could potentially serve different content over HTTPS than over HTTP, which could be a security vulnerability.

Another potential issue is that the automatic upgrade to HTTPS may introduce additional latency and network overhead, as the request must first be sent over HTTPS to the SSL terminator or reverse proxy, and then be forwarded to the actual HTTP server. This could impact the performance of your application, especially if you are making many requests or if the network latency is high.

To avoid these issues, it is recommended that you explicitly specify the HTTP or HTTPS protocol in your Requests requests by passing the scheme parameter to the session() or get() functions. For example:

import requests

session = requests.Session()
response = session.get('http://example.com', scheme='http')

Or, if you want to use HTTPS explicitly:

import requests

session = requests.Session()
response = session.get('https://example.com')

By explicitly specifying the protocol, you can ensure that your requests are sent to the correct endpoint and that any SSL/TLS certificate validation issues are properly handled. Additionally, you can avoid the potential performance impact of automatic upgrades to HTTPS.