Ngrok 搭建指南

文章转载至 Luozm’s Blog

ngrok是一个反向代理,它能够让你本地的web服务或tcp服务通过公共的端口和外部建立一个安全的通道,使得外网可以访问本地的计算机服务。ngrok1.x开源,ngrok2.x不开源。

ngrok

Ngrok的主要用途有以下几种:

  • 内网穿透,可代替vpn
  • 将无外网IP的desktop映射到公网
  • 临时搭建网络并分配二级域名
  • 微信二次开发的本地调试

自己搭建ngrok服务需要一台外网服务器,一个域名(如果只用来内网穿透好像也可以不要?)。本文中使用的服务器系统为Ubuntu 16.04。

有域名之后,需要配置DNS的Host Records,将准备分配给ngrok服务器的域名解析到公网服务器IP地址,如下图所示:

A_Records

泛解析还不太了解,后面补上

ngrok是基于go语言开发的,因此需要先安装go:

sudo apt-get install golang

输入go version来验证安装:

go versiongo version go1.6.2 linux/amd64

设置go环境变量(好像可以不用?):

此外还要使用git,一般ubuntu系统都会自带。

cd /usr/local/src
git clone https://github.com/inconshreveable/ngrok.git
cd ngrok

使用ngrok.com官方服务时,我们使用的是官方的SSL证书。自己建立ngrok服务,需要我们生成自己的证书,并提供携带该证书的ngrok客户端。首先指定域名:

export NGROK_DOMAIN="ngrok.test.website"

生成证书:

openssl genrsa -out rootCA.key 2048openssl req -x509 -new -nodes -key rootCA.key -subj "/CN=$NGROK_DOMAIN" -days 5000 -out rootCA.pem
openssl genrsa -out device.key 2048
openssl req -new -key device.key -subj "/CN=$NGROK_DOMAIN" -out device.csr
openssl x509 -req -in device.csr -CA rootCA.pem -CAkey rootCA.key -CAcreateserial -out device.crt -days 5000

我们在编译可执行文件之前,需要把生成的证书分别替换到 assets/client/tls和assets/server/tls中,这两个目录分别存放着ngrok和ngrokd的默认证书。

cp rootCA.pem assets/client/tls/ngrokroot.crt
cp device.crt assets/server/tls/snakeoil.crt
cp device.key assets/server/tls/snakeoil.key

有没有release的区别是,包含release的编译结果会把assets目录下的内容包括进去,从而可以独立执行。如果你今后还要更换证书,建议编译不包含release的版本。。首先编译ngrok服务端(ngrokd),默认为Linux版本:

make clean
make release-server

编译过程需要等待一会,因为需要通过git安装相关依赖包。如果提示没有权限,使用sudo命令来安装。

在编译客户端的时候需要指明对应的操作系统和构架:

  • Linux 平台 32 位系统:GOOS=linux GOARCH=386
  • Linux 平台 64 位系统:GOOS=linux GOARCH=amd64
  • Windows 平台 32 位系统:GOOS=windows GOARCH=386
  • Windows 平台 64 位系统:GOOS=windows GOARCH=amd64
  • MAC 平台 32 位系统:GOOS=darwin GOARCH=386
  • MAC 平台 64 位系统:GOOS=darwin GOARCH=amd64
  • ARM 平台:GOOS=linux GOARCH=arm

例如编译树莓派 ARM 位的客户端:

export GOOS=linux
export GOARCH=arm
make release-client

生成的文件放在/bin对应的文件夹中,如windows 64位的为:windows_amd64,默认版本的文件就在根目录下。

编译后生成两个文件分别为服务端(ngrokd)和客户端(ngrok)。切换到对应的文件夹,运行服务端:

./ngrokd -domain="$NGROK_DOMAIN" -httpAddr=":801" -httpsAddr=":802"

参数-domain表示服务器域名,请改成你自己的域名;-httpAddr表示默认监听的HTTP端口,-httpsAddr表示默认监听的HTTPS端口,因为我用不到所以都设置成空字符串”“来关闭监听,如果需要打开的话记得格式是:12345(冒号+端口号)这样的;-tunnelAddr表示服务器监听客户端连接的隧道端口号,格式和前面一样;-log表示日志文件位置;还有个-log-level用来控制日志记录的事件级别,选项有DEBUG、INFO、WARNING、ERROR。

