Skip to content

Commit

Permalink
create all machinery to create a dataformat
Browse files Browse the repository at this point in the history
  • Loading branch information
Volubyl committed Jan 24, 2023
1 parent 7e3de42 commit f3aab9b
Show file tree
Hide file tree
Showing 11 changed files with 111 additions and 7 deletions.
29 changes: 27 additions & 2 deletions server/api/dataformats/routes.py
Original file line number Diff line number Diff line change
@@ -1,9 +1,12 @@
import logging
from typing import List

from fastapi import APIRouter, Depends
from fastapi import APIRouter, Depends, HTTPException

from server.application.dataformats.queries import GetAllDataFormat
from server.api.dataformats.schemas import DataFormatCreate
from server.application.dataformats.commands import CreateDataFormat
from server.application.dataformats.exceptions import CannotCreateDataFormat
from server.application.dataformats.queries import GetAllDataFormat, GetDataFormatById
from server.application.dataformats.views import DataFormatView
from server.config.di import resolve
from server.seedwork.application.messages import MessageBus
Expand All @@ -24,3 +27,25 @@ async def list_dataformat() -> List[DataFormatView]:

bus = resolve(MessageBus)
return await bus.execute(GetAllDataFormat())


@router.post(
"/",
dependencies=[Depends(IsAuthenticated())],
response_model=DataFormatView,
status_code=201,
)
async def create_dataformat(data: DataFormatCreate) -> DataFormatView:
bus = resolve(MessageBus)
print(data)

command = CreateDataFormat(value=data.value)

try:
id = await bus.execute(command)
query = GetDataFormatById(id=id)
return await bus.execute(query)

except CannotCreateDataFormat as exc:
logger.exception(exc)
raise HTTPException(403, detail="Permission denied")
7 changes: 7 additions & 0 deletions server/api/dataformats/schemas.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
from pydantic import BaseModel

from server.application.dataformats.validation import CreateDataFormatValidationMixin


class DataFormatCreate(CreateDataFormatValidationMixin, BaseModel):
value: str
6 changes: 6 additions & 0 deletions server/application/dataformats/commands.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
from server.application.dataformats.validation import CreateDataFormatValidationMixin
from server.seedwork.application.commands import Command


class CreateDataFormat(CreateDataFormatValidationMixin, Command[int]):
value: str
2 changes: 2 additions & 0 deletions server/application/dataformats/exceptions.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
class CannotCreateDataFormat(Exception):
pass
20 changes: 18 additions & 2 deletions server/application/dataformats/handlers.py
Original file line number Diff line number Diff line change
@@ -1,12 +1,28 @@
from typing import List
from typing import List, Optional

from server.application.dataformats.queries import GetAllDataFormat
from server.application.dataformats.commands import CreateDataFormat
from server.application.dataformats.queries import GetAllDataFormat, GetDataFormatById
from server.application.dataformats.views import DataFormatView
from server.config.di import resolve
from server.domain.dataformats.entities import DataFormat
from server.domain.dataformats.repositories import DataFormatRepository


async def get_all_dataformats(query: GetAllDataFormat) -> List[DataFormatView]:
repository = resolve(DataFormatRepository)
dataformats = await repository.get_all()
return [DataFormatView(**dataformat.dict()) for dataformat in dataformats]


async def create_dataformat(command: CreateDataFormat) -> Optional[int]:
repository = resolve(DataFormatRepository)
return await repository.insert(DataFormat(name=command.value))


async def get_by_id(query: GetDataFormatById) -> Optional[DataFormatView]:
repository = resolve(DataFormatRepository)
dataformat = await repository.get_by_id(id=query.id)

if dataformat is not None:
return DataFormatView(**dataformat.dict())
return None
4 changes: 4 additions & 0 deletions server/application/dataformats/queries.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,3 +7,7 @@

class GetAllDataFormat(Query[List[DataFormatView]]):
pass


class GetDataFormatById(Query[DataFormatView]):
id: int
9 changes: 9 additions & 0 deletions server/application/dataformats/validation.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
from pydantic import BaseModel, validator


class CreateDataFormatValidationMixin(BaseModel):
@validator("value", check_fields=False)
def check_value_at_least_one(cls, value: str) -> str:
if not value:
raise ValueError("dataformat must have a value")
return value
3 changes: 3 additions & 0 deletions server/domain/dataformats/repositories.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,3 +14,6 @@ async def get_all(self, ids: List[Optional[int]] = None) -> List[DataFormat]:

async def get_by_name(self, name: str) -> Optional[DataFormat]:
raise NotImplementedError # pragma: no cover

async def get_by_id(self, id: int) -> Optional[DataFormat]:
raise NotImplementedError # pragma: no cover
15 changes: 12 additions & 3 deletions server/infrastructure/dataformats/module.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,16 @@
from server.application.dataformats.handlers import get_all_dataformats
from server.application.dataformats.queries import GetAllDataFormat
from server.application.dataformats.commands import CreateDataFormat
from server.application.dataformats.handlers import (
create_dataformat,
get_all_dataformats,
get_by_id,
)
from server.application.dataformats.queries import GetAllDataFormat, GetDataFormatById
from server.seedwork.application.modules import Module


class DataFormatModule(Module):
query_handlers = {GetAllDataFormat: get_all_dataformats}
query_handlers = {
GetAllDataFormat: get_all_dataformats,
GetDataFormatById: get_by_id,
}
command_handlers = {CreateDataFormat: create_dataformat}
9 changes: 9 additions & 0 deletions server/infrastructure/dataformats/repositories.py
Original file line number Diff line number Diff line change
Expand Up @@ -43,3 +43,12 @@ async def get_by_name(self, name: str) -> Optional[DataFormat]:
if instance is None:
return None
return make_entity(instance)

async def get_by_id(self, id: int) -> Optional[DataFormat]:
async with self._db.session() as session:
stmt = select(DataFormatModel).where(DataFormatModel.id == id)
result = await session.execute(stmt)
instance = result.unique().scalar_one_or_none()
if instance is None:
return None
return make_entity(instance)
14 changes: 14 additions & 0 deletions tests/api/test_dataformats.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,3 +30,17 @@ async def test_dataformat_list_not_authenticated(
) -> None:
response = await client.get("/dataformats/")
assert response.status_code == 401


@pytest.mark.asyncio
async def test_create_dataformat(
client: httpx.AsyncClient, temp_user: TestPasswordUser
) -> None:

payload = {"value": "toto"}

response = await client.post("/dataformats/", json=payload, auth=temp_user.auth)
assert response.status_code == 201

data = response.json()
assert data["name"] == "toto"

0 comments on commit f3aab9b

Please sign in to comment.