Spaces:
Sleeping
Sleeping
| """ | |
| Jarvis AI Automation Planner β Hugging Face Space Application | |
| Exposes two interfaces: | |
| 1. Gradio chat UI at / (browser testing) | |
| 2. OpenAI-compatible POST /v1/chat/completions (mobile clients) | |
| """ | |
| import json | |
| import logging | |
| import os | |
| import time | |
| import uuid | |
| import gradio as gr | |
| import uvicorn | |
| from fastapi import FastAPI, Request | |
| from fastapi.middleware.cors import CORSMiddleware | |
| from fastapi.responses import JSONResponse | |
| from jarvis.agent import JarvisAgent | |
| from jarvis.tools import ToolRegistry | |
| # --------------------------------------------------------------------------- | |
| # Logging | |
| # --------------------------------------------------------------------------- | |
| logging.basicConfig( | |
| level=logging.INFO, | |
| format="%(asctime)s %(name)-20s %(levelname)-7s %(message)s", | |
| ) | |
| logger = logging.getLogger("jarvis.app") | |
| # --------------------------------------------------------------------------- | |
| # Initialise agent (loaded once at startup) | |
| # --------------------------------------------------------------------------- | |
| registry = ToolRegistry() | |
| agent = JarvisAgent(registry=registry) | |
| logger.info("Jarvis agent ready β’ model=%s β’ tools=%s", agent.model, registry.tool_names()) | |
| # --------------------------------------------------------------------------- | |
| # Gradio chat interface | |
| # --------------------------------------------------------------------------- | |
| def chat_fn(message: str, _history: list) -> str: | |
| """Gradio handler β takes a user message and returns the JSON plan.""" | |
| plan = agent.plan(message) | |
| return json.dumps(plan, indent=2) | |
| demo = gr.ChatInterface( | |
| fn=chat_fn, | |
| title="π€ Jarvis β AI Automation Planner", | |
| description=( | |
| "Type a command (e.g. *\"download a galaxy image\"*) and Jarvis will " | |
| "return a structured JSON automation plan for your mobile device." | |
| ), | |
| examples=[ | |
| "Download a galaxy image", | |
| "Open YouTube", | |
| "Search water bottle for boys", | |
| "Download a galaxy image and send it to Arun", | |
| "Set an alarm for 7 AM", | |
| "Search Google for latest AI news", | |
| ], | |
| type="messages", | |
| ) | |
| # --------------------------------------------------------------------------- | |
| # Custom FastAPI routes (mounted alongside Gradio) | |
| # --------------------------------------------------------------------------- | |
| app = FastAPI(title="Jarvis β AI Automation Planner", version="1.0.0") | |
| app.add_middleware( | |
| CORSMiddleware, | |
| allow_origins=["*"], | |
| allow_methods=["*"], | |
| allow_headers=["*"], | |
| ) | |
| async def chat_completions(request: Request): | |
| """OpenAI-compatible chat completions endpoint for mobile clients.""" | |
| try: | |
| body = await request.json() | |
| except Exception: | |
| return JSONResponse({"error": "Invalid JSON body."}, status_code=400) | |
| messages = body.get("messages", []) | |
| if not messages: | |
| return JSONResponse({"error": "No messages provided."}, status_code=400) | |
| user_msg = "" | |
| for m in reversed(messages): | |
| if m.get("role") == "user": | |
| user_msg = m.get("content", "") | |
| break | |
| if not user_msg: | |
| return JSONResponse({"error": "No user message found."}, status_code=400) | |
| plan = agent.plan(user_msg) | |
| return JSONResponse({ | |
| "id": f"chatcmpl-{uuid.uuid4().hex[:12]}", | |
| "object": "chat.completion", | |
| "created": int(time.time()), | |
| "model": agent.model, | |
| "choices": [ | |
| { | |
| "index": 0, | |
| "message": { | |
| "role": "assistant", | |
| "content": json.dumps(plan), | |
| }, | |
| "finish_reason": "stop", | |
| } | |
| ], | |
| "usage": {"prompt_tokens": 0, "completion_tokens": 0, "total_tokens": 0}, | |
| }) | |
| async def list_models(): | |
| return { | |
| "object": "list", | |
| "data": [{"id": agent.model, "object": "model", "owned_by": "jarvis"}], | |
| } | |
| async def health(): | |
| return {"status": "ok", "model": agent.model, "tools": registry.tool_names()} | |
| # --------------------------------------------------------------------------- | |
| # Mount Gradio onto the FastAPI app at root | |
| # --------------------------------------------------------------------------- | |
| app = gr.mount_gradio_app(app, demo, path="/") | |
| # --------------------------------------------------------------------------- | |
| # Entry point | |
| # --------------------------------------------------------------------------- | |
| if __name__ == "__main__": | |
| uvicorn.run("app:app", host="0.0.0.0", port=7860, log_level="info") | |