From db5ef316453d54e0432707777c1aeaf1e0675389 Mon Sep 17 00:00:00 2001 From: Heisenberg208 Date: Fri, 20 Feb 2026 19:27:02 +0530 Subject: [PATCH 1/4] [SAM-260011]: feat: add folders in sample folder --- .gitignore | 2 +- requirements.txt | 20 ++++++++++++++++++++ src/{ => sample}/api/__init__.py | 0 src/{ => sample}/api/fast_api.py | 0 src/{ => sample}/db/__init__.py | 0 src/{ => sample}/db/connection.py | 0 src/{features => sample/utils}/__init__.py | 0 src/{ => sample}/utils/_version.py | 0 src/{ => sample}/utils/constants.py | 0 src/{ => sample}/utils/debug.py | 0 src/{ => sample}/utils/helper.py | 0 src/{ => sample}/utils/lint.py | 0 src/{ => sample}/utils/load_messages.py | 0 src/{ => sample}/utils/templates.py | 0 src/utils/__init__.py | 0 15 files changed, 21 insertions(+), 1 deletion(-) create mode 100644 requirements.txt rename src/{ => sample}/api/__init__.py (100%) rename src/{ => sample}/api/fast_api.py (100%) rename src/{ => sample}/db/__init__.py (100%) rename src/{ => sample}/db/connection.py (100%) rename src/{features => sample/utils}/__init__.py (100%) rename src/{ => sample}/utils/_version.py (100%) rename src/{ => sample}/utils/constants.py (100%) rename src/{ => sample}/utils/debug.py (100%) rename src/{ => sample}/utils/helper.py (100%) rename src/{ => sample}/utils/lint.py (100%) rename src/{ => sample}/utils/load_messages.py (100%) rename src/{ => sample}/utils/templates.py (100%) delete mode 100644 src/utils/__init__.py diff --git a/.gitignore b/.gitignore index cf997a8..c4ee0ae 100644 --- a/.gitignore +++ b/.gitignore @@ -135,7 +135,7 @@ celerybeat.pid *.sage.py # Environments -.env +.env** .envrc .venv* env/ diff --git a/requirements.txt b/requirements.txt new file mode 100644 index 0000000..253daf3 --- /dev/null +++ b/requirements.txt @@ -0,0 +1,20 @@ +annotated-doc==0.0.4 ; python_version >= "3.10" and python_version < "3.13" +annotated-types==0.7.0 ; python_version >= "3.10" and python_version < "3.13" +anyio==4.12.1 ; python_version >= "3.10" and python_version < "3.13" +click==8.3.1 ; python_version >= "3.10" and python_version < "3.13" +colorama==0.4.6 ; python_version >= "3.10" and python_version < "3.13" and platform_system == "Windows" +dotenv==0.9.9 ; python_version >= "3.10" and python_version < "3.13" +exceptiongroup==1.3.1 ; python_version == "3.10" +fastapi==0.121.3 ; python_version >= "3.10" and python_version < "3.13" +h11==0.16.0 ; python_version >= "3.10" and python_version < "3.13" +idna==3.11 ; python_version >= "3.10" and python_version < "3.13" +jinja2==3.1.6 ; python_version >= "3.10" and python_version < "3.13" +markupsafe==3.0.3 ; python_version >= "3.10" and python_version < "3.13" +pydantic-core==2.41.5 ; python_version >= "3.10" and python_version < "3.13" +pydantic==2.12.5 ; python_version >= "3.10" and python_version < "3.13" +python-box==7.3.2 ; python_version >= "3.10" and python_version < "3.13" +python-dotenv==1.2.1 ; python_version >= "3.10" and python_version < "3.13" +starlette==0.50.0 ; python_version >= "3.10" and python_version < "3.13" +typing-extensions==4.15.0 ; python_version >= "3.10" and python_version < "3.13" +typing-inspection==0.4.2 ; python_version >= "3.10" and python_version < "3.13" +uvicorn==0.40.0 ; python_version >= "3.10" and python_version < "3.13" diff --git a/src/api/__init__.py b/src/sample/api/__init__.py similarity index 100% rename from src/api/__init__.py rename to src/sample/api/__init__.py diff --git a/src/api/fast_api.py b/src/sample/api/fast_api.py similarity index 100% rename from src/api/fast_api.py rename to src/sample/api/fast_api.py diff --git a/src/db/__init__.py b/src/sample/db/__init__.py similarity index 100% rename from src/db/__init__.py rename to src/sample/db/__init__.py diff --git a/src/db/connection.py b/src/sample/db/connection.py similarity index 100% rename from src/db/connection.py rename to src/sample/db/connection.py diff --git a/src/features/__init__.py b/src/sample/utils/__init__.py similarity index 100% rename from src/features/__init__.py rename to src/sample/utils/__init__.py diff --git a/src/utils/_version.py b/src/sample/utils/_version.py similarity index 100% rename from src/utils/_version.py rename to src/sample/utils/_version.py diff --git a/src/utils/constants.py b/src/sample/utils/constants.py similarity index 100% rename from src/utils/constants.py rename to src/sample/utils/constants.py diff --git a/src/utils/debug.py b/src/sample/utils/debug.py similarity index 100% rename from src/utils/debug.py rename to src/sample/utils/debug.py diff --git a/src/utils/helper.py b/src/sample/utils/helper.py similarity index 100% rename from src/utils/helper.py rename to src/sample/utils/helper.py diff --git a/src/utils/lint.py b/src/sample/utils/lint.py similarity index 100% rename from src/utils/lint.py rename to src/sample/utils/lint.py diff --git a/src/utils/load_messages.py b/src/sample/utils/load_messages.py similarity index 100% rename from src/utils/load_messages.py rename to src/sample/utils/load_messages.py diff --git a/src/utils/templates.py b/src/sample/utils/templates.py similarity index 100% rename from src/utils/templates.py rename to src/sample/utils/templates.py diff --git a/src/utils/__init__.py b/src/utils/__init__.py deleted file mode 100644 index e69de29..0000000 From b01c506d75f256608291f972f85dca1ab69e69b7 Mon Sep 17 00:00:00 2001 From: Heisenberg208 Date: Fri, 20 Feb 2026 20:28:46 +0530 Subject: [PATCH 2/4] [SAM-260011]: feat: refactor imports and enhance configuration management --- .vscode/settings.json | 10 +++++++++- pyproject.toml | 9 ++------- src/__init__.py | 2 +- src/sample/__init__.py | 2 +- src/sample/__main__.py | 4 ++-- src/sample/api/__init__.py | 2 +- src/sample/api/fast_api.py | 16 +++++++++++++--- src/sample/cli.py | 2 +- src/sample/db/connection.py | 3 +-- src/sample/utils/config.py | 15 +++++++++++++++ src/sample/utils/constants.py | 24 ++++++++++++++---------- src/sample/utils/load_messages.py | 4 ++-- 12 files changed, 62 insertions(+), 31 deletions(-) create mode 100644 src/sample/utils/config.py diff --git a/.vscode/settings.json b/.vscode/settings.json index 9e26dfe..61f1747 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -1 +1,9 @@ -{} \ No newline at end of file +{ + "python-envs.pythonProjects": [ + { + "path": "", + "envManager": "ms-python.python:poetry", + "packageManager": "ms-python.python:poetry" + } + ] +} diff --git a/pyproject.toml b/pyproject.toml index aa2658c..294009c 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -28,19 +28,14 @@ mongo = ["pymongo"] [tool.poetry] packages = [ { include = "sample", from = "src" }, - { include = "features", from = "src" }, - { include = "utils", from = "src" }, - { include = "api", from = "src" }, - { include = "db", from = "src" }, - { include = "templates", from = "." }, { include = "assets", from = "." }, ] - +include = [{ path = "templates/**/*", format = ["sdist", "wheel"] }] exclude = ["src/**/__pycache__", "tests", "docs", "*.log"] [project.scripts] sample = "sample.cli:cli" -lint = "utils.lint:main" +lint = "sample.utils.lint:main" [tool.poetry.group.dev.dependencies] diff --git a/src/__init__.py b/src/__init__.py index 0ed1344..bdf1df2 100644 --- a/src/__init__.py +++ b/src/__init__.py @@ -1,3 +1,3 @@ -from utils._version import get_version +from sample.utils._version import get_version __version__ = get_version() diff --git a/src/sample/__init__.py b/src/sample/__init__.py index 143c9a4..20ec7fe 100644 --- a/src/sample/__init__.py +++ b/src/sample/__init__.py @@ -1,3 +1,3 @@ -from utils._version import get_version +from sample.utils._version import get_version __version__ = get_version() diff --git a/src/sample/__main__.py b/src/sample/__main__.py index 942bc01..54c202c 100644 --- a/src/sample/__main__.py +++ b/src/sample/__main__.py @@ -2,12 +2,12 @@ from contextlib import asynccontextmanager from pathlib import Path -from db.connection import connect_db from fastapi import FastAPI, Request from fastapi.responses import HTMLResponse from fastapi.staticfiles import StaticFiles from fastapi.templating import Jinja2Templates -from utils.constants import PORT +from sample.db.connection import connect_db +from sample.utils.constants import PORT from . import __version__ diff --git a/src/sample/api/__init__.py b/src/sample/api/__init__.py index 0ed1344..bdf1df2 100644 --- a/src/sample/api/__init__.py +++ b/src/sample/api/__init__.py @@ -1,3 +1,3 @@ -from utils._version import get_version +from sample.utils._version import get_version __version__ = get_version() diff --git a/src/sample/api/fast_api.py b/src/sample/api/fast_api.py index cd464d4..b55c398 100644 --- a/src/sample/api/fast_api.py +++ b/src/sample/api/fast_api.py @@ -1,9 +1,12 @@ +import logging + from fastapi import APIRouter, FastAPI, HTTPException, Request from fastapi.responses import HTMLResponse, JSONResponse from pydantic import BaseModel +from sample.db.connection import connect_db +from sample.utils.constants import API_PREFIX, GREETING +from sample.utils.helper import normalize_name from starlette.exceptions import HTTPException as StarletteHTTPException -from utils.constants import API_PREFIX, GREETING -from utils.helper import normalize_name from . import __version__ @@ -139,8 +142,15 @@ async def chrome_devtools_probe(): def start(): import uvicorn + try: + _ = connect_db() + except Exception: + logging.warning( + "โš ๏ธ Could not connect to the database. Please check database configuration." + ) + print(f"๐Ÿงต {__version__}\n") - uvicorn.run("api.fast_api:app", host="127.0.0.1", port=5000, reload=True) + uvicorn.run("sample.api.fast_api:app", host="127.0.0.1", port=5000, reload=True) if __name__ == "__main__": diff --git a/src/sample/cli.py b/src/sample/cli.py index cfdffda..5219ceb 100644 --- a/src/sample/cli.py +++ b/src/sample/cli.py @@ -24,6 +24,6 @@ def dev(): @cli.command() def api(): """Run the Sample FastAPI backend.""" - from api.fast_api import start + from sample.api.fast_api import start start() diff --git a/src/sample/db/connection.py b/src/sample/db/connection.py index c80a860..a96e670 100644 --- a/src/sample/db/connection.py +++ b/src/sample/db/connection.py @@ -1,7 +1,7 @@ import io from datetime import datetime -from utils.constants import MONGO_CONFIG +from sample.utils.constants import MONGO_CONFIG _mongo_client = None _db = None @@ -28,7 +28,6 @@ def connect_db(): try: uri = MONGO_CONFIG["MONGODB_URI"] name = MONGO_CONFIG["DATABASE_NAME"] - print("Mongo URI =", repr(uri)) _mongo_client = MongoClient(uri, serverSelectionTimeoutMS=3000) # Force an actual connection attempt diff --git a/src/sample/utils/config.py b/src/sample/utils/config.py new file mode 100644 index 0000000..9735d77 --- /dev/null +++ b/src/sample/utils/config.py @@ -0,0 +1,15 @@ +import os + +from dotenv import load_dotenv + + +def load_env(): + env = os.getenv("ENV", "development") + + file_map = { + "production": ".env.production", + "development": ".env.development", + } + + load_dotenv(file_map.get(env, ".env.development"), override=True) + return env diff --git a/src/sample/utils/constants.py b/src/sample/utils/constants.py index ace9477..15b54c1 100644 --- a/src/sample/utils/constants.py +++ b/src/sample/utils/constants.py @@ -2,9 +2,9 @@ import os from pathlib import Path -from dotenv import load_dotenv +from sample.utils.config import load_env -load_dotenv() +load_env() # These should be in environment variables or .env file. DEFAULT_PORT = 8005 DEFAULT_API_PREFIX = "/api/v1" @@ -30,15 +30,19 @@ def safe_get(env_key: str, default) -> str: return value -MONGODB_URI = safe_get("MONGODB_URI", DEFAULT_MONGODB_URI) -DATABASE_NAME = safe_get("DATABASE_NAME", DEFAULT_DATABASE_NAME) API_PREFIX = safe_get("API_PREFIX", DEFAULT_API_PREFIX) PORT = int(safe_get("PORT", DEFAULT_PORT)) -print("MongoDB URI:", MONGODB_URI) -print("Database Name:", DATABASE_NAME) -MONGO_CONFIG = { - "MONGODB_URI": MONGODB_URI, - "DATABASE_NAME": DATABASE_NAME, -} +def get_mongo_config(): + return { + "MONGODB_URI": safe_get("MONGODB_URI", DEFAULT_MONGODB_URI), + "DATABASE_NAME": safe_get("DATABASE_NAME", DEFAULT_DATABASE_NAME), + } + + +MONGO_CONFIG = get_mongo_config() +# === Environment Selection === +ENVIRONMENT = safe_get("ENVIRONMENT", "development").lower() +logging.info(f"Environment: {ENVIRONMENT}", extra={"color": "yellow"}) +logging.info(f"Project root: {PROJECT_ROOT}", extra={"color": "yellow"}) diff --git a/src/sample/utils/load_messages.py b/src/sample/utils/load_messages.py index a35c171..08c3b5a 100644 --- a/src/sample/utils/load_messages.py +++ b/src/sample/utils/load_messages.py @@ -1,9 +1,9 @@ # utils/get_message.py -from box import Box import importlib +from box import Box -# auto-collect static and text blocks from utils.static +# auto-collect static and text blocks from sample.utils.static _static_module = importlib.import_module("utils.templates") _TEMPLATE_MAP = {} for name, val in vars(_static_module).items(): From 08ce905e91bf625ceb480707ed8a1d48665d0b7f Mon Sep 17 00:00:00 2001 From: Heisenberg208 Date: Fri, 20 Feb 2026 22:35:15 +0530 Subject: [PATCH 3/4] [SAM-260011]: feat: restructure FastAPI application and implement new routing --- src/sample/__main__.py | 66 +--------------- src/sample/api/fast_api.py | 157 ------------------------------------- src/sample/api/main.py | 52 ++++++++++++ src/sample/api/routes.py | 87 ++++++++++++++++++++ src/sample/api/web_page.py | 26 ++++++ src/sample/cli.py | 2 +- 6 files changed, 169 insertions(+), 221 deletions(-) delete mode 100644 src/sample/api/fast_api.py create mode 100644 src/sample/api/main.py create mode 100644 src/sample/api/routes.py create mode 100644 src/sample/api/web_page.py diff --git a/src/sample/__main__.py b/src/sample/__main__.py index 54c202c..ab1001d 100644 --- a/src/sample/__main__.py +++ b/src/sample/__main__.py @@ -1,72 +1,12 @@ -import logging -from contextlib import asynccontextmanager -from pathlib import Path - -from fastapi import FastAPI, Request -from fastapi.responses import HTMLResponse -from fastapi.staticfiles import StaticFiles -from fastapi.templating import Jinja2Templates -from sample.db.connection import connect_db from sample.utils.constants import PORT -from . import __version__ - - -@asynccontextmanager -async def lifespan(app: FastAPI): - # Startup logic - print("๐Ÿท๏ธ Sample version:", __version__) - logging.info("Starting FastAPI server...") - try: - db = connect_db() - print(f"Using database: {db.name}") - except Exception as e: - logging.error(f"โš ๏ธ Database connection failed: {e}") - print("App is ready.") - - yield # <-- control passes to request handling - - # Shutdown logic - logging.info("Shutting down FastAPI server...") - # If you want to close DB connections, do it here - - -# Create FastAPI app with lifespan handler -app = FastAPI(lifespan=lifespan) - -# Mount assets and pages -app.mount("/static", StaticFiles(directory="assets"), name="static") - -# Point Jinja2 to your templates directory -templates = Jinja2Templates( - directory=str(Path(__file__).resolve().parents[2] / "templates") -) - - -@app.get("/", response_class=HTMLResponse) -async def index(request: Request): - """Serve the main index.html at root.""" - return templates.TemplateResponse("index.html", {"request": request}) - - -@app.get("/faq", response_class=HTMLResponse) -async def faq(request: Request): - return templates.TemplateResponse("faq.html", {"request": request}) - - -templates = Jinja2Templates(directory="templates") - - -@app.get("/{full_path:path}", response_class=HTMLResponse) -async def catch_all(request: Request, full_path: str): - return templates.TemplateResponse("404.html", {"request": request}, status_code=404) - def main(): """Entry point for CLI dev command.""" - import uvicorn + from sample.api.main import start - uvicorn.run("sample.__main__:app", host="127.0.0.1", port=PORT, reload=True) + print(f"๐Ÿš€ Starting Sample app on port {PORT}...\n") + start() if __name__ == "__main__": diff --git a/src/sample/api/fast_api.py b/src/sample/api/fast_api.py deleted file mode 100644 index b55c398..0000000 --- a/src/sample/api/fast_api.py +++ /dev/null @@ -1,157 +0,0 @@ -import logging - -from fastapi import APIRouter, FastAPI, HTTPException, Request -from fastapi.responses import HTMLResponse, JSONResponse -from pydantic import BaseModel -from sample.db.connection import connect_db -from sample.utils.constants import API_PREFIX, GREETING -from sample.utils.helper import normalize_name -from starlette.exceptions import HTTPException as StarletteHTTPException - -from . import __version__ - -app = FastAPI( - title="sample API", - description="API endpoints for Sample with rate limiting", - version=__version__, - redoc_url="/redoc", - swagger_ui_parameters={ - "docExpansion": "none", # Collapse all endpoints by default - "defaultModelsExpandDepth": -1, # Hide schemas section - "displayRequestDuration": True, # Show request duration - "layout": "BaseLayout", # Clean layout - "syntaxHighlight": {"theme": "obsidian"}, # Dark theme - }, -) - -api_v1 = APIRouter( - prefix=API_PREFIX, - tags=["V1"], -) - - -class GreetRequest(BaseModel): - name: str - - -class GreetResponse(BaseModel): - message: str - - -@app.get("/version", tags=["Version"]) -def version(): - return {"version": app.version} - - -@app.get("/", response_class=HTMLResponse, tags=["Home"]) -async def read_root(request: Request): - return """ - - - ๐ŸŽ‰ Sample Api ๐ŸŽ‰ - - - -

