File size: 4,244 Bytes
689e710
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
# app.py
import asyncio
from flask import Flask, request, jsonify
from proxy_lite import Runner, RunnerConfig
import os
import logging

# Configure logging for better visibility in Space logs
logging.basicConfig(level=logging.INFO, format='%(asctime)s - %(levelname)s - %(message)s')
logger = logging.getLogger(__name__)

app = Flask(__name__)

# Global runner instance. It will be initialized once.
_runner = None

async def initialize_runner():
    """Initializes the Proxy-lite Runner asynchronously."""
    global _runner
    if _runner is None:
        logger.info("Initializing Proxy-lite Runner...")
        # Retrieve Hugging Face API Token from environment variables (set as Space Secret)
        hf_api_token = os.environ.get("HF_API_TOKEN")
        if not hf_api_token:
            logger.error("HF_API_TOKEN environment variable not set. Cannot initialize Runner.")
            raise ValueError("HF_API_TOKEN environment variable not set. Please set it as a Space secret.")

        config = RunnerConfig.from_dict({
            "environment": {
                "name": "webbrowser",
                "homepage": "https://www.google.com",
                "headless": True, # Runs browser without a visible UI
            },
            "solver": {
                "name": "simple",
                "agent": {
                    "name": "proxy_lite",
                    "client": {
                        "name": "convergence",
                        "model_id": "convergence-ai/proxy-lite-3b",
                        # THIS IS THE HUGGING FACE INFERENCE API ENDPOINT
                        "api_base": "https://api-inference.huggingface.co/models/convergence-ai/proxy-lite-3b",
                        "api_key": hf_api_token # Use the token from environment variable
                    }
                }
            }
        })
        _runner = Runner(config)
        logger.info("Proxy-lite Runner initialized successfully.")
    return _runner

# Helper function to run asynchronous code within a synchronous Flask route
def run_async_task(coro):
    """Helper to run async coroutines in a synchronous context (like Flask routes)."""
    loop = asyncio.get_event_loop()
    return loop.run_until_complete(coro)

@app.route('/run_proxy_task', methods=['POST'])
def run_proxy_task_endpoint():
    """API endpoint to receive a task and execute it with Proxy-lite."""
    data = request.json
    task = data.get('task')
    if not task:
        logger.warning("Received request without 'task' field. Returning 400.")
        return jsonify({"error": "No 'task' provided in request body"}), 400

    logger.info(f"Received task for proxy-lite: '{task}'")
    try:
        # Initialize runner if not already done
        runner = run_async_task(initialize_runner())
        # Run the task using the proxy-lite runner
        result = run_async_task(runner.run(task))

        logger.info(f"Proxy-lite task completed. Output: {result[:200]}...") # Log truncated output
        # Return the result as a JSON response
        return jsonify({"output": result})
    except Exception as e:
        logger.exception(f"Error processing task '{task}':") # Logs full traceback for debugging
        return jsonify({"error": f"An error occurred: {str(e)}. Check logs for details."}), 500

@app.route('/')
def root():
    """Basic root endpoint for health check."""
    logger.info("Root endpoint accessed.")
    return "Proxy-lite API is running. Send POST requests to /run_proxy_task with a 'task' in JSON body."

if __name__ == '__main__':
    # Check if HF_API_TOKEN is set during local development/testing
    if not os.environ.get("HF_API_TOKEN"):
        logger.error("HF_API_TOKEN environment variable is not set. Please set it for local testing.")
        # For local execution, you might choose to exit or just log
        # For deployment on Hugging Face Spaces, it MUST be set as a Secret.
        # exit(1) # Uncomment this if you want to force exit without token locally

    logger.info("Starting Flask development server on 0.0.0.0:7860...")
    # Hugging Face Spaces requires binding to 0.0.0.0 and listening on port 7860
    app.run(host='0.0.0.0', port=7860, debug=True) # debug=True for local, disable for production