ubuntu搭建内网穿透服务Ngrok

说些闲话:

最近一直在乱折腾,看看C,看看Python,又打算去看一下PHP,然后又是前端的Vue.Js,最后发现——嗯?我都在干些什么?

当然不论是在做什么,看什么,基本上还是在学习,这个状态还是比较满意的。值得一提的是,当我发现bash的好用之处后,毫不犹豫的就把我的开发环境迁移到了还算是比较熟悉的Linux发行版本——Ubuntu上。然后就开始了在Ubuntu上的折腾之旅。

因为是用虚拟机搭建的Ubuntu,所以绝大多数情况下,开着VM使用虚拟机的感觉和真机体验差别并不大,虽然有考虑收购一台二手笔记本或组装一台二手台式机用来区分开发环境和日常使用(游戏)环境,但是目前还是没有这个资金的预算的。因此为了方便日常开发调试,就遇到了一个尴尬的问题,外网环境下无法访问内网(本地虚拟机)的Ubuntu系统。

之前在开发参赛项目的时候有遇到过Ngrok,于是在网上搜索了几个Ngrok的服务,然而用起来都不尽如人意,趁着Qcloud上的Ubuntu服务器还没到期,试着自己搭建一个Ngrok的服务器,用于内网穿透。


先介绍一下Ngrok

Ngrok on github

Ngrok is a tunneling, reverse proxy that establishes secure tunnels from a public endpoint to a locally running network service while capturing all traffic for inspection and replay.

翻译一下:

Ngrok是一个隧道,即建立安全通道从公共端点到本地运行的网络服务,同时捕捉检查和重播所有流量的反向代理。

简单来说,他可以代理你本地的数据,并将其转发到外网。

具体操作走起!

Step1:安装git 和Golang

Git是啥,是干什么用的,在此我就不过多阐述了!

# sudo apt-get install build-essential golang mercurial git

Golang,Go语言支持,因为Ngrok是基于Go语言编写的

这里我都已经安装了,没有安装的按照提示安装即可


Step2:获取 Ngrok 源码

此处使用非官方地址,修复了部分包无法获取

# git clone https://github.com/tutumcloud/ngrok.git ngrok
# cd ngrok

Step3:生成自签名证书

使用ngrok.com官方服务时,我们使用的是官方的SSL证书。自建ngrokd服务,如果不想买SSL证书,我们需要生成自己的自签名证书,并编译一个携带该证书的ngrok客户端。

证书生成过程需要一个NGROK_BASE_DOMAIN。 以ngrok官方随机生成的地址693c358d.ngrok.com为例,其NGROK_BASE_DOMAIN就是“ngrok.com”,如果你要 提供服务的地址为 “example.ngrok.xxx.com”,那NGROK_BASE_DOMAIN就应该 是“ngrok.xxx.com”。这里呢,我替换成自己的域名 “ngrok.mdzz2333.cn”

$ cd ngrok

# NGROK_DOMAIN="ngrok.mdzz2333.cn"

# openssl genrsa -out base.key 2048
# openssl req -new -x509 -nodes -key base.key -days 10000 -subj "/CN=$NGROK_DOMAIN" -out base.pem
# openssl genrsa -out server.key 2048
# openssl req -new -key server.key -subj "/CN=$NGROK_DOMAIN" -out server.csr
# openssl x509 -req -in server.csr -CA base.pem -CAkey base.key -CAcreateserial -days 10000 -out server.crt

执行完后

替换: # cp base.pem assets/client/tls/ngrokroot.crt


Step4:编译

# sudo make release-server release-client

这一步骤等待时间较长,成功编译后,会在bin目录下找到ngrokd和ngrok这两个文件。


Step5:启动服务端

前面生成的 ngrokd 就是服务端程序了,指定证书、域名和端口启动它(证书就是前面生成的,注意修改域名):

# sudo ./bin/ngrokd -tlsKey=server.key -tlsCrt=server.crt -domain="ngrok.mdzz2333.cn" -httpAddr=":8081" -httpsAddr=":8082"

到这一步,ngrok 服务已经跑起来了,可以通过屏幕上显示的日志查看更多信息。httpAddr、httpsAddr 分别是 ngrok 用来转发 http、https 服务的端口,可以随意指定。ngrokd 还会开一个 4443 端口用来跟客户端通讯(可通过 -tunnelAddr=”:xxx” 指定),如果你配置了 iptables 规则,需要放行这三个端口上的 TCP 协议。

