bahi-bh commited on
Commit
88a6b83
·
verified ·
1 Parent(s): 90cf7ed

Create app.py

Browse files
Files changed (1) hide show
  1. app.py +228 -0
app.py ADDED
@@ -0,0 +1,228 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import asyncio
2
+ import json
3
+ from concurrent.futures import ThreadPoolExecutor
4
+ from typing import List
5
+
6
+ import g4f
7
+
8
+ from fastapi import FastAPI, HTTPException, Header
9
+ from fastapi.middleware.cors import CORSMiddleware
10
+ from fastapi.responses import StreamingResponse
11
+ from pydantic import BaseModel
12
+
13
+ # =====================================
14
+ # CONFIG
15
+ # =====================================
16
+
17
+ API_KEY = "sk-your-secret-key"
18
+
19
+ PROVIDERS = [
20
+ g4f.Provider.DuckDuckGo,
21
+ g4f.Provider.Blackbox,
22
+ ]
23
+
24
+ executor = ThreadPoolExecutor(max_workers=5)
25
+
26
+ # =====================================
27
+ # APP
28
+ # =====================================
29
+
30
+ app = FastAPI(
31
+ title="HuggingFace AI Gateway"
32
+ )
33
+
34
+ app.add_middleware(
35
+ CORSMiddleware,
36
+ allow_origins=["*"],
37
+ allow_methods=["*"],
38
+ allow_headers=["*"],
39
+ )
40
+
41
+ # =====================================
42
+ # MODELS
43
+ # =====================================
44
+
45
+ class Message(BaseModel):
46
+ role: str
47
+ content: str
48
+
49
+ class ChatRequest(BaseModel):
50
+ model: str = "gpt-4o-mini"
51
+ messages: List[Message]
52
+ stream: bool = False
53
+
54
+ # =====================================
55
+ # AUTH
56
+ # =====================================
57
+
58
+ def verify_api_key(auth: str):
59
+
60
+ if not auth.startswith("Bearer "):
61
+ raise HTTPException(
62
+ status_code=401,
63
+ detail="Invalid Authorization"
64
+ )
65
+
66
+ token = auth.replace("Bearer ", "")
67
+
68
+ if token != API_KEY:
69
+ raise HTTPException(
70
+ status_code=403,
71
+ detail="Invalid API Key"
72
+ )
73
+
74
+ # =====================================
75
+ # GENERATE
76
+ # =====================================
77
+
78
+ def generate(model, messages):
79
+
80
+ last_error = None
81
+
82
+ for provider in PROVIDERS:
83
+
84
+ try:
85
+
86
+ response = g4f.ChatCompletion.create(
87
+ model=model,
88
+ provider=provider,
89
+ messages=messages
90
+ )
91
+
92
+ return response
93
+
94
+ except Exception as e:
95
+
96
+ print(f"{provider.__name__}: {e}")
97
+
98
+ last_error = e
99
+
100
+ raise Exception(str(last_error))
101
+
102
+ # =====================================
103
+ # STREAM
104
+ # =====================================
105
+
106
+ async def stream_generate(model, messages):
107
+
108
+ loop = asyncio.get_event_loop()
109
+
110
+ for provider in PROVIDERS:
111
+
112
+ try:
113
+
114
+ response = await loop.run_in_executor(
115
+ executor,
116
+ lambda: g4f.ChatCompletion.create(
117
+ model=model,
118
+ provider=provider,
119
+ messages=messages,
120
+ stream=True
121
+ )
122
+ )
123
+
124
+ for chunk in response:
125
+
126
+ if chunk:
127
+
128
+ payload = {
129
+ "choices": [
130
+ {
131
+ "delta": {
132
+ "content": chunk
133
+ }
134
+ }
135
+ ]
136
+ }
137
+
138
+ yield f"data: {json.dumps(payload)}\\n\\n"
139
+
140
+ yield "data: [DONE]\\n\\n"
141
+
142
+ return
143
+
144
+ except Exception as e:
145
+
146
+ print(f"Streaming Error: {e}")
147
+
148
+ continue
149
+
150
+ yield f"data: {json.dumps({'error':'All providers failed'})}\\n\\n"
151
+
152
+ # =====================================
153
+ # API
154
+ # =====================================
155
+
156
+ @app.get("/")
157
+ async def home():
158
+
159
+ return {
160
+ "status": "online"
161
+ }
162
+
163
+ @app.post("/v1/chat/completions")
164
+ async def chat(
165
+ req: ChatRequest,
166
+ authorization: str = Header(None)
167
+ ):
168
+
169
+ if not authorization:
170
+ raise HTTPException(
171
+ status_code=401,
172
+ detail="Missing Authorization"
173
+ )
174
+
175
+ verify_api_key(authorization)
176
+
177
+ messages = [
178
+ m.model_dump()
179
+ for m in req.messages
180
+ ]
181
+
182
+ # =================================
183
+ # STREAM
184
+ # =================================
185
+
186
+ if req.stream:
187
+
188
+ return StreamingResponse(
189
+ stream_generate(
190
+ req.model,
191
+ messages
192
+ ),
193
+ media_type="text/event-stream"
194
+ )
195
+
196
+ # =================================
197
+ # NORMAL
198
+ # =================================
199
+
200
+ loop = asyncio.get_event_loop()
201
+
202
+ try:
203
+
204
+ response = await loop.run_in_executor(
205
+ executor,
206
+ lambda: generate(
207
+ req.model,
208
+ messages
209
+ )
210
+ )
211
+
212
+ return {
213
+ "choices": [
214
+ {
215
+ "message": {
216
+ "role": "assistant",
217
+ "content": response
218
+ }
219
+ }
220
+ ]
221
+ }
222
+
223
+ except Exception as e:
224
+
225
+ raise HTTPException(
226
+ status_code=500,
227
+ detail=str(e)
228
+ )