├── deno.js └── index.js /deno.js: -------------------------------------------------------------------------------- 1 | export default { 2 | async fetch(request: Request): Promise { 3 | // Handle CORS preflight request 4 | if (request.method === "OPTIONS") { 5 | return new Response(null, { 6 | headers: { 7 | "Access-Control-Allow-Origin": "*", 8 | "Access-Control-Allow-Methods": "POST, OPTIONS", 9 | "Access-Control-Allow-Headers": "Content-Type, Authorization", 10 | "Access-Control-Max-Age": "86400", 11 | }, 12 | }); 13 | } 14 | 15 | // Only handle POST requests 16 | if (request.method !== "POST") { 17 | return new Response("Method not allowed", { status: 405 }); 18 | } 19 | 20 | // Validate Authorization header 21 | const authHeader = request.headers.get("Authorization"); 22 | const TOKEN = Deno.env.get("TOKEN"); 23 | if (TOKEN) { 24 | if (!authHeader || authHeader !== `Bearer ${TOKEN}`) { 25 | return new Response("Unauthorized", { 26 | status: 401, 27 | headers: { 28 | "Content-Type": "application/json", 29 | "Access-Control-Allow-Origin": "*" 30 | } 31 | }); 32 | } 33 | } 34 | 35 | try { 36 | // Clone request body 37 | const body = await request.json(); 38 | 39 | // Construct new request headers 40 | const headers = new Headers({ 41 | "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/133.0.0.0 Safari/537.36 Edg/133.0.0.0", 42 | "Accept": "text/event-stream", 43 | "Accept-Encoding": "gzip, deflate, br, zstd", 44 | "Content-Type": "application/json", 45 | "sec-ch-ua-platform": "Windows", 46 | "X-Deepinfra-Source": "web-page", 47 | "sec-ch-ua": "\"Not(A:Brand\";v=\"99\", \"Microsoft Edge\";v=\"133\", \"Chromium\";v=\"133\"", 48 | "sec-ch-ua-mobile": "?0", 49 | "Origin": "https://deepinfra.com", 50 | "Sec-Fetch-Site": "same-site", 51 | "Sec-Fetch-Mode": "cors", 52 | "Sec-Fetch-Dest": "empty", 53 | "Referer": "https://deepinfra.com/" 54 | }); 55 | 56 | // Send request to DeepInfra 57 | const response = await fetch("https://api.deepinfra.com/v1/openai/chat/completions", { 58 | method: "POST", 59 | headers: headers, 60 | body: JSON.stringify(body) 61 | }); 62 | 63 | // Construct response 64 | const newResponse = new Response(response.body, { 65 | status: response.status, 66 | statusText: response.statusText, 67 | headers: { 68 | "Access-Control-Allow-Origin": "*", 69 | "Content-Type": response.headers.get("Content-Type") || "application/json", 70 | } 71 | }); 72 | 73 | return newResponse; 74 | 75 | } catch (error) { 76 | return new Response(JSON.stringify({ error: error.message }), { 77 | status: 500, 78 | headers: { 79 | "Content-Type": "application/json", 80 | "Access-Control-Allow-Origin": "*" 81 | } 82 | }); 83 | } 84 | } 85 | }; 86 | -------------------------------------------------------------------------------- /index.js: -------------------------------------------------------------------------------- 1 | export default { 2 | async fetch(request, env, ctx) { 3 | const url = new URL(request.url); 4 | 5 | // 处理 CORS 预检请求 6 | if (request.method === "OPTIONS") { 7 | return new Response(null, { 8 | headers: { 9 | "Access-Control-Allow-Origin": "*", 10 | "Access-Control-Allow-Methods": "POST, GET, OPTIONS", 11 | "Access-Control-Allow-Headers": "Content-Type, Authorization", 12 | "Access-Control-Max-Age": "86400", 13 | }, 14 | }); 15 | } 16 | 17 | // 处理 /v1/models 请求 18 | if (url.pathname === "/v1/models" && request.method === "GET") { 19 | // 鉴权验证 20 | if (env.TOKEN) { 21 | const authHeader = request.headers.get("Authorization"); 22 | if (!authHeader || authHeader !== `Bearer ${env.TOKEN}`) { 23 | return new Response("Unauthorized", { 24 | status: 401, 25 | headers: { 26 | "Content-Type": "application/json", 27 | "Access-Control-Allow-Origin": "*" 28 | } 29 | }); 30 | } 31 | } 32 | 33 | // 构建模型列表 34 | const models = { 35 | object: "list", 36 | data: [ 37 | { 38 | id: "deepseek-ai/DeepSeek-R1", 39 | object: "model", 40 | created: 1624980000, 41 | owned_by: "deepseek-ai" 42 | }, 43 | { 44 | id: "deepseek-ai/DeepSeek-V3", 45 | object: "model", 46 | created: 1632000000, 47 | owned_by: "deepseek-ai" 48 | }, 49 | { 50 | id: "deepseek-ai/DeepSeek-R1-Distill-Llama-70B", 51 | object: "model", 52 | created: 1640000000, 53 | owned_by: "deepseek-ai" 54 | }, 55 | { 56 | id: "deepseek-ai/DeepSeek-R1-Distill-Qwen-32B", 57 | object: "model", 58 | created: 1645000000, 59 | owned_by: "deepseek-ai" 60 | } 61 | ] 62 | }; 63 | 64 | return new Response(JSON.stringify(models), { 65 | headers: { 66 | "Content-Type": "application/json", 67 | "Access-Control-Allow-Origin": "*" 68 | } 69 | }); 70 | } 71 | 72 | // 处理其他 POST 请求 73 | if (request.method !== "POST") { 74 | return new Response("Method not allowed", { 75 | status: 405, 76 | headers: { 77 | "Access-Control-Allow-Origin": "*" 78 | } 79 | }); 80 | } 81 | 82 | // 验证鉴权头 83 | const authHeader = request.headers.get("Authorization"); 84 | if (env.TOKEN) { 85 | if (!authHeader || authHeader !== `Bearer ${env.TOKEN}`) { 86 | return new Response("Unauthorized", { 87 | status: 401, 88 | headers: { 89 | "Content-Type": "application/json", 90 | "Access-Control-Allow-Origin": "*" 91 | } 92 | }); 93 | } 94 | } 95 | 96 | try { 97 | // 原始请求处理逻辑 98 | const body = await request.json(); 99 | const headers = { 100 | "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/133.0.0.0 Safari/537.36 Edg/133.0.0.0", 101 | "Accept": "text/event-stream", 102 | "Accept-Encoding": "gzip, deflate, br, zstd", 103 | "Content-Type": "application/json", 104 | "sec-ch-ua-platform": "Windows", 105 | "X-Deepinfra-Source": "web-page", 106 | "sec-ch-ua": "\"Not(A:Brand\";v=\"99\", \"Microsoft Edge\";v=\"133\", \"Chromium\";v=\"133\"", 107 | "sec-ch-ua-mobile": "?0", 108 | "Origin": "https://deepinfra.com", 109 | "Sec-Fetch-Site": "same-site", 110 | "Sec-Fetch-Mode": "cors", 111 | "Sec-Fetch-Dest": "empty", 112 | "Referer": "https://deepinfra.com/" 113 | }; 114 | 115 | const response = await fetch("https://api.deepinfra.com/v1/openai/chat/completions", { 116 | method: "POST", 117 | headers: headers, 118 | body: JSON.stringify(body) 119 | }); 120 | 121 | return new Response(response.body, { 122 | status: response.status, 123 | headers: { 124 | "Access-Control-Allow-Origin": "*", 125 | "Content-Type": response.headers.get("Content-Type") 126 | } 127 | }); 128 | 129 | } catch (error) { 130 | return new Response(JSON.stringify({ error: error.message }), { 131 | status: 500, 132 | headers: { 133 | "Content-Type": "application/json", 134 | "Access-Control-Allow-Origin": "*" 135 | } 136 | }); 137 | } 138 | } 139 | }; 140 | --------------------------------------------------------------------------------