""" 业务逻辑层 —— 使用内存假数据实现 Todo 的 CRUD 操作。 所有数据存储在内存字典中,服务重启后数据会丢失。 """ from __future__ import annotations from typing import Optional from pydantic import BaseModel, Field # ────────────────────────────────────────────── # Pydantic 模型(请求 / 响应) # ────────────────────────────────────────────── class TodoCreate(BaseModel): """创建待办事项的请求体。""" title: str = Field(..., min_length=1, max_length=200, description="待办事项标题") completed: bool = Field(False, description="是否已完成") class TodoUpdate(BaseModel): """更新待办事项的请求体(部分更新)。""" title: Optional[str] = Field(None, min_length=1, max_length=200, description="待办事项标题") completed: Optional[bool] = Field(None, description="是否已完成") class TodoResponse(BaseModel): """待办事项的响应体。""" id: int = Field(..., description="待办事项 ID") title: str = Field(..., description="待办事项标题") completed: bool = Field(..., description="是否已完成") model_config = {"from_attributes": True} # ────────────────────────────────────────────── # 内存假数据存储 # ────────────────────────────────────────────── class TodoService: """待办事项服务 —— 使用内存字典存储数据。""" def __init__(self) -> None: self._todos: dict[int, dict] = {} self._next_id: int = 1 self._init_mock_data() def _init_mock_data(self) -> None: """初始化一批假数据,方便演示。""" mock_todos = [ {"title": "学习 FastAPI", "completed": False}, {"title": "编写单元测试", "completed": False}, {"title": "阅读 Python 文档", "completed": True}, {"title": "完成项目报告", "completed": False}, {"title": "锻炼身体 30 分钟", "completed": True}, ] for item in mock_todos: self.create_todo(TodoCreate(**item)) def list_todos(self) -> list[TodoResponse]: """返回所有待办事项。""" return [TodoResponse(**todo) for todo in self._todos.values()] def get_todo(self, todo_id: int) -> Optional[TodoResponse]: """根据 ID 获取单个待办事项,不存在则返回 None。""" todo = self._todos.get(todo_id) if todo is None: return None return TodoResponse(**todo) def create_todo(self, todo_in: TodoCreate) -> TodoResponse: """创建新的待办事项并返回。""" todo_id = self._next_id self._next_id += 1 todo = { "id": todo_id, "title": todo_in.title, "completed": todo_in.completed, } self._todos[todo_id] = todo return TodoResponse(**todo) def update_todo(self, todo_id: int, todo_in: TodoUpdate) -> Optional[TodoResponse]: """部分更新指定待办事项,不存在则返回 None。""" todo = self._todos.get(todo_id) if todo is None: return None update_data = todo_in.model_dump(exclude_unset=True) todo.update(update_data) return TodoResponse(**todo) def delete_todo(self, todo_id: int) -> bool: """删除指定待办事项,成功返回 True,不存在返回 False。""" if todo_id not in self._todos: return False del self._todos[todo_id] return True