Endpoint de proxy HTTPS
Todo endpoint de proxy HTTP de Litport también acepta TLS en el mismo host y puerto. Cambia el esquema de la URL del proxy de http:// a https:// y la conexión entre tu cliente y el hub queda cifrada. Las credenciales, el puerto y los destinos siguen siendo los mismos. La sobrecarga de TLS cuenta como tráfico (consulta cuánto cuesta), y un handshake fallido cierra la conexión sin ningún X-Proxy-Error-Code que inspeccionar (consulta cómo comprobar que TLS realmente está en uso).
| Esquema | Del cliente al hub | Ejemplo |
|---|---|---|
http:// |
Sin cifrar | http:// |
https:// |
TLS | https:// |
PORT es el puerto del proxy HTTP que se muestra para tu token en el panel (1337 y 31337 son los valores predeterminados; consulta Entrada del proxy). Los endpoints SOCKS5 no tienen variante con TLS.
Elige un nivel de seguridad#
Hay tres formas de comunicarte con el proxy. Elige la que corresponda al entorno donde se ejecuta tu cliente; el resto de esta página muestra cómo configurar cada una.
| Nivel | URL del proxy y configuración | Observador pasivo (Wi-Fi, ISP, red compartida) | Atacante activo (redirige tu conexión) | Compatibilidad con clientes |
|---|---|---|---|---|
| 0. Sin cifrar | http://, nada más |
Lee tus credencialesCONNECT y los cuerpos de las solicitudes HTTP sin cifrar |
Igual | Todos los clientes |
| 1. Cifrado, sin verificar | https:// más la opción del cliente para «omitir la verificación del proxy» |
No ve nada | Puede hacerse pasar por el hub y capturar tus credenciales | La mayoría de las bibliotecas; no los navegadores, ni Requests sin quitar también la verificación del destino |
| 2. Cifrado y verificado (recomendado) | https:// más el archivo raíz de Litport |
No ve nada | Falla de forma segura: el cliente rechaza todo lo que no sea un hub de Litport | Todos los clientes que admiten un proxy https:// |
Recomendación: usa el nivel 2. Cuesta un archivo público y una opción, y es el único nivel que protege frente a los dos tipos de atacante una credencial que se puede gastar. Descarga la raíz una vez y guárdala junto a tu código:
curl --fail --remote-name https://litport.net/certificates/litport-cache-root.crt
El nivel 1 es una mejora razonable frente al texto sin cifrar para una prueba manual rápida o para un cliente al que no puedes darle un archivo. El nivel 0 es el predeterminado solo porque es lo que admiten todos los clientes; abandónalo siempre que la red entre tú y el hub no sea tuya.
Dos cosas distintas llamadas «proxy HTTPS»#
- Usar el proxy para un destino HTTPS es lo que un proxy HTTP siempre ha hecho: tu cliente envía
CONNECT example.com:443, el hub abre un túnel y tu sesión TLS se ejecuta de extremo a extremo dentro de él. El endpoint de proxyhttp://lo admite; el contenido del túnel es opaco para Litport a menos que actives el modo de caché. - Un endpoint de proxy HTTPS cifra el tramo entre tu cliente y el propio hub. Todo lo que envías al proxy, incluidos la línea
CONNECTy tus credenciales, viaja dentro de esa sesión TLS.
Esta página trata del segundo. Los dos son independientes: puedes usar cualquiera de los dos esquemas con cualquier destino.
Qué expone el endpoint sin cifrar (nivel 0)#
Con http://, cualquier elemento en la ruta entre tu cliente y el hub puede leer:
| Expuesto en la red | Consecuencia |
|---|---|
Encabezado Proxy-Authorization |
Tu usuario y contraseña del proxy, en cada solicitud. Quien capture una credencial de pago por GB puede gastarla. |
Líneas CONNECT host:port |
Cada nombre de host al que te conectas, incluso cuando el túnel mismo está cifrado. |
Solicitudes a destinos http:// sin cifrar |
Los cuerpos completos de la solicitud y la respuesta. |
«En la ruta» incluye la red local en la que estás, tu ISP, una red compartida en la nube, un proxy de salida corporativo y cualquier salto que registre tráfico. El sitio de destino ve lo mismo en ambos casos: la IP de salida seleccionada, nunca la tuya.
Cuándo usar https://#
Usa el endpoint HTTPS cuando:
- El cliente está en una red que no controlas. Equipos portátiles en redes Wi-Fi públicas, oficinas compartidas, redes de hoteles y aeropuertos, y cualquier entorno con un dispositivo de inspección transparente.
- El cliente se ejecuta en infraestructura compartida o de terceros. Runners de CI, funciones serverless, VPC compartidas en la nube y contenedores en hosts que no administras. Allí la captura de credenciales es silenciosa y duradera.
- La propia lista de destinos es sensible. Las líneas
CONNECTrevelan qué hosts investigas aunque el contenido esté cifrado. - Accedes a destinos
http://sin cifrar. De lo contrario, esos cuerpos se pueden leer de extremo a extremo en el primer salto. - El tráfico de proxy sin cifrar está bloqueado o limitado. Algunas redes marcan
CONNECTen puertos no estándar; TLS hacia un nombre de host parece HTTPS normal.
Quédate en http:// cuando:
- El cliente y el hub ya comparten una ruta privada y cifrada, por ejemplo una VPN hacia una red que controlas, y quieres la menor sobrecarga posible por conexión.
- La biblioteca del cliente no puede negociar TLS con un proxy (consulta las notas sobre clientes más abajo).
- Abres muchísimas conexiones cortas y el handshake adicional por conexión pesa más que la exposición.
Cuánto cuesta#
- Un handshake TLS adicional por conexión. Los clientes con keep-alive lo pagan una vez por conexión, no por solicitud.
- La sobrecarga de TLS cuenta como tráfico. El encuadre de los registros y el handshake son bytes que pasan por el hub, así que en las solicitudes normales (sin caché) se mide un poco más de tráfico: normalmente un pequeño porcentaje en las solicitudes pequeñas y una cantidad insignificante en las transferencias grandes. La contabilización en modo de caché no cambia.
- Tu cliente debe confiar en la raíz de Litport para la conexión con el proxy. De eso trata la siguiente sección, y es la razón por la que
curl -kno ayuda.
El certificado del hub y por qué -k no funciona#
El nivel 2 significa verificar el certificado del hub. El hub presenta un certificado para su propio nombre de host (por ejemplo hub-eu-1.litport.net) emitido por la raíz de caché de Litport. Esa raíz no está en los almacenes de confianza de los sistemas operativos, por lo que un cliente que verifica el certificado del proxy con su paquete predeterminado falla:
curl: (60) SSL certificate problem: unable to get local issuer certificate
curl -k no lo soluciona. Los clientes mantienen dos tramos TLS independientes con ajustes independientes:
| Tramo TLS | Qué protege | Opciones de curl |
|---|---|---|
| Del cliente al proxy | Tus credenciales y las líneas CONNECT |
--proxy-cacert, --proxy-insecure |
| Del cliente al destino (dentro del túnel) | El sitio que estás consultando | --cacert, -k / --insecure |
-k solo relaja el tramo hacia el destino. El tramo del proxy sigue verificando con el paquete del sistema y se interrumpe. En su lugar, apunta el tramo del proxy a la raíz de Litport:
curl --fail --remote-name https://litport.net/certificates/litport-cache-root.crt
curl --proxy-cacert litport-cache-root.crt \
-x 'https://USER:[email protected]:PORT' \
'https://example.com/'
Dos cosas que debes saber antes de instalar esa raíz de forma más amplia:
- Confiar en la raíz para el tramo del proxy no activa el modo de caché. El modo de caché necesita el sufijo
_cache-en la contraseña de la credencial; sin él, el túnel sigue siendo opaco. - La misma raíz también puede emitir certificados para la interceptación del modo de caché. Si prefieres no agregarla a un almacén de todo el sistema, limítala al proceso o contenedor que usa el proxy, como hacen todos los ejemplos siguientes.
Usa siempre el nombre de host del hub, nunca su dirección IP. El certificado se emite para el nombre de host.
Nivel 2: ejemplos de clientes con verificación#
Reemplaza USER, PASSWORD y PORT; aplica codificación porcentual a los caracteres reservados de las credenciales. Todos los ejemplos verifican el certificado del proxy con litport-cache-root.crt y mantienen la verificación normal con CA públicas para el destino. Cada sección termina con la opción del nivel 1 que omite la verificación solo del tramo del proxy; lee el nivel 1 para saber qué implica antes de usarla.
curl#
Con verificación (recomendado):
curl --proxy-cacert litport-cache-root.crt \
-x 'https://hub-eu-1.litport.net:PORT' --proxy-user 'USER:PASSWORD' \
'https://example.com/'
Agrega --verbose para ver dos handshakes: el primero con el proxy (hub-eu-1.litport.net), luego CONNECT dentro de él y luego el del destino.
Sin verificación, solo para una prueba desechable (las credenciales siguen cifradas, pero el cliente no puede distinguir un hub real de un impostor):
curl --proxy-insecure -x 'https://USER:[email protected]:PORT' 'https://example.com/'
--proxy-cacert requiere curl 7.52 o posterior, que incluyen todas las distribuciones actuales.
Python Requests#
Requests usa un solo paquete de CA para ambos tramos, y verify= reemplaza su paquete predeterminado. Crea un paquete combinado una vez para que el destino conserve la verificación con CA públicas:
cat "$(python -c 'import certifi; print(certifi.where())')" litport-cache-root.crt > litport-bundle.pem
import requests
proxy = 'https://USER:[email protected]:PORT'
response = requests.get(
'https://example.com/',
proxies={'http': proxy, 'https': proxy},
verify='litport-bundle.pem',
timeout=30,
)
Indica el proxy tanto en la clave http como en la https; Requests elige la entrada según el esquema del destino. TLS dentro de TLS a través de un proxy https:// requiere urllib3 1.26 o posterior, de la que dependen Requests 2.26 y posteriores.
Requests no tiene una opción solo para el proxy: verify=False desactiva la verificación de ambos tramos, el hub y el destino, e imprime una advertencia en cada solicitud. Úsalo solo en pruebas desechables.
response = requests.get('https://example.com/', proxies={'http': proxy, 'https': proxy}, verify=False, timeout=30)
Python httpx#
httpx separa los ajustes TLS del proxy de los del destino:
import ssl
import httpx
context = ssl.create_default_context()
context.load_verify_locations(cafile='litport-cache-root.crt')
proxy = httpx.Proxy('https://USER:[email protected]:PORT', ssl_context=context)
with httpx.Client(proxy=proxy, timeout=30) as client:
response = client.get('https://example.com/')
El ssl_context de Proxy verifica solo el hub; el contexto predeterminado del cliente sigue verificando el destino. Para omitir el tramo del proxy y mantener verificado el destino, pasa a Proxy un contexto con la verificación desactivada:
insecure = ssl.create_default_context()
insecure.check_hostname = False
insecure.verify_mode = ssl.CERT_NONE
proxy = httpx.Proxy('https://USER:[email protected]:PORT', ssl_context=insecure)
Node#
https-proxy-agent acepta una URL de proxy https:// y verifica el hub con el almacén de confianza de Node, así que agrega la raíz mediante NODE_EXTRA_CA_CERTS. No desactiva la verificación en ningún punto.
npm install https-proxy-agent
NODE_EXTRA_CA_CERTS=./litport-cache-root.crt node fetch.mjs
import https from 'node:https'
import { HttpsProxyAgent } from 'https-proxy-agent'
const agent = new HttpsProxyAgent('https://USER:[email protected]:PORT')
https.get('https://example.com/', { agent }, response => response.resume())
Con undici (también el motor detrás del fetch global en Node 18 y posteriores) el tramo del proxy tiene sus propias opciones TLS, por lo que no hace falta ninguna variable de entorno:
import { readFileSync } from 'node:fs'
import { ProxyAgent, fetch } from 'undici'
const dispatcher = new ProxyAgent({
uri: 'https://hub-eu-1.litport.net:PORT',
token: 'Basic ' + Buffer.from('USER:PASSWORD').toString('base64'),
proxyTls: { ca: [readFileSync('litport-cache-root.crt')] },
})
const response = await fetch('https://example.com/', { dispatcher })
Ambas bibliotecas pueden omitir solo el tramo del proxy. En https-proxy-agent, el segundo argumento se pasa a la conexión TLS con el hub; en undici es proxyTls. La verificación del destino sigue activa. No uses NODE_TLS_REJECT_UNAUTHORIZED=0, que desactiva la verificación en todo el proceso.
const agent = new HttpsProxyAgent('https://USER:[email protected]:PORT', { rejectUnauthorized: false })
const dispatcher = new ProxyAgent({ uri: 'https://hub-eu-1.litport.net:PORT', token, proxyTls: { rejectUnauthorized: false } })
Go#
El http.Transport de Go se conecta a un proxy https:// con el mismo TLSClientConfig que usa para los destinos, así que agrega la raíz al pool de certificados del sistema en lugar de reemplazarlo:
pool, err := x509.SystemCertPool()
if err != nil || pool == nil { pool = x509.NewCertPool() }
pem, err := os.ReadFile("litport-cache-root.crt")
if err != nil || !pool.AppendCertsFromPEM(pem) { log.Fatal("could not add Litport root") }
proxyURL, err := url.Parse("https://USER:[email protected]:PORT")
if err != nil { log.Fatal(err) }
client := &http.Client{Transport: &http.Transport{
Proxy: http.ProxyURL(proxyURL),
TLSClientConfig: &tls.Config{RootCAs: pool, MinVersion: tls.VersionTLS12},
}}
response, err := client.Get("https://example.com/")
Go aplica TLSClientConfig a ambos tramos, por lo que InsecureSkipVerify: true también dejaría de verificar el destino. No hay una opción solo para el proxy; en su lugar, mantén la raíz en el pool.
PHP#
La extensión curl expone las mismas opciones del tramo del proxy que la línea de comandos:
$ch = curl_init('https://example.com/');
curl_setopt_array($ch, [
CURLOPT_PROXY => 'https://hub-eu-1.litport.net:PORT',
CURLOPT_PROXYUSERPWD => 'USER:PASSWORD',
CURLOPT_PROXY_CAINFO => __DIR__ . '/litport-cache-root.crt',
CURLOPT_RETURNTRANSFER => true,
]);
$body = curl_exec($ch);
Para omitir solo el tramo del proxy, reemplaza CURLOPT_PROXY_CAINFO por CURLOPT_PROXY_SSL_VERIFYPEER => false y CURLOPT_PROXY_SSL_VERIFYHOST => 0; el CURLOPT_SSL_VERIFYPEER del destino se queda en su valor predeterminado.
Java#
El java.net.http.HttpClient integrado en el JDK solo admite proxies sin cifrar. Usa Apache HttpClient 5, que acepta un host de proxy https, y dale a la JVM un truststore que contenga la raíz de Litport junto con las raíces predeterminadas:
keytool -importcert -noprompt -alias litport-cache -file litport-cache-root.crt \
-keystore ./litport-truststore.p12 -storetype PKCS12 -storepass changeit
java -Djavax.net.ssl.trustStore=./litport-truststore.p12 \
-Djavax.net.ssl.trustStoreType=PKCS12 -Djavax.net.ssl.trustStorePassword=changeit App
HttpHost proxy = new HttpHost("https", "hub-eu-1.litport.net", PORT);
BasicCredentialsProvider credentials = new BasicCredentialsProvider();
credentials.setCredentials(new AuthScope(proxy), new UsernamePasswordCredentials("USER", "PASSWORD".toCharArray()));
try (CloseableHttpClient client = HttpClients.custom()
.setProxy(proxy)
.setDefaultCredentialsProvider(credentials)
.build()) {
client.execute(new HttpGet("https://example.com/"), response -> EntityUtils.toString(response.getEntity()));
}
Un truststore dedicado reemplaza el paquete predeterminado de la JVM, así que importa en él también las raíces públicas que necesites, o importa la raíz de Litport en una copia del cacerts de la JVM. Java no tiene una opción solo para el proxy: un TrustManager que confíe en todo también dejaría de verificar los destinos, así que usa el truststore.
Navegadores y automatización de navegadores#
Los navegadores verifican el certificado del proxy con el almacén del sistema operativo (Firefox, con el suyo propio). Instala la raíz allí para el perfil que uses y luego apunta el navegador al proxy HTTPS:
- Chrome y Edge: inicia con
--proxy-server="https://hub-eu-1.litport.net:PORT", o usa un archivo PAC que devuelvaHTTPS hub-eu-1.litport.net:PORT. El navegador solicita las credenciales del proxy. - Firefox: usa un archivo PAC con la misma directiva
HTTPS host:port, o establece el tipo de proxy en HTTPS en la configuración de conexión. - Playwright y Puppeteer: pasa
server: 'https://hub-eu-1.litport.net:PORT'junto con el usuario y la contraseña. El navegador sigue necesitando la raíz en su almacén;ignoreHTTPSErrorsy--ignore-certificate-errorsafectan solo a los certificados de los destinos. Los navegadores nunca omiten la verificación del certificado de un proxy, así que instalar la raíz es la única opción.
Las instrucciones para cada almacén de sistema operativo y de Firefox están en la página del certificado.
Clientes sin compatibilidad con TLS hacia el proxy#
El descargador predeterminado de Scrapy, el HttpClient del JDK y muchas bibliotecas HTTP antiguas solo pueden comunicarse con un proxy sin cifrar. En esos casos, mantén http:// o ejecuta un pequeño reenviador local en 127.0.0.1 que acepte texto sin cifrar y se conecte al hub mediante TLS; así el tramo sensible permanece en tu equipo.
Nivel 1: cifrado sin verificación#
Cada ejemplo con verificación de arriba tiene una variante sin verificación. Omitir la verificación mantiene cifrado el tramo, por lo que un observador pasivo en la red sigue sin ver nada. Elimina la garantía de que te estás comunicando con un hub de Litport: un atacante activo que pueda redirigir tu conexión podría presentar cualquier certificado y capturar tus credenciales. Es la misma exposición que tiene el nivel 0 frente a un atacante activo, así que considera el nivel 1 una mejora respecto de http://, no un equivalente del nivel 2.
| Cliente | Solo el tramo del proxy | Ambos tramos |
|---|---|---|
| curl | --proxy-insecure |
--proxy-insecure -k |
| Python Requests | no disponible | verify=False |
| Python httpx | Proxy(..., ssl |
agrega verify=False en el cliente |
Node https-proxy-agent |
opción de agente { reject |
NODE (evítalo) |
| Node undici | proxyTls: { reject |
agrega requestTls: { reject |
| Go | no disponible | Insecure |
| PHP curl | CURLOPT / CURLOPT |
agrega CURLOPT |
| Java | no disponible | TrustManager que confía en todo (evítalo) |
| Navegadores | no disponible | no disponible; instala la raíz |
Prefiere el nivel 2 para todo lo que se ejecute sin supervisión. La verificación cuesta un archivo y una opción; la credencial que protege se puede gastar.
Comprobar que TLS realmente está en uso#
curl --verboseimprime el handshake del proxy antes de la líneaCONNECT, incluido el sujeto del certificadoCN=hub-eu-1.litport.net.- Una contraseña incorrecta por
https://sigue devolviendo407conX-Proxy-Error-Code: 4, igual que porhttp://; los encabezados de error viajan dentro de TLS. - Si la conexión se cierra de inmediato sin respuesta HTTP, el hub no pudo completar el handshake TLS. Comprueba que usaste el nombre de host y no una dirección IP, que el esquema es
https://en un puerto HTTP y no en un puerto SOCKS5, y que tu cliente confía en la raíz de Litport para el tramo del proxy. Consulta la referencia de errores del proxy.
Páginas relacionadas#
- Tokens, productos de proxy y hubs para puertos y credenciales.
- Configuración del certificado de caché para la identidad de la raíz, las huellas digitales y la instalación en cada almacén.
- Caché de respuestas estáticas si además quieres que las respuestas estáticas repetidas se sirvan gratis.