diff --git a/app/api/gemini/__init__.py b/app/api/gemini/__init__.py deleted file mode 100644 index 0d3c8e1..0000000 --- a/app/api/gemini/__init__.py +++ /dev/null @@ -1,3 +0,0 @@ -"""Gemini Routes""" - -from .gemini import router as gemini_router diff --git a/app/api/llm/__init__.py b/app/api/llm/__init__.py new file mode 100644 index 0000000..678e5f6 --- /dev/null +++ b/app/api/llm/__init__.py @@ -0,0 +1,3 @@ +"""LLM Routes""" + +from .llm import router as llm_router diff --git a/app/api/gemini/gemini.py b/app/api/llm/llm.py similarity index 87% rename from app/api/gemini/gemini.py rename to app/api/llm/llm.py index 700adaf..7481a98 100644 --- a/app/api/gemini/gemini.py +++ b/app/api/llm/llm.py @@ -4,15 +4,15 @@ router = APIRouter() -@router.get("/gemini") +@router.get("/llm") def root() -> dict: - """GET /gemini endpoint.""" - meta = make_meta("success", "Gemini endpoint says hello") + """GET /llm endpoint.""" + meta = make_meta("success", "LLM endpoint says hello") return {"meta": meta} -@router.post("/gemini") -def gemini_post(payload: dict) -> dict: - """POST /gemini: send prompt to Gemini, returns completion google-genai SDK.""" +@router.post("/llm") +def llm_post(payload: dict) -> dict: + """POST /llm: send prompt to Gemini, returns completion google-genai SDK.""" prompt = payload.get("prompt") if not prompt: raise HTTPException(status_code=400, detail="Missing 'prompt' in request body.") diff --git a/app/api/prompts/__init__.py b/app/api/prompts/__init__.py deleted file mode 100644 index 8775bfb..0000000 --- a/app/api/prompts/__init__.py +++ /dev/null @@ -1,3 +0,0 @@ -"""Prompts Routes""" - -from .prompts import router as prompts_router diff --git a/app/api/prompts/prompts.py b/app/api/prompts/prompts.py deleted file mode 100644 index efd1307..0000000 --- a/app/api/prompts/prompts.py +++ /dev/null @@ -1,114 +0,0 @@ -from fastapi import HTTPException -from app import __version__ - -import os -from app.utils.make_meta import make_meta -from fastapi import APIRouter, Query, Path, status -from app.utils.db import get_db_connection -from app.api.prompts.schemas import PromptCreate, PromptOut -from fastapi import Body - -router = APIRouter() -base_url = os.getenv("BASE_URL", "http://localhost:8000") - -@router.get("/prompts") -def root() -> dict: - """GET /prompts endpoint.""" - from fastapi import status - meta = None - data = [] - # Check if 'prompts' table exists - from app.utils.db import get_db_connection_direct - conn = get_db_connection_direct() - try: - with conn.cursor() as cur: - cur.execute(""" - SELECT EXISTS ( - SELECT FROM information_schema.tables - WHERE table_name = 'prompts' - ); - """) - result = cur.fetchone() - exists = result[0] if result else False - finally: - conn.close() - if not exists: - meta = make_meta("warning", "Table 'prompts' does not exist.") - return {"meta": meta} - else: - meta = make_meta("success", "Prompts") - # Fetch all records from prompts table - data = [] - conn = get_db_connection_direct() - try: - with conn.cursor() as cur: - cur.execute("SELECT id, prompt, response, llm, started, completed, timestamp FROM prompts ORDER BY id DESC;") - rows = cur.fetchall() - keys = ["id", "prompt", "response", "llm", "started", "completed", "timestamp"] - for row in rows: - data.append(dict(zip(keys, row))) - finally: - conn.close() - return {"meta": meta, "data": data} - - - -# POST /prompts endpoint -@router.post("/prompts", status_code=status.HTTP_201_CREATED) -def create_prompt(prompt_in: PromptCreate = Body(...)): - """Create a new prompt record in the prompts table.""" - from app.utils.db import get_db_connection_direct - import psycopg2 - import time - conn = get_db_connection_direct() - started = prompt_in.started if prompt_in.started is not None else int(time.time()) - try: - with conn.cursor() as cur: - cur.execute( - """ - INSERT INTO prompts (prompt, response, llm, started, completed, timestamp) - VALUES (%s, %s, %s, %s, %s, COALESCE(%s, NOW())) - RETURNING id, prompt, response, llm, started, completed, timestamp - """, - ( - prompt_in.prompt, - None, # Always set response to NULL initially - prompt_in.llm, - started, - None, # completed is NULL initially - None, # timestamp - ) - ) - row = cur.fetchone() - conn.commit() - except psycopg2.Error as e: - conn.rollback() - return {"error": str(e)} - finally: - conn.close() - if row: - keys = ["id", "prompt", "response", "llm", "started", "completed", "timestamp"] - return dict(zip(keys, row)) - return {"error": "Failed to insert prompt."} - - -# DELETE /prompts/{id} endpoint -@router.delete("/prompts/{id}", status_code=status.HTTP_200_OK) -def delete_prompt(id: int): - """Delete a prompt record by id from the prompts table.""" - from app.utils.db import get_db_connection_direct - import psycopg2 - conn = get_db_connection_direct() - try: - with conn.cursor() as cur: - cur.execute("DELETE FROM prompts WHERE id = %s RETURNING id;", (id,)) - row = cur.fetchone() - conn.commit() - except psycopg2.Error as e: - conn.rollback() - raise HTTPException(status_code=500, detail=str(e)) - finally: - conn.close() - if row: - return {"success": True, "deleted_id": row[0]} - raise HTTPException(status_code=404, detail=f"Prompt with id {id} not found.") diff --git a/app/api/prompts/schemas.py b/app/api/prompts/schemas.py deleted file mode 100644 index e44773f..0000000 --- a/app/api/prompts/schemas.py +++ /dev/null @@ -1,16 +0,0 @@ -from pydantic import BaseModel -from typing import Optional - -class PromptCreate(BaseModel): - prompt: str - llm: str - started: Optional[int] = None # Unix epoch, set by backend if not provided - -class PromptOut(BaseModel): - id: int - prompt: str - response: Optional[str] - llm: str - started: int - completed: Optional[int] - timestamp: str diff --git a/app/api/prompts/utils/alter_prompts_table_add_started_completed.sql b/app/api/prompts/utils/alter_prompts_table_add_started_completed.sql deleted file mode 100644 index b5a92ff..0000000 --- a/app/api/prompts/utils/alter_prompts_table_add_started_completed.sql +++ /dev/null @@ -1,5 +0,0 @@ --- Migration: Update prompts table for async processing -ALTER TABLE prompts - DROP COLUMN IF EXISTS duration_ms, - ADD COLUMN IF NOT EXISTS started BIGINT NOT NULL DEFAULT (extract(epoch from now())), - ADD COLUMN IF NOT EXISTS completed BIGINT; diff --git a/app/api/prompts/utils/create_prompts_table.py b/app/api/prompts/utils/create_prompts_table.py deleted file mode 100644 index 6c9eb08..0000000 --- a/app/api/prompts/utils/create_prompts_table.py +++ /dev/null @@ -1,20 +0,0 @@ -import os -import sys -sys.path.insert(0, os.path.abspath(os.path.join(os.path.dirname(__file__), '../../../../'))) -from app.utils.db import get_db_connection_direct - -def run_create_prompts_table_sql(): - sql_path = os.path.join(os.path.dirname(__file__), "create_prompts_table.sql") - with open(sql_path, "r") as f: - sql = f.read() - conn = get_db_connection_direct() - try: - with conn.cursor() as cur: - cur.execute(sql) - conn.commit() - print("prompts table created or already exists.") - finally: - conn.close() - -if __name__ == "__main__": - run_create_prompts_table_sql() diff --git a/app/api/prompts/utils/create_prompts_table.sql b/app/api/prompts/utils/create_prompts_table.sql deleted file mode 100644 index 7836126..0000000 --- a/app/api/prompts/utils/create_prompts_table.sql +++ /dev/null @@ -1,9 +0,0 @@ --- Migration: Create prompts table -CREATE TABLE IF NOT EXISTS prompts ( - id SERIAL PRIMARY KEY, - prompt TEXT NOT NULL, - response TEXT NOT NULL, - duration_ms INTEGER NOT NULL, - timestamp TIMESTAMPTZ NOT NULL DEFAULT NOW(), - llm VARCHAR(128) NOT NULL -); diff --git a/app/api/prompts/utils/migrate_prompts_table.py b/app/api/prompts/utils/migrate_prompts_table.py deleted file mode 100644 index b0f07b7..0000000 --- a/app/api/prompts/utils/migrate_prompts_table.py +++ /dev/null @@ -1,40 +0,0 @@ -""" -Python migration script to update prompts table: -- Remove duration_ms column -- Add started (BIGINT NOT NULL, default now as epoch) -- Add completed (BIGINT, nullable) -""" -import os -import psycopg2 -from dotenv import load_dotenv - -load_dotenv() - -ALTER_SQL = """ -ALTER TABLE prompts - DROP COLUMN IF EXISTS duration_ms, - ADD COLUMN IF NOT EXISTS started BIGINT NOT NULL DEFAULT (extract(epoch from now())), - ADD COLUMN IF NOT EXISTS completed BIGINT; -""" - -def main(): - conn = psycopg2.connect( - host=os.getenv('DB_HOST'), - port=os.getenv('DB_PORT', '5432'), - dbname=os.getenv('DB_NAME'), - user=os.getenv('DB_USER'), - password=os.getenv('DB_PASSWORD'), - ) - try: - with conn.cursor() as cur: - cur.execute(ALTER_SQL) - conn.commit() - print("Migration applied successfully.") - except Exception as e: - conn.rollback() - print(f"Migration failed: {e}") - finally: - conn.close() - -if __name__ == "__main__": - main() diff --git a/app/api/root.py b/app/api/root.py index 77df888..cd8e87f 100644 --- a/app/api/root.py +++ b/app/api/root.py @@ -20,7 +20,7 @@ def root() -> dict: "time": epoch, } endpoints = [ - {"name": "gemini", "url": f"{base_url}/gemini"}, + {"name": "llm", "url": f"{base_url}/llm"}, {"name": "docs", "url": f"{base_url}/docs"}, {"name": "resend", "url": f"{base_url}/resend"}, {"name": "health", "url": f"{base_url}/health"}, diff --git a/app/api/routes.py b/app/api/routes.py index 243dd37..5b540f2 100644 --- a/app/api/routes.py +++ b/app/api/routes.py @@ -10,16 +10,15 @@ from app.api.root import router as root_router from app.api.health import router as health_router from app.api.resend.resend import router as resend_router -from app.api.prompts.prompts import router as prompts_router +from app.api.llm.llm import router as llm_router from app.api.prospects.prospects import router as prospects_router from app.api.prospects.search import router as prospects_search_router -from app.api.gemini.gemini import router as gemini_router +from app.api.llm.llm import router as gemini_router router.include_router(root_router) router.include_router(resend_router) router.include_router(health_router) -router.include_router(prompts_router) +router.include_router(llm_router) router.include_router(prospects_search_router) router.include_router(prospects_router) router.include_router(gemini_router) -