golang实现正向代理http_proxy和https_proxy

Go 复制代码
package main

import (
	"bytes"
	"fmt"
	"io"
	"log"
	"net"
	"net/url"
	"strings"
)

func main() {
	// tcp 连接,监听 8080 端口
	l, err := net.Listen("tcp", ":8080")
	if err != nil {
		log.Panic(err)
	}

	// 死循环,每当遇到连接时,调用 handle
	for {
		client, err := l.Accept()
		if err != nil {
			log.Panic(err)
		}

		go handle(client)
	}
}

func handle(client net.Conn) {
	if client == nil {
		return
	}
	defer client.Close()

	log.Printf("remote addr: %v\n", client.RemoteAddr())

	// 用来存放客户端数据的缓冲区
	var b [1024]byte
	//从客户端获取数据
	n, err := client.Read(b[:])
	if err != nil {
		log.Println(err)
		return
	}

	var method, URL, address string
	// 从客户端数据读入 method,url
	fmt.Sscanf(string(b[:bytes.IndexByte(b[:], '\n')]), "%s%s", &method, &URL)
	hostPortURL, err := url.Parse(URL)
	if err != nil {
		log.Println(err)
		return
	}

	// 如果方法是 CONNECT,则为 https 协议
	if method == "CONNECT" {
		address = hostPortURL.Scheme + ":" + hostPortURL.Opaque
	} else { //否则为 http 协议
		address = hostPortURL.Host
		// 如果 host 不带端口,则默认为 80
		if strings.Index(hostPortURL.Host, ":") == -1 { //host 不带端口, 默认 80
			address = hostPortURL.Host + ":80"
		}
	}

	//获得了请求的 host 和 port,向服务端发起 tcp 连接
	server, err := net.Dial("tcp", address)
	if err != nil {
		log.Println(err)
		return
	}
	//如果使用 https 协议,需先向客户端表示连接建立完毕
	if method == "CONNECT" {
		fmt.Fprint(client, "HTTP/1.1 200 Connection established\r\n\r\n")
	} else { //如果使用 http 协议,需将从客户端得到的 http 请求转发给服务端
		server.Write(b[:n])
	}

	//将客户端的请求转发至服务端,将服务端的响应转发给客户端。io.Copy 为阻塞函数,文件描述符不关闭就不停止
	go io.Copy(server, client)
	io.Copy(client, server)
}
相关推荐
chillxiaohan7 小时前
GO学习记录——多文件调用
开发语言·学习·golang
2501_9159184110 小时前
常见 iOS 抓包工具的使用,从代理抓包、设备抓包到数据流抓包
android·ios·小程序·https·uni-app·iphone·webview
Grassto11 小时前
11 Go Module 缓存机制详解
开发语言·缓存·golang·go·go module
福大大架构师每日一题12 小时前
ollama v0.15.2发布:新增Clawdbot集成指令,全面支持Ollama模型启动!
golang·ollama
参.商.14 小时前
【Day25】26.删除有序数组中的重复项 80.删除有序数组中的重复项II
leetcode·golang
小高Baby@14 小时前
ShouldBind、ShouldBindJson、ShouldBindQuery的区别
后端·golang
moxiaoran575315 小时前
Go语言的文件操作
开发语言·后端·golang
赴前尘16 小时前
记一次golang进程执行卡住的问题排查
开发语言·后端·golang
暴躁小师兄数据学院18 小时前
【WEB3.0零基础转行笔记】Golang编程篇-第3讲:GO语言中的运算符
笔记·golang·web3
小二·18 小时前
Go 语言系统编程与云原生开发实战(第9篇)安全加固实战:认证授权 × 数据加密 × 安全审计(生产级落地)
安全·云原生·golang