Added custom extra fields to backend
No integration tests yet, TBD
This commit is contained in:
98
spoolman/api/v1/field.py
Normal file
98
spoolman/api/v1/field.py
Normal file
@@ -0,0 +1,98 @@
|
||||
"""Vendor related endpoints."""
|
||||
|
||||
import logging
|
||||
from typing import Annotated, Union
|
||||
|
||||
from fastapi import APIRouter, Depends, Path
|
||||
from fastapi.responses import JSONResponse
|
||||
from sqlalchemy.ext.asyncio import AsyncSession
|
||||
|
||||
from spoolman.api.v1.models import Message
|
||||
from spoolman.database.database import get_db_session
|
||||
from spoolman.exceptions import ItemNotFoundError
|
||||
from spoolman.extra_fields import (
|
||||
EntityType,
|
||||
ExtraField,
|
||||
ExtraFieldParameters,
|
||||
add_or_update_extra_field,
|
||||
delete_extra_field,
|
||||
get_extra_fields,
|
||||
)
|
||||
|
||||
router = APIRouter(
|
||||
prefix="/field",
|
||||
tags=["field"],
|
||||
)
|
||||
|
||||
# ruff: noqa: D103,B008
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
@router.get(
|
||||
"/{entity_type}",
|
||||
name="Get extra fields",
|
||||
description="Get all extra fields for a specific entity type.",
|
||||
response_model_exclude_none=True,
|
||||
)
|
||||
async def get(
|
||||
db: Annotated[AsyncSession, Depends(get_db_session)],
|
||||
entity_type: Annotated[EntityType, Path(description="Entity type this field is for")],
|
||||
) -> list[ExtraField]:
|
||||
return await get_extra_fields(db, entity_type)
|
||||
|
||||
|
||||
@router.post(
|
||||
"/{entity_type}/{key}",
|
||||
name="Add or update extra field",
|
||||
description=(
|
||||
"Add or update an extra field for a specific entity type. "
|
||||
"Returns the full list of extra fields for the entity type."
|
||||
),
|
||||
response_model_exclude_none=True,
|
||||
response_model=list[ExtraField],
|
||||
responses={400: {"model": Message}},
|
||||
)
|
||||
async def update(
|
||||
db: Annotated[AsyncSession, Depends(get_db_session)],
|
||||
entity_type: Annotated[EntityType, Path(description="Entity type this field is for")],
|
||||
key: Annotated[str, Path(min_length=1, max_length=64, regex="^[a-z0-9_]+$")],
|
||||
body: ExtraFieldParameters,
|
||||
) -> Union[list[ExtraField], JSONResponse]:
|
||||
body_with_key = ExtraField.parse_obj(body.copy(update={"key": key}))
|
||||
|
||||
try:
|
||||
await add_or_update_extra_field(db, entity_type, body_with_key)
|
||||
except ValueError as e:
|
||||
return JSONResponse(status_code=400, content=Message(message=str(e)).dict())
|
||||
|
||||
return await get_extra_fields(db, entity_type)
|
||||
|
||||
|
||||
@router.delete(
|
||||
"/{entity_type}/{key}",
|
||||
name="Delete extra field",
|
||||
description=(
|
||||
"Delete an extra field for a specific entity type. "
|
||||
"Returns the full list of extra fields for the entity type."
|
||||
),
|
||||
response_model_exclude_none=True,
|
||||
response_model=list[ExtraField],
|
||||
responses={404: {"model": Message}},
|
||||
)
|
||||
async def delete(
|
||||
db: Annotated[AsyncSession, Depends(get_db_session)],
|
||||
entity_type: Annotated[EntityType, Path(description="Entity type this field is for")],
|
||||
key: Annotated[str, Path(min_length=1, max_length=64, regex="^[a-z0-9_]+$")],
|
||||
) -> Union[list[ExtraField], JSONResponse]:
|
||||
try:
|
||||
await delete_extra_field(db, entity_type, key)
|
||||
except ItemNotFoundError:
|
||||
return JSONResponse(
|
||||
status_code=404,
|
||||
content=Message(
|
||||
message=f"Extra field with key {key} does not exist for entity type {entity_type.name}",
|
||||
).dict(),
|
||||
)
|
||||
|
||||
return await get_extra_fields(db, entity_type)
|
||||
Reference in New Issue
Block a user