๐ŸŽˆ This is sample API Tool ๐ŸŽˆ

-

Explore the API Documentation

- - - """ - - -@app.get("/health", tags=["Help"]) -def health_check(): - return {"status": "ok"} - - -@api_v1.get("/help", tags=["Help"]) -def get_help(): - return JSONResponse( - status_code=200, - content={ - "message": "Welcome to the Sample BoilerPlate API! Visit /docs for API documentation." - }, - ) - - -@api_v1.post("/greet", response_model=GreetResponse) -def greet_user(payload: GreetRequest): - clean_name = normalize_name(payload.name) - - if not clean_name: - raise HTTPException(status_code=400, detail="Invalid name provided") - - return {"message": f"{GREETING}, {clean_name} ๐Ÿ‘‹"} - - -@app.exception_handler(StarletteHTTPException) -async def http_exception_handler(request: Request, exc: StarletteHTTPException): - if exc.status_code == 404: - endpoint = request.url.path - - return JSONResponse( - status_code=404, - content={ - "error": f"Endpoint '{endpoint}' does not exist, use /docs to see available endpoints.", - "status": 404, - }, - ) - - # fallback for other HTTP errors - return JSONResponse( - status_code=exc.status_code, - content={"error": exc.detail}, - ) - - -# suppress chrome log -@app.get("/.well-known/appspecific/com.chrome.devtools.json") -async def chrome_devtools_probe(): - return JSONResponse({}) - - -app.include_router(api_v1) - - -def start(): - import uvicorn - - try: - _ = connect_db() - except Exception: - logging.warning( - "โš ๏ธ Could not connect to the database. Please check database configuration." - ) - - print(f"๐Ÿงต {__version__}\n") - uvicorn.run("sample.api.fast_api:app", host="127.0.0.1", port=5000, reload=True) - - -if __name__ == "__main__": - start() diff --git a/src/sample/api/main.py b/src/sample/api/main.py new file mode 100644 index 0000000..af95b4f --- /dev/null +++ b/src/sample/api/main.py @@ -0,0 +1,52 @@ +import logging +from contextlib import asynccontextmanager +from pathlib import Path + +from fastapi import FastAPI +from fastapi.staticfiles import StaticFiles +from fastapi.templating import Jinja2Templates +from sample import __version__ +from sample.api.routes import api_router +from sample.api.web_page import web_router +from sample.db.connection import connect_db +from sample.utils.constants import PORT + + +@asynccontextmanager +async def lifespan(app: FastAPI): + print("๐Ÿท๏ธ Sample version:", __version__) + logging.info("Starting FastAPI server...") + try: + db = connect_db() + print(f"Using database: {db.name}") + except Exception as e: + logging.error(f"โš ๏ธ Database connection failed: {e}") + + yield + + logging.info("Shutting down FastAPI server...") + + +app = FastAPI( + title="Sample API", + version=__version__, + lifespan=lifespan, +) + +# Static +app.mount("/static", StaticFiles(directory="assets"), name="static") + +# Templates +templates = Jinja2Templates( + directory=str(Path(__file__).resolve().parent / "templates") +) + + +app.include_router(web_router) +app.include_router(api_router) + + +def start(): + import uvicorn + + uvicorn.run("sample.api.main:app", host="127.0.0.1", port=PORT, reload=True) diff --git a/src/sample/api/routes.py b/src/sample/api/routes.py new file mode 100644 index 0000000..70443f5 --- /dev/null +++ b/src/sample/api/routes.py @@ -0,0 +1,87 @@ +from fastapi import APIRouter, HTTPException, Request +from pydantic import BaseModel +from sample.utils.constants import API_PREFIX, GREETING +from sample.utils.helper import normalize_name +from starlette.responses import HTMLResponse, JSONResponse + +api_router = APIRouter(prefix=API_PREFIX, tags=["V1"]) + + +class GreetRequest(BaseModel): + name: str + + +class GreetResponse(BaseModel): + message: str + + +@api_router.get("/health") +def health_check(): + return {"status": "ok"} + + +@api_router.post("/greet", response_model=GreetResponse) +def greet_user(payload: GreetRequest): + clean_name = normalize_name(payload.name) + + if not clean_name: + raise HTTPException(status_code=400, detail="Invalid name provided") + + return {"message": f"{GREETING}, {clean_name} ๐Ÿ‘‹"} + + +@api_router.get("/version", tags=["Version"]) +def version(): + return {"version": api_router.version} + + +@api_router.get("/index", response_class=HTMLResponse, tags=["Home"]) +async def read_root(request: Request): + return """ + + + ๐ŸŽ‰ Sample Api ๐ŸŽ‰ + + + +

