10
25
2012
24

使用 TLS/SSL 加密你的 HTTP 代理

本文来自依云's Blog,转载请注明。

HTTP 代理是明文的,这导致实际访问的 URL 可以被他人监测到。即使使用 HTTPS 协议,经过 HTTP 代理时会发送CONNECT请求,告诉代理要连续到远程主机的指定端口。于是,访问的目标域名暴露了。

有没有办法将传输内容加密呢?比如像 HTTPS 那样,使用 TLS 协议连接到代理服务器,然后再进行 HTTP 请求。很遗憾的是,我在 ziproxy 的配置里没有发现这样的选项。在 shlug 邮件列表里询问后,Shell Xu 提到了 stunnel 这个工具。以前我试过用它把 HTTP 的网站转成 HTTPS 的,但是网站后端程序无法知晓用户实际上使用的是 HTTPS,有些郁闷,就没管它了。

这次再次请出 stunnel,在代理服务器上执行如下命令:

sudo stunnel -d 0.0.0.0:8081 -r localhost:8080 -p /etc/stunnel/stunnel.pem

这样,所有到服务器的 8081 端口的请求,都会经过 TLS 解密后传递给 8080 端口。同时响应的数据也会被加密后再返回请求方。

接下来的问题是,浏览器无法直接使用这种代理。实际上除了拿 openssl 命令手动连接外,我不知道任何程序能够使用这种代理。那好,本地弄个反过来加密/解密的服务好了。还是使用 stunnel。不过出了点意外:Arch Linux 的 stunnel 是第四版,不再用命令行参数,转而使用配置文件了。于是参考这篇 Upgrading to stunnel 4,写了份 stunnel4 的配置文件:

compression = zlib
foreground = yes
output = /dev/stdout
client = yes
pid = /tmp/stunnel.pid
# or will output to syslog :-(
output = /tmp/stunnel.log

[name]
accept = 8082
connect = server.com:8081

这样在本地 8082 端口监听,把所有请求加密后转发到 server.com 的 8081 端口。同时响应的数据会被解密后再返回。

现在,所有与代理服务器传输的数据都被加密了,不怕被偷窥啦。

后记:

后来,我发现其实代理服务器和我本机都装了两个版本的 stunnel,只是名字中不带版本号的一个是第三版而另一个是第四版而已……

再后来,我猛然想起神器 socat——这家伙是支持 OpenSSL 的!比如客户端这边像下边这样子就可以了:

$ socat tcp-listen:8082,fork openssl:server.com:8081,verify=0

socat 真是神器啊,cat、netcat、rinetd、stunnel 的功能都覆盖了!

这样使用的时候,每次来新请求时,socat 会 fork 一个新进程来处理。有点浪费资源。不过略微查看了下,stunnel 似乎也一样。

Category: Linux | Tags: http linux socat 安全 网络 stunnel ssl | Read Count: 24114
eleven.i386 说:
Oct 26, 2012 02:18:40 PM

555, 我在辛辛苦苦搞chrome的时候, 你咋不告诉我这个方法呢.. 我还在傻傻的ssh, , ssh -D 不稳定的说... (T^T)

asahui 说:
Oct 28, 2012 10:45:20 AM

有点没看懂,那个本地侦听8082端口转发给服务器的8081端口这个看懂了,就是ssh -D 干的事,但服务器端侦听自己的8081端口转发给8080就不懂了,只转给服务器的8080,那么客户端还能上网的吗?网络小白求教

asahui 说:
Oct 28, 2012 10:48:07 AM

不好意思,刚才E-mail写错了,还是我
还有一个想问的就是你后记里的socat已经可以取代了stunnel的作用了?还是说只有客户端是,服务器端还是要用stunnel?

Avatar_small
依云 说:
Oct 28, 2012 10:58:21 AM

服务器 8080 接受的是明文数据,你不能把加密的数据直接给它。
socat 可以完全取代 stunnel 的,反过来是
socat openssl-listen:8081,fork tcp:localhost:8080

asahui 说:
Oct 28, 2012 12:38:14 PM

可能是我说得不清楚或者是我没完全理解文章里的内容

现在你"使用 TLS/SSL 加密你的 HTTP 代理"单纯是加密访问服务器的网站(像Tomcat用8080这样的)?

那有没有像ssh -D那样动态转发然后利用服务器代理上网的方法,就刚才你服务器里那句socat openssl-listen:8081,fork tcp:localhost:8080只是把8081的数据转发到8080端口,有没有方法也是动态分析到8081进来的数据自动解密转发到相应端口而不限于8080?

Avatar_small
依云 说:
Oct 28, 2012 01:40:03 PM

访问目标是 HTTP 代理,不是 Web 服务啊。

ym 说:
Dec 31, 2012 11:51:53 AM

hi.
socat有WINDOWS下的客户端吗?能否写篇用SOCAT翻#墙的详细文章?

Avatar_small
依云 说:
Dec 31, 2012 12:28:09 PM

Windows 上可以用 Cygwin 版,很容易找到单独的下载的,比如这里 http://linuxtechres.blogspot.com/2010/10/use-socat-as-tcp-forwarder-on-windows.html。
socat 只是流转发工具而已,翻墙还要配合其它工具的。

ym 说:
Dec 31, 2012 07:29:57 PM

hi.

