letterm commited on
Commit
1c6ea51
·
verified ·
1 Parent(s): 6b49430

Delete warp_api_server.py

Browse files
Files changed (1) hide show
  1. warp_api_server.py +0 -341
warp_api_server.py DELETED
@@ -1,341 +0,0 @@
1
- #!/usr/bin/env python3
2
- """
3
- Warp API 服务器
4
- 整合所有模块,提供OpenAI兼容的API接口和Token管理Web界面
5
- """
6
- import json
7
- import threading
8
- from flask import Flask, request, jsonify, Response, stream_with_context, render_template_string, session, redirect, url_for
9
- from loguru import logger
10
-
11
- from config import Config
12
- from utils import Utils
13
- from api_service import ApiService
14
-
15
- # 初始化日志
16
- Utils.setup_logging()
17
-
18
- # 创建Flask应用
19
- app = Flask(__name__)
20
- app.secret_key = 'warp-api-server-secret-key-2024' # 用于session管理
21
-
22
- # 创建API服务
23
- api_service = ApiService()
24
-
25
- def check_admin_auth():
26
- """检查管理员认证"""
27
- if not Config.require_admin_auth():
28
- return True
29
-
30
- # 检查session中的管理员认证状态
31
- return session.get('admin_authenticated', False)
32
-
33
- def verify_admin_key(admin_key: str) -> bool:
34
- """验证管理员密钥"""
35
- if not Config.require_admin_auth():
36
- return True
37
-
38
- return admin_key == Config.get_admin_key()
39
-
40
- @app.before_request
41
- def check_auth():
42
- """请求前鉴权检查"""
43
- # 跳过管理员认证的端点
44
- admin_auth_endpoints = ['admin_login', 'admin_auth']
45
- if request.endpoint in admin_auth_endpoints:
46
- return
47
-
48
- # 管理界面相关端点需要管理员认证
49
- admin_endpoints = ['index', 'token_status', 'add_tokens', 'batch_login', 'refresh_tokens', 'remove_tokens', 'export_tokens']
50
- if request.endpoint in admin_endpoints:
51
- if not check_admin_auth():
52
- if request.endpoint == 'index':
53
- return redirect(url_for('admin_login'))
54
- else:
55
- return jsonify({"error": "需要管理员认证"}), 401
56
-
57
- # API端点需要API密钥认证
58
- api_endpoints = ['get_models', 'chat_completions']
59
- if request.endpoint in api_endpoints:
60
- auth_header = request.headers.get('Authorization')
61
- if not api_service.authenticate_request(auth_header):
62
- return jsonify({"error": "未授权访问"}), 401
63
-
64
- @app.route('/admin/login')
65
- def admin_login():
66
- """管理员登录页面"""
67
- if not Config.require_admin_auth():
68
- return redirect(url_for('index'))
69
-
70
- if check_admin_auth():
71
- return redirect(url_for('index'))
72
-
73
- from web_template import get_admin_login_template
74
- return render_template_string(get_admin_login_template())
75
-
76
- @app.route('/admin/auth', methods=['POST'])
77
- def admin_auth():
78
- """管理员认证处理"""
79
- if not Config.require_admin_auth():
80
- return jsonify({"success": True, "redirect": "/"})
81
-
82
- try:
83
- data = request.get_json()
84
- admin_key = data.get('admin_key', '')
85
-
86
- if verify_admin_key(admin_key):
87
- session['admin_authenticated'] = True
88
- logger.info("🔐 管理员认证成功")
89
- return jsonify({"success": True, "message": "认证成功", "redirect": "/"})
90
- else:
91
- logger.warning("⚠️ 管理员认证失败")
92
- return jsonify({"success": False, "message": "管理员密钥错误"})
93
-
94
- except Exception as e:
95
- logger.error(f"❌ 管理员认证出错: {e}")
96
- return jsonify({"success": False, "message": "认证失败"}), 500
97
-
98
- @app.route('/admin/logout', methods=['POST'])
99
- def admin_logout():
100
- """管理员登出"""
101
- session.pop('admin_authenticated', None)
102
- return jsonify({"success": True, "message": "已登出"})
103
-
104
- @app.route('/')
105
- def index():
106
- """管理页面"""
107
- from web_template import get_html_template
108
- return render_template_string(get_html_template())
109
-
110
- @app.route(f"/{Config.OPENAI_API_VERSION}/models", methods=['GET'])
111
- def get_models():
112
- """获取模型列表"""
113
- return jsonify(api_service.get_models())
114
-
115
- @app.route(f"/{Config.OPENAI_API_VERSION}/chat/completions", methods=['POST'])
116
- def chat_completions():
117
- """聊天完成端点"""
118
- try:
119
- request_data = request.get_json()
120
- if not request_data:
121
- return jsonify({"error": "无效的请求数据"}), 400
122
-
123
- # 检查模型是否有效
124
- model = request_data.get("model")
125
- from model_mapper import ModelMapper
126
- if not ModelMapper.is_valid_model(model):
127
- return jsonify({"error": f"不支持的模型: {model}"}), 400
128
-
129
- stream = request_data.get("stream", False)
130
-
131
- if stream:
132
- # 流式响应
133
- def generate():
134
- for chunk in api_service.chat_completion(request_data, stream=True):
135
- yield chunk
136
-
137
- return Response(
138
- stream_with_context(generate()),
139
- content_type='text/event-stream',
140
- headers={
141
- 'Cache-Control': 'no-cache',
142
- 'Connection': 'keep-alive',
143
- 'Access-Control-Allow-Origin': '*'
144
- }
145
- )
146
- else:
147
- # 非流式响应
148
- response_text = ""
149
- for chunk in api_service.chat_completion(request_data, stream=False):
150
- response_text = chunk
151
- break
152
-
153
- return Response(
154
- json.dumps(response_text) if isinstance(response_text, dict) else response_text,
155
- content_type='application/json'
156
- )
157
-
158
- except Exception as e:
159
- logger.error(f"❌ 处理聊天请求时出错: {e}")
160
- return jsonify({"error": f"服务器内部错误: {str(e)}"}), 500
161
-
162
- @app.route('/token/status', methods=['GET'])
163
- def token_status():
164
- """获取token状态"""
165
- try:
166
- status = api_service.get_token_status()
167
- return jsonify(status)
168
- except Exception as e:
169
- return jsonify({"success": False, "message": str(e)}), 500
170
-
171
- @app.route('/token/add', methods=['POST'])
172
- def add_tokens():
173
- """添加token"""
174
- try:
175
- data = request.get_json()
176
- tokens = data.get('tokens', [])
177
-
178
- result = api_service.add_tokens(tokens)
179
- return jsonify(result)
180
-
181
- except Exception as e:
182
- return jsonify({"success": False, "message": str(e)}), 500
183
-
184
- @app.route('/token/remove', methods=['POST'])
185
- def remove_tokens():
186
- """删除token"""
187
- try:
188
- data = request.get_json()
189
- refresh_token = data.get('refresh_token')
190
-
191
- result = api_service.remove_refresh_token(refresh_token=refresh_token)
192
- return jsonify(result)
193
-
194
- except Exception as e:
195
- return jsonify({"success": False, "message": str(e)}), 500
196
-
197
- @app.route('/token/refresh', methods=['POST'])
198
- def refresh_tokens():
199
- """刷新所有token"""
200
- try:
201
- result = api_service.refresh_all_tokens()
202
- return jsonify(result)
203
- except Exception as e:
204
- return jsonify({"success": False, "message": str(e)}), 500
205
-
206
- @app.route('/token/export', methods=['POST'])
207
- def export_tokens():
208
- """导出refresh token(需要超级管理员密钥验证)"""
209
- try:
210
- data = request.get_json()
211
- super_admin_key = data.get('super_admin_key', '')
212
-
213
- result = api_service.export_refresh_tokens(super_admin_key)
214
- return jsonify(result)
215
-
216
- except Exception as e:
217
- logger.error(f"❌ 导出token时出错: {e}")
218
- return jsonify({"success": False, "message": str(e)}), 500
219
-
220
- @app.route('/login/batch', methods=['POST'])
221
- def batch_login():
222
- """批量获取refresh token"""
223
- try:
224
- data = request.get_json()
225
- email_url_pairs = data.get('email_url_pairs', [])
226
- max_workers = data.get('max_workers', 5)
227
-
228
- # 转换为字典格式
229
- email_url_dict = {}
230
- for pair in email_url_pairs:
231
- email = pair.get('email', '').strip()
232
- url = pair.get('url', '').strip()
233
-
234
- if email and url:
235
- email_url_dict[email] = url
236
-
237
- if not email_url_dict:
238
- return jsonify({'success': False, 'message': '没有有效的邮箱和URL对'}), 400
239
-
240
- result = api_service.batch_get_refresh_tokens(email_url_dict, max_workers)
241
- return jsonify(result)
242
-
243
- except Exception as e:
244
- logger.error(f"❌ 批量登录时出错: {e}")
245
- return jsonify({'success': False, 'message': f'服务器错误: {str(e)}'}), 500
246
-
247
- @app.route('/health', methods=['GET'])
248
- def health_check():
249
- """健康检查端点"""
250
- return jsonify({
251
- "status": "healthy",
252
- "timestamp": Utils.get_current_timestamp(),
253
- "version": "2.0.0"
254
- })
255
-
256
- def compile_protobuf_at_startup():
257
- """启动时编译protobuf"""
258
- logger.info("🔧 开始编译Protobuf文件...")
259
- try:
260
- from protobuf_manager import ProtobufManager
261
- success = ProtobufManager.validate_protobuf_module()
262
- if success:
263
- logger.success("✅ Protobuf模块验证成功")
264
- else:
265
- logger.warning("⚠️ Protobuf模块验证失败,但服务仍将启动")
266
- except Exception as e:
267
- logger.error(f"❌ 编译Protobuf时出错: {e}")
268
-
269
- def main():
270
- """主函数"""
271
- config = Config()
272
-
273
- print("=" * 80)
274
- print("🚀 启动 Warp API 服务器 v2.0")
275
- print("=" * 80)
276
- print(f"📡 服务器地址: http://localhost:{Config.SERVER_PORT}")
277
- print(f"🔧 管理界面: http://localhost:{Config.SERVER_PORT}")
278
- print(f"📚 模型端点: http://localhost:{Config.SERVER_PORT}/{Config.OPENAI_API_VERSION}/models")
279
- print(f"💬 聊天端点: http://localhost:{Config.SERVER_PORT}/{Config.OPENAI_API_VERSION}/chat/completions")
280
- print(f"❤️ 健康检查: http://localhost:{Config.SERVER_PORT}/health")
281
- print(f"📝 文件日志: {'启��' if Config.enable_file_logging() else '禁用'}")
282
-
283
- # 显示安全配置信息
284
- if Config.require_admin_auth():
285
- print(f"🔐 管理员认证: 已启用 (需要 ADMIN_KEY)")
286
- else:
287
- print("⚠️ 管理员认证: 未启用 (可通过 ADMIN_KEY 环境变量启用)")
288
-
289
- if Config.require_super_admin_auth():
290
- print(f"🔒 超级管理员认证: 已启用 (导出功能需要 SUPER_ADMIN_KEY)")
291
- else:
292
- print("⚠️ 超级管理员认证: 未启用 (可通过 SUPER_ADMIN_KEY 环境变量启用)")
293
-
294
- # 显示环境变量token信息
295
- env_tokens = Config.get_refresh_tokens()
296
- if env_tokens:
297
- print(f"🎯 环境变量Token: 已设置 {len(env_tokens)} 个")
298
- for i, token in enumerate(env_tokens, 1):
299
- print(f" #{i}: {token[:20]}...{token[-8:] if len(token) > 28 else ''}")
300
- else:
301
- print("⚠️ 环境变量Token: 未设置 (请设置 WARP_REFRESH_TOKEN)")
302
- print("💡 支持多个token,使用分号(;)分割:token1;token2;token3")
303
-
304
- print("-" * 80)
305
-
306
- try:
307
- # 编译protobuf
308
- compile_protobuf_at_startup()
309
-
310
- # 启动后台服务
311
- logger.info("🔄 启动后台服务...")
312
- api_service.start_services()
313
- logger.success("✅ 后台服务启动完成")
314
-
315
- logger.info("-" * 80)
316
- logger.success("🌟 服务器启动完成!")
317
- if Config.require_admin_auth():
318
- logger.info(f"🔐 访问管理界面需要管理员密钥: http://localhost:{Config.SERVER_PORT}")
319
- else:
320
- logger.info(f"🌐 访问管理界面: http://localhost:{Config.SERVER_PORT}")
321
- logger.info("-" * 80)
322
-
323
- # 启动Flask服务器
324
- app.run(
325
- host=Config.SERVER_HOST,
326
- port=Config.SERVER_PORT,
327
- debug=False,
328
- threaded=True
329
- )
330
-
331
- except KeyboardInterrupt:
332
- logger.info("🛑 接收到停止信号")
333
- except Exception as e:
334
- logger.error(f"❌ 服务器启动失败: {e}")
335
- finally:
336
- logger.info("🧹 清理资源...")
337
- api_service.stop_services()
338
- logger.info("👋 服务器已停止")
339
-
340
- if __name__ == "__main__":
341
- main()