网络编程入门, 100行实现Websocket转TCP代理

本文发表于入职啦(公众号: ruzhila) 大家可以访问入职啦学习更多的编程实战。

🎉 用Go实现Websocket转TCP代理,浏览器可以访问TCP Socket,网络编程入门 实用项目 👏 🎉

项目地址

代码已经开源, websockify-go 👏 欢迎Star

代码运行效果:

Websockify

所有的项目都在github上开源:100-line-code 欢迎Star 👏

用100行代码的不同语言(Java、Python、Go、Javascript、Rust)实现项目,通过讲解项目的实现,帮助大家学习编程

会定期在群里分享最新的项目实战代码,包括不同语言的实现

老师还会详细讲解代码优化的思路,扫码加入实战群:
入群学习

为什么需要Websocket转TCP

Websocket是一种全双工通信协议,可以在浏览器和服务器之间建立持久连接,用于实时通信。但是Websocket只支持文本和二进制数据,无法直接访问TCP Socket。
如果要在网页上访问TCP Socket,就需要一个代理服务器,将Websocket请求转发到TCP Socket, 这就是Websocket转TCP代理:

Websocket <----> Websocket转TCP代理 <----> TCP Socket

典型的场景:

  • 在浏览器上访问VNC远程桌面
  • 在浏览器上访问SSH终端
  • 在浏览器上访问数据库管理工具
  • 在浏览器上访问自定义TCP服务, 比如游戏服务器或者IM服务器

novnc/websockify是一个非常流行的Websocket转TCP代理,但是它是用Python实现的,性能不够好,代码也很复杂

用Go实现一个Websocket转TCP代理,性能更好,更稳定

Go实现Websocket转TCP代理

Go特别适合网络编程,标准库提供了丰富的网络库,不仅性能好,而且代码简洁,只需要一个可执行文件就可以运行,不需要依赖其他库
这次要通过100行代码实现一个Websocket转TCP代理:

  • 要支持SSL
  • 要支持自定义URL路径
  • 要支持自定义目标地址
  • 完整的单元测试和标准的服务程序架构

代码

在这里插入图片描述

代码解析

代码结构

  • cmd/main.go 是程序的入口,解析命令行参数,启动服务
  • websockify.go 是Websocket转TCP代理的核心代码
  • websockify_test.go 是单元测试代码
  • Dockerfile 是构建Docker镜像的文件,方便部署可以直接上生产系统

启动一个HTTP服务器

在这里插入图片描述

  • 82行: 监听一个HTTP端口
  • 89-95行: 如果是443并且有SSL证书,就启动一个HTTPS服务器
  • 86行: 利用标准库创建一个能自定义处理的HTTP Server

处理Websocket请求

采用了gorilla/websocket库来处理Websocket请求,这个库是Go语言中最流行的Websocket库

所有的业务逻辑都在ServeHTTP函数:
在这里插入图片描述

  • 31行: 升级HTTP连接为Websocket连接, Websocket协议是基于GET这个HTTP请求升级为Websocket协议
  • 36行: 利用defer关键字,当链接断开的时候,关闭TCP连接,确保不会泄露资源
  • 44-59行: 读取Websocket数据,转发到TCP Socket
  • 60-73行: 读取TCP Socket数据,转发到Websocket
一个链接启动了两个协程

其实从ServerHTTP这个函数开始,系统库就为每个请求创建了一个协程,这个协程负责处理这个请求
在这个函数里面又启动了两个协程:

  • 一个负责读取Websocket数据
  • 一个负责读取TCP Socket数据

这样就实现了一个链接同时处理两个方向的数据流

  • 43和75行 创建了能接受err的channel,当处理数据从协程出现错误的时候,就会发送一个错误到这个channel,然后当前的主协程就会退出关闭链接

单元测试

golang的单元测试非常的方便,只需要在文件名后面加上_test.go,然后在函数名前面加上Test就可以了
在这里插入图片描述

单元测试的逻辑:

  • 2-28行 创建一个测试用的TCP服务器,写了一个Echo服务器,就是把接收到的数据原样返回
  • 31-41行 创建一个Websockify代理服务器
  • 43-63行 启动一个Websocket客户端测试链接是否能正常工作

标准的服务器程序架构

这个项目提供了Dockerfile,现在Docker是最主要的线上程序交付方式,强烈建议用Docker部署服务
基于flag这个库,来处理命令行参数,这是Go语言标准库提供的命令行参数解析库

程序能支持的命令行参数来控制服务的启动

总结

通过Websockify这个项目,学习了Go语言的网络编程,Websocket是一个非常重要的协议,可以用于实时通信,实现一个Websockify的转发代理,对于内部项目的开发非常有用

Docker也是非常重要的技术,我们提供了Dockerfile,可以直接部署到生产环境

过去的演示项目都没提供单元测试,这里提供了一个非常实用的单元测试流程,大家可以参考即便是复杂的流程也是可以通过单元测试来验证的

交流

构建一个100行代码项目的实战群,大家可以扫码加入,一起学习编程

入群学习

也可以访问入职啦学习更多的编程实战

所有的代码都在github上开源:100-line-code 欢迎Star 👏

  • 25
    点赞
  • 18
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
实现WebSocket的反向代理,可以使用Spring Boot提供的WebSocketStompClient来实现。首先,需要添加以下依赖到你的项目中: ```xml <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-websocket</artifactId> </dependency> ``` 然后,你需要配置你的WebSocket拦截器,可以通过添加`@ServerEndpoint`注解和设置configurator来获取Filter中的数据。这里需要注意的是,要加上断点注解:`@ServerEndpoint(value = "/websocket", configurator = WebSocketConfigurator.class)`。这样,你就可以通过session来获取Filter中的数据了。 接下来是分布式部署和共享的问题。在分布式部署中,WebSocket的共享问题可以通过使用消息代理来解决。你可以使用Spring的消息中间件,如RabbitMQ或ActiveMQ,来实现WebSocket的消息代理。通过配置消息代理,你可以确保WebSocket的消息在多个节点之间共享。 最后,如果你遇到了无法注入对象的问题,可以检查你的WebSocket配置是否正确,并确保你的对象被正确注入。你可以使用`@Autowired`注解来注入对象。如果仍然无法注入对象,可能需要检查你的配置和代码逻辑是否正确。 总结起来,要实现Spring Boot的WebSocket反向代理,你需要添加必要的依赖和配置WebSocket拦截器。在分布式部署中,你可以使用消息代理来解决WebSocket的共享问题。如果遇到无法注入对象的问题,可以检查配置和代码逻辑是否正确。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值