Files
home-automation/app/api/routes/homeassistant.py
T

50 lines
2.0 KiB
Python

import json
import logging
from fastapi import APIRouter, Depends, Request, status
from fastapi.responses import PlainTextResponse, Response
from pydantic import ValidationError
from sqlalchemy.orm import Session
from app.dependencies import get_db
from app.schemas.homeassistant import HomeAssistantPublishEnvelope
from app.services.homeassistant_inbound import (
UnsupportedHomeAssistantMessage,
handle_homeassistant_message,
)
router = APIRouter(tags=["homeassistant"])
logger = logging.getLogger(__name__)
BAD_REQUEST_MESSAGE = "bad request"
INTERNAL_SERVER_ERROR_MESSAGE = "internal server error"
@router.post("/homeassistant/publish")
async def publish_from_homeassistant(
request: Request, db: Session = Depends(get_db)
) -> Response:
try:
raw_payload = await request.body()
data = json.loads(raw_payload)
envelope = HomeAssistantPublishEnvelope.model_validate(data)
handle_homeassistant_message(db, envelope)
except json.JSONDecodeError as exc:
logger.warning("Rejected Home Assistant publish request due to invalid JSON: %s", exc)
return PlainTextResponse(BAD_REQUEST_MESSAGE, status_code=status.HTTP_400_BAD_REQUEST)
except ValidationError as exc:
logger.warning(
"Rejected Home Assistant publish request due to validation failure: %s", exc
)
return PlainTextResponse(BAD_REQUEST_MESSAGE, status_code=status.HTTP_400_BAD_REQUEST)
except UnsupportedHomeAssistantMessage as exc:
logger.warning("Home Assistant publish target/action unsupported: %s", exc)
return PlainTextResponse(
INTERNAL_SERVER_ERROR_MESSAGE,
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
)
except ValueError as exc:
logger.warning("Rejected Home Assistant publish request due to invalid content: %s", exc)
return PlainTextResponse(BAD_REQUEST_MESSAGE, status_code=status.HTTP_400_BAD_REQUEST)
return Response(status_code=status.HTTP_200_OK)