如果编译的是不带release的版本,还可以通过-tlsCrt-tlsKey选项来指定证书文件的位置。

出现类似以下内容,则说明我们的服务器端ngrokd正常运行了:

[16:41:56 CST 2017/04/20] [INFO] (ngrok/log.(*PrefixLogger).Info:83) [registry] [tun] No affinity cache specified
[16:41:56 CST 2017/04/20] [INFO] (ngrok/log.(*PrefixLogger).Info:83) [metrics] Reporting every 30 seconds
[16:41:57 CST 2017/04/20] [INFO] (ngrok/log.Info:112) Listening for public http connections on [::]:80
[16:41:57 CST 2017/04/20] [INFO] (ngrok/log.Info:112) Listening for public https connections on [::]:443
[16:41:57 CST 2017/04/20] [INFO] (ngrok/log.Info:112) Listening for control and proxy connections on [::]:4443
[16:41:57 CST 2017/04/20] [INFO] (ngrok/log.(*PrefixLogger).Info:83) [tun:627acc92] New connection from 42.53.196.242:9386
[16:41:57 CST 2017/04/20] [DEBG] (ngrok/log.(*PrefixLogger).Debug:79) [tun:627acc92] Waiting to read message
[16:41:57 CST 2017/04/20] [DEBG] (ngrok/log.(*PrefixLogger).Debug:79) [tun:627acc92] Reading message with length: 159

如果需要后台运行可以使用screennohup,详情自行搜索。

附1:将ngrokd 添加到系统服务(CentOS)

新建系统服务文件ngrokd.service

sudo vim /usr/lib/systemd/system/ngrokd.service

[Unit]
Description=Share local port(s) with ngrok
After=syslog.target network.target

[Service]
PrivateTmp=true
Type=simple
Restart=always
RestartSec=1min
StandardOutput=null
StandardError=null
ExecStart=/usr/local/ngrok/bin/ngrokd -tlsKey=/usr/local/ngrok/assets/server/tls/snakeoil.key -tlsCrt=/usr/local/ngrok/assets/server/tls/snakeoil.crt -domain=xxx网址 -httpAddr=:8081 -httpsAddr=:443 -tunnelAddr=:8083 %i
ExecStop=/usr/bin/killall ngrok

[Install]
WantedBy=multi-user.target

保存并设置为默认启动服务

systemctl enable ngrok.service //加入开机启动
systemctl daemon-reload //重新载入 systemd,扫描新的或有变动的单元

将之前编译好的客户端文件拷贝到需要使用服务的设备上。

在ngrok同路径下建立配置文件ngrok.yml

server_addr: “ngrok.test.website:4443"
trust_host_root_certs: falsetunnels:
    ssh:
    remote_port: 6666
    proto:
      tcp: 22

server_addr端口默认4443,可通过ngrokd服务端启动修改端口。在tunnels里配置隧道信息,具体可见「翻译」ngrok 1.X 配置文档。注意httphttps隧道可设置subdomainauth,而tcp里只能设置remote_port

还可以转发其他IP的端口,方法就是在proto下的tcp(或http、https)后的端口号写成IP地址:端口号的格式(中间是英文冒号)。如:tcp: 192.168.11.1:80

现在运行客户端:

./ngrok -config=ngrok.yml start ssh

回车后,看到这样一个界面,说明启动成功:

Online

如果显示reconnecting说明连接有错,在运行时加入-log=stdout来进行debug。可能有以下几方面原因:

  1. 可能是服务器端口未开放,在服务器上使用sudo iptables --list查看当前规则
  2. 查看是否网络问题,ping到对应的地址检查
  3. 可能是编译的时候证书没有覆盖或者版本不对,重新编译试试

以下是我搭建服务器时参考的一些资料:

Related post

  1. NO IMAGE
  2. NO IMAGE
  3. NO IMAGE
  4. NO IMAGE
  5. NO IMAGE
  6. NO IMAGE

There are no comment yet.

ABOUT

老赵的个人博客,关于 Mac, iPhone, iPad, iPod等产品的软件和硬件技术交流。也讨论Linux/UNIX技术,服务器运维技术等。

2025 年 1 月
 1234
567891011
12131415161718
19202122232425
262728293031  

Powerd by WordPress on Xserve
Xserve 2009
@2012-2024 HelloMac Copyright