Socket5 Proxy课程小项目(下) | 青训营笔记

63 阅读2分钟

这是我参与「第五届青训营 」伴学笔记创作活动的第 2 天

前言

上一篇已经是10天前了,我太摸鱼了,赶工赶工!

上回说到项目的前两个部分:搭建一个简单的服务器端环境;在服务器处理客户端请求的process中加入鉴权的逻辑,即加入auth()方法。

项目V3代码

在服务器处理客户端请求的process鉴权auth后,授权成功后进行后续连接操作,即加入connect()方法。 注意本项目的目标是完成一个代理服务器,所以服务器端会在成功授权后读取并解析客户端的连接请求,解析成功后,服务器端获取到客户端期待连接的目标ip或是目标域名。

此时connect()方法完成了一部分。

项目V4代码

在这part中加入了connect()方法的最后的逻辑,根据之前获得的客户端期待连接的ip或是域名,进行服务器端到目标的连接。

最后这一部分的代码我想了很久:

ctx, cancel := context.WithCancel(context.Background())
defer cancel()

go func() {
   _, _ = io.Copy(dest, reader)
   cancel()
}()
go func() {
   _, _ = io.Copy(conn, dest)
   cancel()
}()

<-ctx.Done()

dest是服务器端拨号目标地址获得的conn类型对象,conn是服务器端接收客户端获得的conn类型对象; reader是conn包装后的reader对象。

我猜这段代码大致的作用应该是开了两个协程完成一个代理通信,第一个可能是把reader中的信息写到dest连接中,服务器端就代理发送请求给目标;第二个可能是把dest传回给conn,把目标响应的内容写到conn中,客户端就能接收到。

这段最让我迷惑的就是这段代码的框架,搜了一下是什么上下文和取消函数,总之应该就是做协程之间的一个并发之类的?其中一个不能执行下去了,就直接取消掉其他协程然后退出嘛。再看看再看看,这几天多看点文档。