现在,通过 http://ngrok.mdzz2333.cn:8081http://ngrok.mdzz2333.cn:8082就可以访问到 ngrok 提供的转发服务。为了使用方便,建议把域名泛解析到 VPS 上,这样能方便地使用不同子域转发不同的本地服务。

访问后看到提示:

Tunnel pub.imququ.com:8081 not found

这说明万事俱备,只差客户端来连了。

在服务端为了保证服务的一直启动,可以使用screen,此处略过.

注意:上述代码示例和域名示例请更改成自己的域名!!!


Step6:客户端 单有服务端,你转发什么捏?肯定要在你需要发布内容(web,服务)的设备上安装匹配的客户端啊。在这里,我使用的服务器是ubuntu,而需要转发的服务器,也是ubuntu,就省去了重新编译这一环节。

将/ngrok/bin目录下的 ngrok 通过ssh的scp指令下载到当前客户端所在的系统中。

# scp username@serverIp:/ngrok/bin/ngrok /home/ubunutu/ngrok

上述指令根据服务器信息和本地路径替换

创建一个ngrok配置文件:ngrok.cfg 写入以下内容:

server_addr: “ngrok.mdzz2333.cn:4443"
trust_host_root_certs: false

注意:这里的server_addr换成前面配置的自签名证书中的域名 另外,这个域名请提前解析到服务器IP,参考如下:

接下来只需要指定子域、要转发的协议和端口,以及配置文件,运行客户端:

#./ngrok -subdomain pub -proto=http -config=ngrok.cfg 80

如果没有错误,就会出现下面的界面

这表示转发成功,转发后的端口号,是在服务端中设置的端口号,转发为你填写的本地端口号。

在本地环境访问Web Interface也可以查看该端口转发下的请求

一个简单的ngrok转发就配置好了,只需要一个外网服务器和域名,就可以轻松的将你所有的内网服务器/虚拟主机/SSH转发到外网。

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏风中追风

java类的加载过程和类加载器的分析

我们知道,我们写的java代码保存的格式是 .java, java文件被编译后会转换为字节码,字节码可以在任何平台通过java虚拟机来运行,这也是java能够跨...

55780
来自专栏ascii0x03的安全笔记

【C++】小心使用文件读写模式:回车('\r') 换行('\n')问题的一次纠结经历

原来没有仔细注意C++读写文件的二进制模式和文本模式,这次吃了大亏。(平台:windows  VS2012) BUG出现: 写了一个程序A,生成一个文本文件F保...

38770
来自专栏北京马哥教育

面试分享系列 | 17道Python面试题,让你在求职中无往不利

今天给大家分享的是Python面试题系列的第一篇文章,后续我也会陆续整理Python相关的问题给大家,无论是求职者还是新人都可以通过面试题来考察自己的能力缺陷。...

37640
来自专栏农夫安全

代码审计入门总结

0x00 简介 ---- 之前看了seay写的PHP代码审计的书,全部浏览了一遍,作为一个代码审计小白,希望向一些和我一样的小白的人提供一下我的收获,以及一个整...

36370
来自专栏Golang语言社区

Go语言并发模型:以并行处理MD5为例

简介 Go语言的并发原语允许开发者以类似于 Unix Pipe 的方式构建数据流水线 (data pipelines),数据流水线能够高效地利用 I/O和多核 ...

47460
来自专栏我是攻城师

给Java字节码加上”翅膀“的JIT编译器

上面文章在介绍Java的内存模型的时候,提到过由于编译器的优化会导致重排序的问题,其中一个比较重要的点地方就是关于JIT编译器的功能。JIT的英文单词是Just...

13150
来自专栏一个爱瞎折腾的程序猿

常用cmd代码片段及.net core打包脚本分享

保存:set currentPath=%cd% 输出:echo %currentPath

12830
来自专栏玄魂工作室

看代码学渗透 Day5 - escapeshellarg与escapeshellcmd使用不当

--------------------------------------------------------------------------------...

34620
来自专栏Java学习之路

Struts2学习---result结果集 result type:全局结果集:动态结果集带有参数的结果集

这一章节主要介绍如何配置结果集,分为以下几个知识点: 结果集类型(result type) 全局结果集(global types) 动态结果集(dynamic ...

33140
来自专栏大内老A

WCF技术剖析之二十三:服务实例(Service Instance)生命周期如何控制[上篇]

服务调用的目的体现在对某项服务功能的消费上,而功能的实现又定义在相应的服务类型中。不论WCF服务端框架处理服务调用请求的流程有多么复杂,最终都落实在服务实例的激...

24880

扫码关注云+社区

领取腾讯云代金券