├── scf_bootstrap ├── .gitignore ├── go.mod ├── main.go └── README.md /scf_bootstrap: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | ./main -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | main 2 | main.zip 3 | .DS_Store 4 | -------------------------------------------------------------------------------- /go.mod: -------------------------------------------------------------------------------- 1 | module github.com/riba2534/openai-scf-goproxy 2 | 3 | go 1.18 4 | -------------------------------------------------------------------------------- /main.go: -------------------------------------------------------------------------------- 1 | package main 2 | 3 | import ( 4 | "log" 5 | "net/http" 6 | "net/http/httputil" 7 | "net/url" 8 | "time" 9 | ) 10 | 11 | func main() { 12 | targetUrl := "https://api.openai.com" // 目标域名和端口 13 | target, err := url.Parse(targetUrl) 14 | if err != nil { 15 | log.Fatal(err) 16 | } 17 | 18 | // 创建反向代理 19 | proxy := httputil.NewSingleHostReverseProxy(target) 20 | 21 | // 修改请求头,将Host设置为目标域名 22 | proxy.Director = func(req *http.Request) { 23 | req.Host = target.Host 24 | req.URL.Scheme = target.Scheme 25 | req.URL.Host = target.Host 26 | } 27 | 28 | // 打印HTTP请求和响应的日志 29 | proxy.ModifyResponse = func(resp *http.Response) error { 30 | // 打印HTTP响应的日志 31 | responseDump, err := httputil.DumpResponse(resp, true) 32 | if err != nil { 33 | log.Printf("Failed to dump response: %v\n", err) 34 | } else { 35 | log.Printf("Response: \n%s\n", string(responseDump)) 36 | } 37 | 38 | return nil 39 | } 40 | 41 | // 设置日志前缀和输出位置 42 | log.SetFlags(log.Ldate | log.Ltime | log.Lshortfile) 43 | 44 | // 启动HTTP服务器 45 | http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { 46 | // 打印HTTP请求日志 47 | requestDump, err := httputil.DumpRequest(r, true) 48 | if err != nil { 49 | log.Printf("Failed to dump request: \n%v\n", err) 50 | } else { 51 | log.Printf("%s Request: %s\n", time.Now().Format("2006-01-02 15:04:05"), string(requestDump)) 52 | } 53 | // 反向代理转发 54 | proxy.ServeHTTP(w, r) 55 | }) 56 | 57 | log.Printf("Starting server on port 9000...\n") 58 | if err := http.ListenAndServe(":9000", nil); err != nil { 59 | log.Fatal(err) 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # 腾讯云函数1分钟搭建 OpenAI 国内代理 2 | 3 | > 项目地址: https://github.com/riba2534/openai-scf-goproxy 4 | > 5 | > ps: **建议大家自己部署好之后在函数配置里面调一调参数,包括但不限于把并发度调高,超时时间调长,可以解决很多问题** 6 | 7 | 最近有一个好消息,OpenAI 开放了自己的 API,开发者可以很方便的调用各种语言模型来完成自己的创意,但是由于众所周知的原因国内访问 OpenAI 时接口可能大概率超时或者调不通,那解决无非是通过 proxy 的方式: 8 | 9 | - 直接在境外服务器运行自己的服务,缺点是国内访问可能比较慢 10 | - 国内服务器运行服务,把 OpenAPI 的相关请求用境外服务器做一层转发 11 | 12 | 本文介绍一种对于国内相对而言比较方便的办法,使用腾讯云函数来完成一个指向 OpenAI 的反向代理服务搭建,完成后开发者开发时直接把请求 OpenAPI 的接口直接指向腾讯云函数的地址即可。 13 | 14 | 直接开始正题 15 | 16 | 17 | ## 第一步:新建云函数 18 | 19 | 1. 打开腾讯云函数控制台: https://console.cloud.tencent.com/scf/list?rid=5&ns=default 20 | 2. 页面左边「函数服务」中,点击「新建」,然后照着下面图填: 21 | 22 | - 点「从头开始」 23 | - 函数类型选 web函数 24 | - 名称自己随便填 25 | - 地域选择一个境外的,推荐新加坡(香港好像不在openai支持地区内) 26 | - 运行环境选 Go1 27 | - 时区选上海 28 | - 提交方法:本地上传zip包 29 | - 日志投递也推荐选上,方便看日志 30 | - 触发器配置照着图看 31 | 32 | ![云函数.png](https://image-1252109614.cos.ap-beijing.myqcloud.com/2023/03/09/64096590d8255.png) 33 | 34 | 3. 注意,上传的 zip 包可以在本项目 [releases](https://github.com/riba2534/openai-scf-goproxy/releases) 中下载到,最新的包地址是: [main.zip](https://github.com/riba2534/openai-scf-goproxy/releases/download/V2.0/main.zip) 35 | 36 | 37 | ## 第二步:查看部署信息 38 | 39 | 新建好之后,在腾讯云函数列表中找到你刚创建的,从左边 「函数管理」-> 「函数代码」,找到你的访问路径 40 | 41 | ![1678337783998.png](https://image-1252109614.cos.ap-beijing.myqcloud.com/2023/03/09/640966f88f891.png) 42 | 43 | 44 | 这个访问路径就是你之后请求 OpenAPI 的访问路径,访问路径的格式是 `https://service-xxxxxx.hk.apigw.tencentcs.com/release/` 45 | 46 | 注意: 这里的访问路径后面有个 `/release/` 你在用的时候把这个去掉,即: `https://service-xxxxxx.hk.apigw.tencentcs.com` 47 | 48 | 49 | 50 | **重要提示**:云函数默认访问的超时时间较短,而调用 openai 的时间可能很长,所以我们需要改一下云函数配置,把超时时间调大,在左边「函数管理」-> 「函数配置」 里面,把访问的超时时间和并发度调大,如下图: 51 | 52 | [![超时时间.png](https://image-1252109614.cos.ap-beijing.myqcloud.com/2023/03/13/640ece0cc7848.png)](https://image-1252109614.cos.ap-beijing.myqcloud.com/2023/03/13/640ece0cc7848.png) 53 | 54 | [![并发配置.png](https://image-1252109614.cos.ap-beijing.myqcloud.com/2023/03/13/640ece0c4dd58.png)](https://image-1252109614.cos.ap-beijing.myqcloud.com/2023/03/13/640ece0c4dd58.png) 55 | 56 | ### 大功告成 57 | 58 | 至此,一个指向 openAPI 的反向代理就搭好了,你在开发的时候使用国内服务器,只需要把 `api.openapi.com` 换成这个新的地址就可以了. 59 | 60 | 我们可以通过类似 postman 这种工具来测试一下是否可用,查询一个完成模型试试,可以看到,成功的返回了信息! 61 | 62 | ![1678338111283.png](https://image-1252109614.cos.ap-beijing.myqcloud.com/2023/03/09/6409683fa484c.png) 63 | 64 | 65 | # 玩耍 66 | 67 | 接下来就需要去看看 OpenAI 的接口文档了: https://platform.openai.com/docs/introduction 68 | --------------------------------------------------------------------------------