| |
| """ |
| Hugging Face Spaces Application - Fixed Version |
| """ |
|
|
| import os |
| import sys |
| import subprocess |
| import json |
| import time |
|
|
| |
| def install_requirements(): |
| try: |
| print("Installing requirements...") |
| subprocess.check_call([sys.executable, "-m", "pip", "install", "-r", "requirements.txt"]) |
| print("Requirements installed successfully!") |
| except Exception as e: |
| print(f"Failed to install requirements: {e}") |
| |
| try: |
| subprocess.check_call([sys.executable, "-m", "pip", "install", "flask"]) |
| subprocess.check_call([sys.executable, "-m", "pip", "install", "flask-cors"]) |
| subprocess.check_call([sys.executable, "-m", "pip", "install", "requests"]) |
| except: |
| pass |
|
|
| |
| install_requirements() |
|
|
| |
| try: |
| from flask import Flask, request, jsonify, Response, send_from_directory |
| from flask_cors import CORS |
| print("Flask modules imported successfully!") |
| except ImportError as e: |
| print(f"Failed to import Flask: {e}") |
| sys.exit(1) |
|
|
| |
| app = Flask(__name__) |
| CORS(app) |
|
|
| |
| CONFIG_FILE = "business_gemini_session.json" |
|
|
| |
| def load_config(): |
| if os.path.exists(CONFIG_FILE): |
| with open(CONFIG_FILE, 'r', encoding='utf-8') as f: |
| return json.load(f) |
| return { |
| "proxy": "", |
| "proxy_enabled": False, |
| "accounts": [], |
| "models": [] |
| } |
|
|
| |
| def save_config(config): |
| try: |
| with open(CONFIG_FILE, 'w', encoding='utf-8') as f: |
| json.dump(config, f, indent=2, ensure_ascii=False) |
| return True |
| except Exception as e: |
| print(f"Error saving config: {e}") |
| return False |
|
|
| |
| @app.route('/') |
| def index(): |
| """Main page - serve HTML if exists, otherwise show simple interface""" |
| if os.path.exists('index.html'): |
| return send_from_directory('.', 'index.html') |
|
|
| |
| return """ |
| <!DOCTYPE html> |
| <html> |
| <head> |
| <title>Business Gemini Pool</title> |
| <style> |
| body { font-family: Arial, sans-serif; max-width: 800px; margin: 0 auto; padding: 20px; } |
| .card { background: #f5f5f5; padding: 20px; border-radius: 8px; margin: 20px 0; } |
| .btn { background: #007bff; color: white; padding: 10px 20px; border: none; border-radius: 4px; cursor: pointer; } |
| .input { width: 100%; padding: 8px; margin: 5px 0; border: 1px solid #ddd; border-radius: 4px; } |
| </style> |
| </head> |
| <body> |
| <h1>🚀 Business Gemini Pool</h1> |
| |
| <div class="card"> |
| <h2>Status</h2> |
| <p>✅ Server is running successfully!</p> |
| <p><a href="/health">Health Check</a> | <a href="/v1/models">Models API</a></p> |
| </div> |
| |
| <div class="card"> |
| <h2>Quick Account Setup</h2> |
| <p>Add your Gemini account to start using the API:</p> |
| <button class="btn" onclick="showAccountForm()">Add Account</button> |
| <div id="accountForm" style="display:none; margin-top: 20px;"> |
| <input type="text" class="input" id="teamId" placeholder="Team ID"><br> |
| <input type="text" class="input" id="secureCookie" placeholder="Secure Cookie"><br> |
| <input type="text" class="input" id="hostCookie" placeholder="Host Cookie"><br> |
| <input type="text" class="input" id="sessionIndex" placeholder="Session Index"><br> |
| <input type="text" class="input" id="userAgent" placeholder="User Agent"><br> |
| <button class="btn" onclick="saveAccount()">Save Account</button> |
| </div> |
| </div> |
| |
| <script> |
| function showAccountForm() { |
| document.getElementById('accountForm').style.display = 'block'; |
| } |
| |
| async function saveAccount() { |
| const account = { |
| team_id: document.getElementById('teamId').value, |
| secure_c_ses: document.getElementById('secureCookie').value, |
| host_c_oses: document.getElementById('hostCookie').value, |
| csesidx: document.getElementById('sessionIndex').value, |
| user_agent: document.getElementById('userAgent').value, |
| available: true |
| }; |
| |
| try { |
| const response = await fetch('/api/accounts', { |
| method: 'POST', |
| headers: { 'Content-Type': 'application/json' }, |
| body: JSON.stringify(account) |
| }); |
| const result = await response.json(); |
| if (result.success) { |
| alert('Account saved successfully!'); |
| document.getElementById('accountForm').style.display = 'none'; |
| } else { |
| alert('Error: ' + result.error); |
| } |
| } catch (error) { |
| alert('Error: ' + error.message); |
| } |
| } |
| </script> |
| </body> |
| </html> |
| """ |
|
|
| @app.route('/health') |
| def health(): |
| """Health check endpoint""" |
| return jsonify({ |
| "status": "ok", |
| "timestamp": time.time(), |
| "message": "Business Gemini Pool is running" |
| }) |
|
|
| @app.route('/v1/models') |
| def models(): |
| """List available models (OpenAI compatible)""" |
| config = load_config() |
|
|
| |
| default_models = [ |
| { |
| "id": "gemini-enterprise", |
| "object": "model", |
| "created": int(time.time()), |
| "owned_by": "google" |
| }, |
| { |
| "id": "gemini-3-pro-preview", |
| "object": "model", |
| "created": int(time.time()), |
| "owned_by": "google" |
| } |
| ] |
|
|
| |
| custom_models = config.get('models', []) |
| if custom_models: |
| for model in custom_models: |
| default_models.append({ |
| "id": model.get('id', model.get('name', 'custom-model')), |
| "object": "model", |
| "created": int(time.time()), |
| "owned_by": "custom" |
| }) |
|
|
| return jsonify({ |
| "object": "list", |
| "data": default_models |
| }) |
|
|
| @app.route('/v1/chat/completions', methods=['POST']) |
| def chat_completions(): |
| """Chat completions endpoint (OpenAI compatible)""" |
| try: |
| data = request.get_json() |
| if not data or 'messages' not in data: |
| return jsonify({"error": "Missing messages field"}), 400 |
|
|
| |
| config = load_config() |
| accounts = config.get('accounts', []) |
|
|
| if not accounts: |
| return jsonify({ |
| "error": { |
| "message": "No Gemini accounts configured. Please add an account through the web interface.", |
| "type": "invalid_request_error" |
| } |
| }), 400 |
|
|
| |
| |
| return jsonify({ |
| "id": "chatcmpl-" + str(int(time.time())), |
| "object": "chat.completion", |
| "created": int(time.time()), |
| "model": data.get("model", "gemini-enterprise"), |
| "choices": [{ |
| "index": 0, |
| "message": { |
| "role": "assistant", |
| "content": "This is a placeholder response. The full Gemini integration requires your account credentials. Please configure your Gemini account through the web interface to get actual responses." |
| }, |
| "finish_reason": "stop" |
| }], |
| "usage": { |
| "prompt_tokens": len(str(data.get('messages', []))), |
| "completion_tokens": 50, |
| "total_tokens": len(str(data.get('messages', []))) + 50 |
| } |
| }) |
|
|
| except Exception as e: |
| return jsonify({"error": str(e)}), 500 |
|
|
| @app.route('/api/accounts', methods=['GET']) |
| def get_accounts(): |
| """Get all configured accounts""" |
| config = load_config() |
| accounts = config.get('accounts', []) |
|
|
| |
| safe_accounts = [] |
| for acc in accounts: |
| safe_accounts.append({ |
| "id": acc.get('id'), |
| "team_id": acc.get('team_id'), |
| "available": acc.get('available', True) |
| }) |
|
|
| return jsonify(safe_accounts) |
|
|
| @app.route('/api/accounts', methods=['POST']) |
| def add_account(): |
| """Add a new account""" |
| try: |
| data = request.get_json() |
| if not data: |
| return jsonify({"error": "No data provided"}), 400 |
|
|
| |
| required_fields = ['team_id', 'secure_c_ses', 'host_c_oses', 'csesidx', 'user_agent'] |
| for field in required_fields: |
| if not data.get(field): |
| return jsonify({"error": f"Missing required field: {field}"}), 400 |
|
|
| config = load_config() |
| if 'accounts' not in config: |
| config['accounts'] = [] |
|
|
| |
| account_id = str(int(time.time())) |
| data['id'] = account_id |
| data['available'] = True |
|
|
| config['accounts'].append(data) |
|
|
| if save_config(config): |
| return jsonify({"success": True, "id": account_id}) |
| else: |
| return jsonify({"error": "Failed to save configuration"}), 500 |
|
|
| except Exception as e: |
| return jsonify({"error": str(e)}), 500 |
|
|
| @app.route('/v1/status') |
| def status(): |
| """Get system status""" |
| config = load_config() |
| return jsonify({ |
| "status": "running", |
| "accounts_count": len(config.get('accounts', [])), |
| "proxy_enabled": config.get('proxy_enabled', False), |
| "proxy_url": config.get('proxy', ''), |
| "models": config.get('models', []), |
| "space_info": { |
| "environment": "huggingface", |
| "python_version": sys.version, |
| "platform": sys.platform |
| } |
| }) |
|
|
| |
| if not os.path.exists(CONFIG_FILE): |
| initial_config = { |
| "proxy": "", |
| "proxy_enabled": False, |
| "accounts": [], |
| "models": [] |
| } |
| save_config(initial_config) |
| print(f"Created initial config file: {CONFIG_FILE}") |
|
|
| if __name__ == "__main__": |
| print("\n" + "="*60) |
| print("Business Gemini Pool for Hugging Face Spaces") |
| print("="*60) |
| print(f"Python version: {sys.version}") |
| print(f"Working directory: {os.getcwd()}") |
| print(f"Config file: {CONFIG_FILE}") |
|
|
| |
| if os.path.exists(CONFIG_FILE): |
| config = load_config() |
| print(f"Accounts configured: {len(config.get('accounts', []))}") |
| else: |
| print("No config file found, will create on first run") |
|
|
| print("="*60) |
| print("Starting server...") |
|
|
| |
| port = int(os.environ.get("PORT", 7860)) |
| app.run(host="0.0.0.0", port=port, debug=False) |