๐ŸŽˆ This is sample API Tool ๐ŸŽˆ

+

Explore the API Documentation

+ + + """ + + +@api_router.get("/help", tags=["Help"]) +def get_help(): + return JSONResponse( + status_code=200, + content={ + "message": "Welcome to the Sample BoilerPlate API! Visit /docs for API documentation." + }, + ) diff --git a/src/sample/api/web_page.py b/src/sample/api/web_page.py new file mode 100644 index 0000000..824f016 --- /dev/null +++ b/src/sample/api/web_page.py @@ -0,0 +1,26 @@ +from pathlib import Path + +from fastapi import APIRouter, Request +from fastapi.responses import HTMLResponse +from fastapi.templating import Jinja2Templates + +web_router = APIRouter() + +templates = Jinja2Templates( + directory=str(Path(__file__).resolve().parents[3] / "templates") +) + + +@web_router.get("/", response_class=HTMLResponse) +async def index(request: Request): + return templates.TemplateResponse("index.html", {"request": request}) + + +@web_router.get("/faq", response_class=HTMLResponse) +async def faq(request: Request): + return templates.TemplateResponse("faq.html", {"request": request}) + + +@web_router.get("/{full_path:path}", response_class=HTMLResponse) +async def catch_all(request: Request, full_path: str): + return templates.TemplateResponse("404.html", {"request": request}, status_code=404) diff --git a/src/sample/cli.py b/src/sample/cli.py index 5219ceb..6d20c61 100644 --- a/src/sample/cli.py +++ b/src/sample/cli.py @@ -24,6 +24,6 @@ def dev(): @cli.command() def api(): """Run the Sample FastAPI backend.""" - from sample.api.fast_api import start + from sample.api.main import start start() From 67124eb40a5c73346539c8946f9e08b9bfb03f5f Mon Sep 17 00:00:00 2001 From: Heisenberg208 Date: Fri, 20 Feb 2026 23:03:13 +0530 Subject: [PATCH 4/4] [SAM-260011]: feat: update FastAPI routing and CLI command structure --- src/sample/api/main.py | 8 +++----- src/sample/api/routes.py | 27 ++++++++++++++++++++++----- src/sample/cli.py | 2 +- 3 files changed, 26 insertions(+), 11 deletions(-) diff --git a/src/sample/api/main.py b/src/sample/api/main.py index af95b4f..e1bcef2 100644 --- a/src/sample/api/main.py +++ b/src/sample/api/main.py @@ -5,8 +5,8 @@ from fastapi import FastAPI from fastapi.staticfiles import StaticFiles from fastapi.templating import Jinja2Templates -from sample import __version__ -from sample.api.routes import api_router + +from sample.api.routes import greet_router from sample.api.web_page import web_router from sample.db.connection import connect_db from sample.utils.constants import PORT @@ -14,7 +14,6 @@ @asynccontextmanager async def lifespan(app: FastAPI): - print("๐Ÿท๏ธ Sample version:", __version__) logging.info("Starting FastAPI server...") try: db = connect_db() @@ -29,7 +28,6 @@ async def lifespan(app: FastAPI): app = FastAPI( title="Sample API", - version=__version__, lifespan=lifespan, ) @@ -43,7 +41,7 @@ async def lifespan(app: FastAPI): app.include_router(web_router) -app.include_router(api_router) +app.include_router(greet_router) def start(): diff --git a/src/sample/api/routes.py b/src/sample/api/routes.py index 70443f5..2d43ff0 100644 --- a/src/sample/api/routes.py +++ b/src/sample/api/routes.py @@ -1,10 +1,17 @@ -from fastapi import APIRouter, HTTPException, Request +from fastapi import APIRouter, FastAPI, HTTPException, Request from pydantic import BaseModel -from sample.utils.constants import API_PREFIX, GREETING +from sample.utils.constants import API_PREFIX, GREETING, PORT from sample.utils.helper import normalize_name from starlette.responses import HTMLResponse, JSONResponse +from sample import __version__ -api_router = APIRouter(prefix=API_PREFIX, tags=["V1"]) +app = FastAPI( + title="Sample API", + version=__version__, +) + +api_router = APIRouter() +greet_router = APIRouter(prefix=API_PREFIX, tags=["V1"]) class GreetRequest(BaseModel): @@ -20,7 +27,7 @@ def health_check(): return {"status": "ok"} -@api_router.post("/greet", response_model=GreetResponse) +@greet_router.post("/greet", response_model=GreetResponse) def greet_user(payload: GreetRequest): clean_name = normalize_name(payload.name) @@ -35,7 +42,7 @@ def version(): return {"version": api_router.version} -@api_router.get("/index", response_class=HTMLResponse, tags=["Home"]) +@api_router.get("/", response_class=HTMLResponse, tags=["Home"]) async def read_root(request: Request): return """ @@ -85,3 +92,13 @@ def get_help(): "message": "Welcome to the Sample BoilerPlate API! Visit /docs for API documentation." }, ) + + +app.include_router(api_router) +app.include_router(greet_router) + + +def start(): + import uvicorn + + uvicorn.run("sample.api.routes:app", host="127.0.0.1", port=PORT, reload=True) diff --git a/src/sample/cli.py b/src/sample/cli.py index 6d20c61..c0a0746 100644 --- a/src/sample/cli.py +++ b/src/sample/cli.py @@ -24,6 +24,6 @@ def dev(): @cli.command() def api(): """Run the Sample FastAPI backend.""" - from sample.api.main import start + from sample.api.routes import start start()