task.py 9.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264
  1. """
  2. Pydantic schemas for Task API.
  3. Defines request and response models for task operations.
  4. """
  5. from datetime import datetime
  6. from typing import Optional, Any, List
  7. from pydantic import BaseModel, Field
  8. class TaskCreate(BaseModel):
  9. """Schema for creating a new task."""
  10. project_id: str = Field(..., min_length=1, description="Project ID this task belongs to")
  11. name: str = Field(..., min_length=1, description="Task name")
  12. data: dict = Field(..., description="Task data (JSON object)")
  13. assigned_to: Optional[str] = Field(None, description="User ID assigned to this task")
  14. class Config:
  15. json_schema_extra = {
  16. "example": {
  17. "project_id": "proj_123abc",
  18. "name": "Annotate Image Batch 1",
  19. "data": {
  20. "image_url": "https://example.com/image1.jpg",
  21. "metadata": {"batch": 1}
  22. },
  23. "assigned_to": "user_001"
  24. }
  25. }
  26. class TaskUpdate(BaseModel):
  27. """Schema for updating an existing task."""
  28. name: Optional[str] = Field(None, min_length=1, description="Task name")
  29. data: Optional[dict] = Field(None, description="Task data (JSON object)")
  30. status: Optional[str] = Field(None, description="Task status (pending, in_progress, completed)")
  31. assigned_to: Optional[str] = Field(None, description="User ID assigned to this task")
  32. class Config:
  33. json_schema_extra = {
  34. "example": {
  35. "name": "Updated Task Name",
  36. "status": "in_progress",
  37. "assigned_to": "user_002"
  38. }
  39. }
  40. class TaskResponse(BaseModel):
  41. """Schema for task response."""
  42. id: str = Field(..., description="Task unique identifier")
  43. project_id: str = Field(..., description="Project ID this task belongs to")
  44. name: str = Field(..., description="Task name")
  45. data: dict = Field(..., description="Task data (JSON object)")
  46. status: str = Field(..., description="Task status (pending, in_progress, completed)")
  47. assigned_to: Optional[str] = Field(None, description="User ID assigned to this task")
  48. created_at: datetime = Field(..., description="Task creation timestamp")
  49. progress: float = Field(default=0.0, description="Task completion progress (0.0 to 1.0)")
  50. class Config:
  51. json_schema_extra = {
  52. "example": {
  53. "id": "task_456def",
  54. "project_id": "proj_123abc",
  55. "name": "Annotate Image Batch 1",
  56. "data": {
  57. "image_url": "https://example.com/image1.jpg",
  58. "metadata": {"batch": 1}
  59. },
  60. "status": "in_progress",
  61. "assigned_to": "user_001",
  62. "created_at": "2024-01-12T11:00:00",
  63. "progress": 0.5
  64. }
  65. }
  66. class TaskAssignRequest(BaseModel):
  67. """Schema for assigning a task to a user."""
  68. user_id: str = Field(..., min_length=1, description="User ID to assign the task to")
  69. class Config:
  70. json_schema_extra = {
  71. "example": {
  72. "user_id": "user_001"
  73. }
  74. }
  75. class BatchAssignRequest(BaseModel):
  76. """Schema for batch assigning tasks to users."""
  77. task_ids: List[str] = Field(..., min_length=1, description="List of task IDs to assign")
  78. user_ids: List[str] = Field(..., min_length=1, description="List of user IDs to assign to")
  79. mode: str = Field(
  80. default="round_robin",
  81. description="Assignment mode: 'round_robin' (轮询分配) or 'equal' (平均分配)"
  82. )
  83. class Config:
  84. json_schema_extra = {
  85. "example": {
  86. "task_ids": ["task_001", "task_002", "task_003"],
  87. "user_ids": ["user_001", "user_002"],
  88. "mode": "equal"
  89. }
  90. }
  91. class TaskAssignmentResponse(BaseModel):
  92. """Schema for task assignment response."""
  93. task_id: str = Field(..., description="Task ID")
  94. assigned_to: str = Field(..., description="User ID assigned to")
  95. assigned_by: str = Field(..., description="User ID who made the assignment")
  96. assigned_at: datetime = Field(..., description="Assignment timestamp")
  97. class BatchAssignResponse(BaseModel):
  98. """Schema for batch assignment response."""
  99. success_count: int = Field(..., description="Number of successfully assigned tasks")
  100. failed_count: int = Field(..., description="Number of failed assignments")
  101. assignments: List[TaskAssignmentResponse] = Field(
  102. default_factory=list,
  103. description="List of successful assignments"
  104. )
  105. errors: List[dict] = Field(
  106. default_factory=list,
  107. description="List of errors for failed assignments"
  108. )
  109. class MyTasksResponse(BaseModel):
  110. """Schema for current user's tasks response."""
  111. tasks: List[TaskResponse] = Field(..., description="List of tasks assigned to current user")
  112. total: int = Field(..., description="Total number of tasks")
  113. completed: int = Field(..., description="Number of completed tasks")
  114. in_progress: int = Field(..., description="Number of in-progress tasks")
  115. pending: int = Field(..., description="Number of pending tasks")
  116. # ============== 任务分发相关Schema ==============
  117. class AnnotatorWorkload(BaseModel):
  118. """标注人员工作负载"""
  119. user_id: str = Field(..., description="用户ID")
  120. username: str = Field(..., description="用户名")
  121. current_tasks: int = Field(..., description="当前任务数")
  122. completed_today: int = Field(default=0, description="今日完成数")
  123. class Config:
  124. json_schema_extra = {
  125. "example": {
  126. "user_id": "user_001",
  127. "username": "annotator1",
  128. "current_tasks": 15,
  129. "completed_today": 5
  130. }
  131. }
  132. class AnnotatorAssignment(BaseModel):
  133. """单个标注人员的分配信息"""
  134. user_id: str = Field(..., description="用户ID")
  135. username: str = Field(..., description="用户名")
  136. task_count: int = Field(..., description="将分配的任务数")
  137. percentage: float = Field(..., description="分配百分比")
  138. current_workload: int = Field(default=0, description="当前已有任务数")
  139. class Config:
  140. json_schema_extra = {
  141. "example": {
  142. "user_id": "user_001",
  143. "username": "annotator1",
  144. "task_count": 50,
  145. "percentage": 50.0,
  146. "current_workload": 10
  147. }
  148. }
  149. class AssignmentPreviewRequest(BaseModel):
  150. """分配预览请求"""
  151. user_ids: List[str] = Field(..., min_length=1, description="标注人员ID列表")
  152. class Config:
  153. json_schema_extra = {
  154. "example": {
  155. "user_ids": ["user_001", "user_002"]
  156. }
  157. }
  158. class AssignmentPreviewResponse(BaseModel):
  159. """分配预览响应"""
  160. project_id: str = Field(..., description="项目ID")
  161. total_tasks: int = Field(..., description="总任务数")
  162. unassigned_tasks: int = Field(..., description="未分配任务数")
  163. assignments: List[AnnotatorAssignment] = Field(..., description="分配预览列表")
  164. class Config:
  165. json_schema_extra = {
  166. "example": {
  167. "project_id": "proj_123abc",
  168. "total_tasks": 100,
  169. "unassigned_tasks": 100,
  170. "assignments": [
  171. {
  172. "user_id": "user_001",
  173. "username": "annotator1",
  174. "task_count": 50,
  175. "percentage": 50.0,
  176. "current_workload": 10
  177. }
  178. ]
  179. }
  180. }
  181. class DispatchRequest(BaseModel):
  182. """一键分发请求"""
  183. user_ids: List[str] = Field(..., min_length=1, description="标注人员ID列表")
  184. mode: str = Field(default="equal", description="分配模式:equal(平均分配)或 round_robin(轮询分配)")
  185. class Config:
  186. json_schema_extra = {
  187. "example": {
  188. "user_ids": ["user_001", "user_002"],
  189. "mode": "equal"
  190. }
  191. }
  192. class DispatchResponse(BaseModel):
  193. """分发结果响应"""
  194. project_id: str = Field(..., description="项目ID")
  195. success: bool = Field(..., description="是否成功")
  196. total_assigned: int = Field(..., description="分配的任务总数")
  197. assignments: List[AnnotatorAssignment] = Field(..., description="分配结果列表")
  198. project_status: str = Field(..., description="更新后的项目状态")
  199. class Config:
  200. json_schema_extra = {
  201. "example": {
  202. "project_id": "proj_123abc",
  203. "success": True,
  204. "total_assigned": 100,
  205. "assignments": [
  206. {
  207. "user_id": "user_001",
  208. "username": "annotator1",
  209. "task_count": 50,
  210. "percentage": 50.0,
  211. "current_workload": 60
  212. }
  213. ],
  214. "project_status": "in_progress"
  215. }
  216. }