brite@brite-Lenovo-3000:~$ socat tcp-listen:7777,fork openssl:mydomain.com:440,verify=0
2012/12/31 19:23:54 socat[9721] E unknown device/address "openssl"
2012/12/31 19:24:00 socat[9723] E unknown device/address "openssl"

how did the error above happen?how to fix it?

Avatar_small
依云 说:
Dec 31, 2012 07:44:34 PM

Check socat -V. Your socat doesn't have OpenSSL support compiled in.

ym 说:
Jan 02, 2013 12:07:43 PM

hi.
你说“所有到服务器的 8081 端口的请求,都会经过 TLS 解密后传递给 8080 端口”,这个服务器上的8080端口是不是可以随便设置?(还是非得设为服务器上的squid的端口?)

Avatar_small
依云 说:
Jan 02, 2013 03:53:34 PM

是啊,想转到哪个端口改那个数字就可以了。只要是 TCP 协议的都行。

eleven.i386 说:
May 20, 2013 11:44:07 AM

我也是想到了,其实socat可以完全代替stunnel呆在代理服务器上, 仙子喵, 你用的什么架设代理的? 咱的kangle可以作为代理使用,但是总感觉怪怪的,不是专业代理工具

Avatar_small
依云 说:
May 20, 2013 11:51:25 AM

ziproxy, 支持透明代理的哦~不过记得把它的图片压缩功能关掉,不然很多大图都会被它搞模糊!

cookies 说:
Jul 02, 2013 01:07:51 PM

请问你用socat时,有没有遇到很多类似socat[2880] E write(4, 0x954a758, 8192): Broken pipe的报错,而且vps上还报TCP: Possible SYN flooding

Avatar_small
依云 说:
Jul 02, 2013 01:16:25 PM

抓包看下,是不是被重置之类的了?

fish 说:
Mar 31, 2016 02:42:06 PM

hi.

在mac上,运行命令brew install socat,在vps上搭建加密的squid(或者stunnel+squid/tinyproxy)然后用你的命令能翻#墙,打开一些网站,可惜速度慢。且根本打不开youtube,可见这个socat的效率不高

Avatar_small
依云 说:
Mar 31, 2016 09:16:02 PM

这结论做得挺草率的,因为变量太多:

1. 你直接访问 vps 上的 https 站点速度如何?
2. 你的 vps 访问 YouTube 速度如何?
3. 你使用的代理的运作效率如何?
4. 你能否确认所有需要的流量(包括 DNS)都走了代理?
5. 你的 socat 是什么版本的,编译选项里开了优化没?
6. 你同时向你的 vps 建立多个 https 连接,速度如何?
7. 你是否使用了非标准端口号,墙是否对其进行了劣化?

其实我们都知道,Google 的技术很差劲的,你看看百度多棒,眨眼间就加载得差不多了。

fish 说:
Sep 17, 2018 12:13:46 PM

hi.

bogon:~ brite$ socat tcp-listen:7082,fork openssl:my-vps-ip:8081,verify=0
dyld: Library not loaded: /usr/local/opt/readline/lib/libreadline.6.dylib
Referenced from: /usr/local/bin/socat
Reason: image not found
Abort trap: 6
bogon:~ brite$

how to fix the issue?
tks a lot

Avatar_small
依云 说:
Sep 18, 2018 12:02:44 AM

You have a broken socat installation: the readline library is missing. Try recompile and reinstall it on current system.

ym 说:
Dec 05, 2018 10:46:05 PM

hi,

服务器上搭建的是node-spdyproxy :(http://github.com/igrigorik/node-spdyproxy/)

root@wh:~# ps aux|grep spdyproxy
root 20810 0.0 0.0 3084 940 pts/3 S+ 09:29 0:00 grep --color=auto spdyproxy
root 27059 0.0 2.3 895588 24360 ? Ssl Dec04 0:03 /root/node-v4.1.0-linux-x64/bin/node /root/node-v4.1.0-linux-x64/bin/spdyproxy -k /root/private.key -c /root/public.crt -p 344
root@wh:~#

我在mac上运行:
socat tcp-listen:7085,fork openssl:vps-ip:344,verify=0
然后设置浏览器的http proxy为127.0.0.1:7085 ,但是浏览器翻墙失败,不知为什么??

我用服务器上搭建的stunnel+tinyproxy,然后在本地运行命令:
socat tcp-listen:7082,fork openssl:vps-ip:440,verify=0
然后设置浏览器的http proxy为127.0.0.1:7082 ,浏览器可以翻墙
成功。

你可以试试在你的vps上搭建node-spdyproxy,测试一下吗?
(node版本需为4.1.0才行)

Avatar_small
依云 说:
Dec 06, 2018 03:52:08 PM

因为 node-spdyproxy 是 spdy/h2s 协议吧。你可以参考这篇文章搭建两边的 h2 代理: https://wzyboy.im/post/1052.html

ym 说:
Dec 08, 2018 03:08:07 AM

看到这里https://www.williamlong.info/archives/4142.html 说:
“预计2016年就会完全从Chrome中移除对SPDY协议的支持。“,就知道原因了。SPDY协议现在已没鬼用了,没法用来翻墙了


登录 *


loading captcha image...
(输入验证码)
or Ctrl+Enter

| Theme: Aeros 2.0 by TheBuckmaker.com