collabrix/backend/app/schemas.py
DGSoft a7ff948e7e Beta Release: Complete Kanban system with auto-save, route persistence, and UI improvements
- Added complete Kanban board functionality with drag-and-drop
- Implemented auto-save for Kanban card editing (no more edit button)
- Added route persistence to remember last visited page on reload
- Improved Kanban UI design with slimmer borders and compact layout
- Added checklist functionality for Kanban cards
- Enhanced file upload and direct messaging features
- Improved authentication and user management
- Added toast notifications system
- Various UI/UX improvements and bug fixes
2025-12-10 23:17:07 +01:00

391 lines
7.8 KiB
Python

from pydantic import BaseModel, EmailStr
from typing import Optional, List
from datetime import datetime
# User Schemas
class UserBase(BaseModel):
username: str
email: EmailStr
full_name: Optional[str] = None
profile_picture: Optional[str] = None
theme: str = "light"
class UserCreate(UserBase):
password: str
class UserUpdate(BaseModel):
email: Optional[EmailStr] = None
full_name: Optional[str] = None
password: Optional[str] = None
theme: Optional[str] = None
class UserLogin(BaseModel):
username: str
password: str
class UserResponse(UserBase):
id: int
is_active: bool
is_admin: bool = False
created_at: datetime
class Config:
from_attributes = True
class UserWithDepartments(UserResponse):
departments: List["DepartmentResponse"] = []
# Token Schemas
class Token(BaseModel):
access_token: str
token_type: str
class TokenData(BaseModel):
username: Optional[str] = None
# Department Schemas
class DepartmentBase(BaseModel):
name: str
description: Optional[str] = None
class DepartmentCreate(DepartmentBase):
pass
class DepartmentResponse(DepartmentBase):
id: int
snippets_enabled: bool
created_at: datetime
class Config:
from_attributes = True
# Channel Schemas
class ChannelBase(BaseModel):
name: str
description: Optional[str] = None
department_id: int
class ChannelCreate(ChannelBase):
pass
class ChannelResponse(ChannelBase):
id: int
created_at: datetime
class Config:
from_attributes = True
# Message Schemas
class MessageBase(BaseModel):
content: str
channel_id: int
snippet_id: Optional[int] = None
reply_to_id: Optional[int] = None
class MessageCreate(MessageBase):
pass
class MessageResponse(MessageBase):
id: int
sender_id: int
created_at: datetime
is_deleted: bool = False
sender_username: Optional[str] = None
sender_full_name: Optional[str] = None
sender_profile_picture: Optional[str] = None
attachments: List["FileAttachmentResponse"] = []
snippet: Optional["SnippetResponse"] = None
reply_to: Optional[dict] = None # Contains replied message info
class Config:
from_attributes = True
# Direct Message Schemas
class DirectMessageBase(BaseModel):
content: str
receiver_id: int
snippet_id: Optional[int] = None
reply_to_id: Optional[int] = None
class DirectMessageCreate(DirectMessageBase):
pass
class DirectMessageResponse(DirectMessageBase):
id: int
sender_id: int
created_at: datetime
is_read: bool
sender_username: Optional[str] = None
receiver_username: Optional[str] = None
sender_full_name: Optional[str] = None
sender_profile_picture: Optional[str] = None
snippet: Optional["SnippetResponse"] = None
reply_to: Optional[dict] = None # Contains replied message info
class Config:
from_attributes = True
# File Attachment Schemas
class FileAttachmentCreate(BaseModel):
permission: str = "read" # "read" or "write"
class FileAttachmentResponse(BaseModel):
id: int
filename: str
original_filename: str
mime_type: str
file_size: int
uploaded_at: datetime
message_id: int
upload_permission: Optional[str] = "read"
uploader_id: Optional[int] = None
is_editable: bool = False # Computed: whether current user can edit
class Config:
from_attributes = True
# Snippet Schemas
class SnippetBase(BaseModel):
title: str
language: str
content: str
tags: Optional[str] = None
visibility: str = "private" # private, department, organization
department_id: Optional[int] = None
class SnippetCreate(SnippetBase):
pass
class SnippetUpdate(BaseModel):
title: Optional[str] = None
language: Optional[str] = None
content: Optional[str] = None
tags: Optional[str] = None
visibility: Optional[str] = None
department_id: Optional[int] = None
class SnippetResponse(SnippetBase):
id: int
owner_id: int
owner_username: Optional[str] = None
created_at: datetime
updated_at: datetime
class Config:
from_attributes = True
class LanguageBase(BaseModel):
code: str
name: str
class LanguageCreate(LanguageBase):
pass
class LanguageResponse(LanguageBase):
id: int
is_default: bool
created_at: datetime
class Config:
from_attributes = True
class TranslationEntryResponse(BaseModel):
translation_id: int
language_id: int
language_code: str
language_name: str
value: str
class TranslationGroupResponse(BaseModel):
key: str
label: str
description: Optional[str] = None
entries: List[TranslationEntryResponse]
class TranslationUpdateRequest(BaseModel):
translation_id: int
value: str
# Kanban Schemas
class KanbanBoardBase(BaseModel):
name: str = "Kanban Board"
class KanbanBoardCreate(KanbanBoardBase):
channel_id: int
class KanbanBoardUpdate(BaseModel):
name: Optional[str] = None
class KanbanBoardResponse(KanbanBoardBase):
id: int
channel_id: int
created_at: datetime
updated_at: datetime
class Config:
from_attributes = True
class KanbanColumnBase(BaseModel):
name: str
position: int = 0
color: Optional[str] = None
class KanbanColumnCreate(KanbanColumnBase):
board_id: int
class KanbanColumnUpdate(BaseModel):
name: Optional[str] = None
position: Optional[int] = None
color: Optional[str] = None
class KanbanColumnResponse(KanbanColumnBase):
id: int
board_id: int
created_at: datetime
updated_at: datetime
class Config:
from_attributes = True
class KanbanCardBase(BaseModel):
title: str
description: Optional[str] = None
assignee_id: Optional[int] = None
position: int = 0
due_date: Optional[datetime] = None
priority: Optional[str] = "medium"
labels: Optional[str] = None
class KanbanCardCreate(KanbanCardBase):
column_id: int
class KanbanCardUpdate(BaseModel):
title: Optional[str] = None
description: Optional[str] = None
assignee_id: Optional[int] = None
position: Optional[int] = None
due_date: Optional[datetime] = None
priority: Optional[str] = None
labels: Optional[str] = None
class KanbanCardResponse(KanbanCardBase):
id: int
column_id: int
created_at: datetime
updated_at: datetime
class Config:
from_attributes = True
class KanbanBoardWithColumns(KanbanBoardResponse):
columns: List["KanbanColumnWithCards"] = []
class KanbanColumnWithCards(KanbanColumnResponse):
cards: List[KanbanCardResponse] = []
# Checklist Schemas
class KanbanChecklistBase(BaseModel):
title: str
position: int = 0
class KanbanChecklistCreate(KanbanChecklistBase):
card_id: int
class KanbanChecklistUpdate(BaseModel):
title: Optional[str] = None
position: Optional[int] = None
class KanbanChecklistResponse(KanbanChecklistBase):
id: int
card_id: int
created_at: datetime
updated_at: datetime
class Config:
from_attributes = True
class KanbanChecklistItemBase(BaseModel):
title: str
is_completed: bool = False
position: int = 0
class KanbanChecklistItemCreate(KanbanChecklistItemBase):
checklist_id: int
class KanbanChecklistItemUpdate(BaseModel):
title: Optional[str] = None
is_completed: Optional[bool] = None
position: Optional[int] = None
class KanbanChecklistItemResponse(KanbanChecklistItemBase):
id: int
checklist_id: int
created_at: datetime
updated_at: datetime
class Config:
from_attributes = True
class KanbanChecklistWithItems(KanbanChecklistResponse):
items: List[KanbanChecklistItemResponse] = []
class KanbanCardWithChecklists(KanbanCardResponse):
checklists: List[KanbanChecklistWithItems] = []