¿Es posible tener conexiones HTTPS a través de servidores proxy? Si es así, ¿qué tipo de servidor proxy permite esto?
Duplicado con ¿Cómo usar el proxy Socks 5 con Apache HTTP Client 4?
¿Es posible tener conexiones HTTPS a través de servidores proxy? Si es así, ¿qué tipo de servidor proxy permite esto?
Duplicado con ¿Cómo usar el proxy Socks 5 con Apache HTTP Client 4?
Respuestas:
TLS / SSL (La S en HTTPS) garantiza que no hay espías entre usted y el servidor con el que está contactando, es decir, no hay proxies. Normalmente, se utiliza CONNECT
para abrir una conexión TCP a través del proxy. En este caso, el proxy no podrá almacenar en caché, leer o modificar ninguna solicitud / respuesta y, por lo tanto, será bastante inútil.
Si desea que el proxy pueda leer información, puede tomar el siguiente enfoque:
Un ejemplo es el salto SSL de Squid . Del mismo modo, el eructo se puede configurar para hacer esto. Esto también ha sido utilizado en un contexto menos benigno por un ISP egipcio .
Tenga en cuenta que los sitios web y los navegadores modernos pueden emplear HPKP o pines de certificado integrados que anulan este enfoque.
Unconditionally trusted
refiere a un certificado de CA. Los certificados de CA no tienen dominios. He modificado la respuesta con dos ejemplos en los que esto funciona / funcionó en la práctica sin ninguna alerta para el usuario.
La respuesta corta es: es posible y se puede hacer con un proxy HTTP especial o un proxy SOCKS.
En primer lugar, HTTPS usa SSL / TLS que, por diseño, garantiza la seguridad de un extremo a otro al establecer un canal de comunicación seguro sobre uno inseguro. Si el proxy HTTP puede ver el contenido, entonces es un interlocutor intermedio y esto anula el objetivo de SSL / TLS. Por lo tanto, debe haber algunos trucos si queremos hacer un proxy a través de un proxy HTTP simple.
El truco es que convertimos un proxy HTTP en un proxy TCP con un comando especial llamado CONNECT
. No todos los proxies HTTP admiten esta función, pero muchos lo hacen ahora. El proxy TCP no puede ver el contenido HTTP que se transfiere en texto sin cifrar, pero eso no afecta su capacidad para reenviar paquetes de un lado a otro. De esta manera, el cliente y el servidor pueden comunicarse entre sí con la ayuda del proxy. Esta es la forma segura de transferir datos HTTPS.
También existe una forma insegura de hacerlo, en la que el proxy HTTP se convierte en un intermediario. Recibe la conexión iniciada por el cliente y luego inicia otra conexión con el servidor real. En un SSL / TLS bien implementado, se notificará al cliente que el proxy no es el servidor real. Entonces, el cliente debe confiar en el proxy ignorando la advertencia para que las cosas funcionen. Después de eso, el proxy simplemente descifra los datos de una conexión, los vuelve a cifrar y los alimenta a la otra.
Finalmente, ciertamente podemos proxy HTTPS a través de un proxy SOCKS , porque el proxy SOCKS funciona en un nivel más bajo. Puede pensar que un proxy SOCKS es un proxy TCP y UDP.
Por lo que puedo recordar, debe utilizar una consulta HTTP CONNECT en el proxy. esto convertirá la conexión de la solicitud en un túnel TCP / IP transparente.
por lo que necesita saber si el servidor proxy que utiliza es compatible con este protocolo.
Si todavía le interesa, aquí hay una respuesta a una pregunta similar: Convierta el proxy HTTP en proxy HTTPS en Twisted
Para responder a la segunda parte de la pregunta:
Si es así, ¿qué tipo de servidor proxy permite esto?
De fábrica, la mayoría de los servidores proxy se configurarán para permitir conexiones HTTPS solo al puerto 443, por lo que los URI https con puertos personalizados no funcionarían. Esto generalmente se puede configurar, según el servidor proxy. Squid y TinyProxy lo admiten, por ejemplo.
Aquí está mi código Java completo que admite solicitudes HTTP y HTTPS utilizando el proxy SOCKS.
import java.io.IOException;
import java.net.InetSocketAddress;
import java.net.Proxy;
import java.net.Socket;
import java.nio.charset.StandardCharsets;
import org.apache.http.HttpHost;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.protocol.HttpClientContext;
import org.apache.http.config.Registry;
import org.apache.http.config.RegistryBuilder;
import org.apache.http.conn.socket.ConnectionSocketFactory;
import org.apache.http.conn.socket.PlainConnectionSocketFactory;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.impl.conn.PoolingHttpClientConnectionManager;
import org.apache.http.protocol.HttpContext;
import org.apache.http.ssl.SSLContexts;
import org.apache.http.util.EntityUtils;
import javax.net.ssl.SSLContext;
/**
* How to send a HTTP or HTTPS request via SOCKS proxy.
*/
public class ClientExecuteSOCKS {
public static void main(String[] args) throws Exception {
Registry<ConnectionSocketFactory> reg = RegistryBuilder.<ConnectionSocketFactory>create()
.register("http", new MyHTTPConnectionSocketFactory())
.register("https", new MyHTTPSConnectionSocketFactory(SSLContexts.createSystemDefault
()))
.build();
PoolingHttpClientConnectionManager cm = new PoolingHttpClientConnectionManager(reg);
try (CloseableHttpClient httpclient = HttpClients.custom()
.setConnectionManager(cm)
.build()) {
InetSocketAddress socksaddr = new InetSocketAddress("mysockshost", 1234);
HttpClientContext context = HttpClientContext.create();
context.setAttribute("socks.address", socksaddr);
HttpHost target = new HttpHost("www.example.com/", 80, "http");
HttpGet request = new HttpGet("/");
System.out.println("Executing request " + request + " to " + target + " via SOCKS " +
"proxy " + socksaddr);
try (CloseableHttpResponse response = httpclient.execute(target, request, context)) {
System.out.println("----------------------------------------");
System.out.println(response.getStatusLine());
System.out.println(EntityUtils.toString(response.getEntity(), StandardCharsets
.UTF_8));
}
}
}
static class MyHTTPConnectionSocketFactory extends PlainConnectionSocketFactory {
@Override
public Socket createSocket(final HttpContext context) throws IOException {
InetSocketAddress socksaddr = (InetSocketAddress) context.getAttribute("socks.address");
Proxy proxy = new Proxy(Proxy.Type.SOCKS, socksaddr);
return new Socket(proxy);
}
}
static class MyHTTPSConnectionSocketFactory extends SSLConnectionSocketFactory {
public MyHTTPSConnectionSocketFactory(final SSLContext sslContext) {
super(sslContext);
}
@Override
public Socket createSocket(final HttpContext context) throws IOException {
InetSocketAddress socksaddr = (InetSocketAddress) context.getAttribute("socks.address");
Proxy proxy = new Proxy(Proxy.Type.SOCKS, socksaddr);
return new Socket(proxy);
}
}
}
tunelización HTTPS a través de SSH (versión linux):
1) turn off using 443 on localhost
2) start tunneling as root: ssh -N login@proxy_server -L 443:target_ip:443
3) adding 127.0.0.1 target_domain.com to /etc/hosts
todo lo que haces en localhost. luego:
target_domain.com is accessible from localhost browser.
Había intentado
ssh -N -D 12345 login@proxy_server
localhost:12345
pero esto resultó en el error "Conexión insegura" cada vez que intentaba conectarme a un sitio web https.
La solución fue
Referencia de documentación oceánica digital
Cómo enrutar el tráfico web de forma segura sin una VPN utilizando un túnel SOCKS
No creo que "tener conexiones HTTPS a través de servidores proxy" signifique el tipo de ataque Man-in-the-Middle de servidor proxy. Creo que se está preguntando si uno puede conectarse a un servidor proxy http a través de TLS. Y la respuesta es sí.
¿Es posible tener conexiones HTTPS a través de servidores proxy?
Sí, vea mi pregunta y respuesta aquí. El servidor proxy HTTP solo funciona en SwitchOmega
Si es así, ¿qué tipo de servidor proxy permite esto?
El tipo de servidor proxy implementa certificados SSL, como lo hacen los sitios web comunes. Pero necesita un pac
archivo para que el navegador configure la conexión proxy a través de SSL.