Skip to content

Commit

Permalink
Add admin stats endpoint
Browse files Browse the repository at this point in the history
- Update default user to be a superuser in data.json
- Fix CSS in NoSectionSelected
  • Loading branch information
m-danya committed Jan 27, 2025
1 parent 7163fcf commit ab39a63
Show file tree
Hide file tree
Showing 8 changed files with 77 additions and 24 deletions.
8 changes: 1 addition & 7 deletions check.sh
Original file line number Diff line number Diff line change
@@ -1,10 +1,4 @@
(
ruff format --check || (
ruff format && \
echo "Reformatted. You should run this script again." && \
false
)
) && \
ruff format && \
ruff check --fix && \
mypy planty && \
pytest -x && \
Expand Down
6 changes: 3 additions & 3 deletions frontend/components/no-section-selected.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,11 @@ import Image from "next/image";

function NoSectionSelected() {
return (
<div className="flex justify-center w-full h-full items-center opacity-[.12]">
<div className="w-20 ">
<div className="flex justify-center items-center w-full h-[calc(100vh-128px)] opacity-[.12]">
<div className="w-20">
<Image
src="/sign_black_stroke.png"
className="w-full h-auto "
className="w-full h-auto"
width={200}
height={200}
alt="Planty logo"
Expand Down
7 changes: 7 additions & 0 deletions planty/application/auth.py
Original file line number Diff line number Diff line change
Expand Up @@ -75,9 +75,16 @@ async def get_user_manager(


current_user_dependency = fastapi_users_obj.current_user()
admin_user_dependency = fastapi_users_obj.current_user(superuser=True)


def current_user(
user: UserModel = Depends(current_user_dependency),
) -> User:
return user.to_entity()


def admin_user(
user: UserModel = Depends(admin_user_dependency),
) -> User:
return user.to_entity()
27 changes: 15 additions & 12 deletions planty/application/router.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,43 +3,39 @@

from fastapi import APIRouter, Depends, status


from planty.application.auth import admin_user, current_user
from planty.application.schemas import (
RequestAttachmentUpload,
ArchivedTasksResponse,
AttachmentUploadInfo,
RequestAttachmentUpload,
SectionCreateRequest,
SectionCreateResponse,
SectionMoveRequest,
SectionResponse,
SectionsListResponse,
SectionUpdateRequest,
SectionUpdateResponse,
ShuffleSectionRequest,
StatsResponse,
TaskCreateRequest,
TaskCreateResponse,
TaskSearchResponse,
TaskMoveRequest,
TaskRemoveRequest,
ArchivedTasksResponse,
TaskToggleArchivedRequest,
TasksByDatesResponse,
TaskSearchResponse,
TaskToggleArchivedRequest,
TaskToggleCompletedRequest,
TaskUpdateRequest,
TaskUpdateResponse,
SectionsListResponse,
)
from planty.application.services.stats import StatsService
from planty.application.services.tasks import (
SectionService,
TaskService,
)
from planty.application.uow import SqlAlchemyUnitOfWork


from planty.domain.task import User


from planty.application.auth import current_user


router = APIRouter(tags=["User tasks"], prefix="/api")


Expand Down Expand Up @@ -252,3 +248,10 @@ async def shuffle_section(
section = await section_service.shuffle(user.id, request)
await uow.commit()
return section


@router.get("/stats")
async def get_stats(admin_user: User = Depends(admin_user)) -> StatsResponse:
async with SqlAlchemyUnitOfWork() as uow:
stats_service = StatsService(uow=uow)
return await stats_service.get_stats()
12 changes: 12 additions & 0 deletions planty/application/schemas.py
Original file line number Diff line number Diff line change
Expand Up @@ -196,3 +196,15 @@ class UserCreate(fastapi_users_schemas.BaseUserCreate):

class UserUpdate(fastapi_users_schemas.BaseUserUpdate):
pass


class UserStats(Schema):
id: UUID
email: str
tasks_count: int
sections_count: int
attachments_count: int
model_config = ConfigDict(extra="allow")


StatsResponse = list[UserStats]
10 changes: 10 additions & 0 deletions planty/application/services/stats.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
from planty.application.schemas import StatsResponse
from planty.application.uow import IUnitOfWork


class StatsService:
def __init__(self, uow: IUnitOfWork):
self.uow = uow

async def get_stats(self) -> StatsResponse:
return await self.uow.user_repo.get_all_users()
29 changes: 28 additions & 1 deletion planty/infrastructure/repositories.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,19 +3,21 @@
from uuid import UUID

from pydantic import NonNegativeInt
from sqlalchemy import asc, desc, select
from sqlalchemy import asc, desc, func, select
from sqlalchemy.ext.asyncio import AsyncSession
from sqlalchemy.orm import selectinload

from planty.application.exceptions import (
SectionNotFoundException,
TaskNotFoundException,
)
from planty.application.schemas import UserStats
from planty.domain.task import Attachment, Section, Task
from planty.infrastructure.models import (
AttachmentModel,
SectionModel,
TaskModel,
UserModel,
)
from planty.utils import get_today

Expand All @@ -24,6 +26,31 @@ class SQLAlchemyUserRepository:
def __init__(self, db_session: AsyncSession):
self._db_session = db_session

async def get_all_users(self) -> list[UserStats]:
result = await self._db_session.execute(
select(
UserModel,
func.count(TaskModel.id).label("tasks_count"),
func.count(SectionModel.id).label("sections_count"),
func.count(AttachmentModel.id).label("attachments_count"),
)
.outerjoin(TaskModel, UserModel.id == TaskModel.user_id) # type: ignore
.outerjoin(SectionModel, UserModel.id == SectionModel.user_id) # type: ignore
.outerjoin(AttachmentModel, TaskModel.attachments)
.group_by(UserModel) # type: ignore
.order_by(desc(UserModel.added_at))
)

users = []
for user_model, tasks_count, sections_count, attachments_count in result:
user = user_model.to_entity().model_dump()
user["tasks_count"] = tasks_count
user["sections_count"] = sections_count
user["attachments_count"] = attachments_count
users.append(UserStats.model_validate(user))

return users


class SQLAlchemyTaskRepository:
def __init__(self, db_session: AsyncSession):
Expand Down
2 changes: 1 addition & 1 deletion planty/resources/data.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
"added_at": "2024-03-28T04:11:17.677Z",
"hashed_password": "$argon2id$v=19$m=65536,t=3,p=4$k1eNeIjFZcxaEsMP1d931g$X32zZKlcoTzQHmFJl5Qo8XhDBQ4vtgQcOM0DFEinr+k",
"is_active": 1,
"is_superuser": 0,
"is_superuser": 1,
"is_verified": 0
},
{
Expand Down

0 comments on commit ab39a63

Please sign in to comment.