OpenAI api代理的搭建 代码

49 min read
  1. 新建一个 Cloudflare Worker
  2. 复制 cf_worker.js 里的代码粘贴到 Worker 中并部署
  3. 给 Worker 绑定一个没有被 GFW 墙的域名
  4. 使用自己的域名代替 api.openai.com
const TELEGRAPH_URL = 'https://api.openai.com';

addEventListener('fetch', event => {
  event.respondWith(handleRequest(event.request))
})

async function handleRequest(request) {
  const url = new URL(request.url);
  const headers_Origin = request.headers.get("Access-Control-Allow-Origin") || "*"
  url.host = TELEGRAPH_URL.replace(/^https?:\/\//, '');
  const modifiedRequest = new Request(url.toString(), {
    headers: request.headers,
    method: request.method,
    body: request.body,
    redirect: 'follow'
  });
  const response = await fetch(modifiedRequest);
  const modifiedResponse = new Response(response.body, response);
  // 添加允许跨域访问的响应头
  modifiedResponse.headers.set('Access-Control-Allow-Origin', headers_Origin);
  return modifiedResponse;
}


nginx 配置

server {
    listen 80;

    location / {
        # 设置反向代理地址
        proxy_pass https://api.openai.com;

        # 将请求的 Host 头设置为目标服务器的域名
        proxy_set_header Host api.openai.com;

        # 允许跨域
        add_header 'Access-Control-Allow-Origin' '*';
        
        # 其他可能需要的跨域头部
        add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
        add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
        add_header 'Access-Control-Expose-Headers' 'Content-Length,Content-Range';

        # 关于跨域的预请求,返回 204
        if ($request_method = 'OPTIONS') {
            return 204;
        }
    }
}

Go的实现

package main

import (
	"net/http"
	"net/http/httputil"
	"net/url"
)

func main() {
	// 目标 URL
	targetUrl, _ := url.Parse("https://api.openai.com")

	// 创建反向代理
	proxy := httputil.NewSingleHostReverseProxy(targetUrl)

	// 更新请求头
	proxy.ModifyResponse = func(r *http.Response) error {
		r.Header.Set("Access-Control-Allow-Origin", "*")
		r.Header.Set("Access-Control-Allow-Methods", "GET, POST, OPTIONS")
		r.Header.Set("Access-Control-Allow-Headers", "DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range")
		r.Header.Set("Access-Control-Expose-Headers", "Content-Length,Content-Range")
		return nil
	}

	// 启动 HTTP 服务器
	http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
		proxy.ServeHTTP(w, r)
	})

	http.ListenAndServe(":8080", nil)
}