179 lines
8.3 KiB
Python
179 lines
8.3 KiB
Python
# services/production/app/schemas/quality_templates.py
|
|
"""
|
|
Quality Check Template Pydantic schemas for validation and serialization
|
|
"""
|
|
|
|
from pydantic import BaseModel, Field, validator
|
|
from typing import Optional, List, Dict, Any, Union
|
|
from uuid import UUID
|
|
from datetime import datetime
|
|
from enum import Enum
|
|
|
|
from ..models.production import ProcessStage
|
|
|
|
|
|
class QualityCheckType(str, Enum):
|
|
"""Quality check types"""
|
|
VISUAL = "visual"
|
|
MEASUREMENT = "measurement"
|
|
TEMPERATURE = "temperature"
|
|
WEIGHT = "weight"
|
|
BOOLEAN = "boolean"
|
|
TIMING = "timing"
|
|
|
|
|
|
class QualityCheckTemplateBase(BaseModel):
|
|
"""Base schema for quality check templates"""
|
|
name: str = Field(..., min_length=1, max_length=255, description="Template name")
|
|
template_code: Optional[str] = Field(None, max_length=100, description="Template code for reference")
|
|
check_type: QualityCheckType = Field(..., description="Type of quality check")
|
|
category: Optional[str] = Field(None, max_length=100, description="Check category (e.g., appearance, structure)")
|
|
description: Optional[str] = Field(None, description="Template description")
|
|
instructions: Optional[str] = Field(None, description="Check instructions for staff")
|
|
|
|
# Configuration
|
|
parameters: Optional[Dict[str, Any]] = Field(None, description="Dynamic check parameters")
|
|
thresholds: Optional[Dict[str, Any]] = Field(None, description="Pass/fail criteria")
|
|
scoring_criteria: Optional[Dict[str, Any]] = Field(None, description="Scoring methodology")
|
|
|
|
# Settings
|
|
is_active: bool = Field(True, description="Whether template is active")
|
|
is_required: bool = Field(False, description="Whether check is required")
|
|
is_critical: bool = Field(False, description="Whether failure blocks production")
|
|
weight: float = Field(1.0, ge=0.0, le=10.0, description="Weight in overall quality score")
|
|
|
|
# Measurement specifications
|
|
min_value: Optional[float] = Field(None, description="Minimum acceptable value")
|
|
max_value: Optional[float] = Field(None, description="Maximum acceptable value")
|
|
target_value: Optional[float] = Field(None, description="Target value")
|
|
unit: Optional[str] = Field(None, max_length=20, description="Unit of measurement")
|
|
tolerance_percentage: Optional[float] = Field(None, ge=0.0, le=100.0, description="Tolerance percentage")
|
|
|
|
# Process stage applicability
|
|
applicable_stages: Optional[List[ProcessStage]] = Field(None, description="Applicable process stages")
|
|
|
|
@validator('applicable_stages')
|
|
def validate_stages(cls, v):
|
|
if v is not None:
|
|
# Ensure all values are valid ProcessStage enums
|
|
for stage in v:
|
|
if stage not in ProcessStage:
|
|
raise ValueError(f"Invalid process stage: {stage}")
|
|
return v
|
|
|
|
@validator('min_value', 'max_value', 'target_value')
|
|
def validate_measurement_values(cls, v, values):
|
|
if v is not None and values.get('check_type') not in [QualityCheckType.MEASUREMENT, QualityCheckType.TEMPERATURE, QualityCheckType.WEIGHT]:
|
|
return None # Clear values for non-measurement types
|
|
return v
|
|
|
|
|
|
class QualityCheckTemplateCreate(QualityCheckTemplateBase):
|
|
"""Schema for creating quality check templates"""
|
|
created_by: UUID = Field(..., description="User ID who created the template")
|
|
|
|
|
|
class QualityCheckTemplateUpdate(BaseModel):
|
|
"""Schema for updating quality check templates"""
|
|
name: Optional[str] = Field(None, min_length=1, max_length=255)
|
|
template_code: Optional[str] = Field(None, max_length=100)
|
|
check_type: Optional[QualityCheckType] = None
|
|
category: Optional[str] = Field(None, max_length=100)
|
|
description: Optional[str] = None
|
|
instructions: Optional[str] = None
|
|
parameters: Optional[Dict[str, Any]] = None
|
|
thresholds: Optional[Dict[str, Any]] = None
|
|
scoring_criteria: Optional[Dict[str, Any]] = None
|
|
is_active: Optional[bool] = None
|
|
is_required: Optional[bool] = None
|
|
is_critical: Optional[bool] = None
|
|
weight: Optional[float] = Field(None, ge=0.0, le=10.0)
|
|
min_value: Optional[float] = None
|
|
max_value: Optional[float] = None
|
|
target_value: Optional[float] = None
|
|
unit: Optional[str] = Field(None, max_length=20)
|
|
tolerance_percentage: Optional[float] = Field(None, ge=0.0, le=100.0)
|
|
applicable_stages: Optional[List[ProcessStage]] = None
|
|
|
|
|
|
class QualityCheckTemplateResponse(QualityCheckTemplateBase):
|
|
"""Schema for quality check template responses"""
|
|
id: UUID
|
|
tenant_id: UUID
|
|
created_by: UUID
|
|
created_at: datetime
|
|
updated_at: datetime
|
|
|
|
class Config:
|
|
from_attributes = True
|
|
|
|
|
|
class QualityCheckTemplateList(BaseModel):
|
|
"""Schema for paginated quality check template lists"""
|
|
templates: List[QualityCheckTemplateResponse]
|
|
total: int
|
|
skip: int
|
|
limit: int
|
|
|
|
|
|
class QualityCheckCriterion(BaseModel):
|
|
"""Individual quality check criterion within a template"""
|
|
id: str = Field(..., description="Unique criterion identifier")
|
|
name: str = Field(..., description="Criterion name")
|
|
description: str = Field(..., description="Criterion description")
|
|
check_type: QualityCheckType = Field(..., description="Type of check")
|
|
required: bool = Field(True, description="Whether criterion is required")
|
|
weight: float = Field(1.0, ge=0.0, le=10.0, description="Weight in template score")
|
|
acceptable_criteria: str = Field(..., description="Description of acceptable criteria")
|
|
min_value: Optional[float] = None
|
|
max_value: Optional[float] = None
|
|
unit: Optional[str] = None
|
|
is_critical: bool = Field(False, description="Whether failure is critical")
|
|
|
|
|
|
class QualityCheckResult(BaseModel):
|
|
"""Result of a quality check criterion"""
|
|
criterion_id: str = Field(..., description="Criterion identifier")
|
|
value: Union[float, str, bool] = Field(..., description="Check result value")
|
|
score: float = Field(..., ge=0.0, le=10.0, description="Score for this criterion")
|
|
notes: Optional[str] = Field(None, description="Additional notes")
|
|
photos: Optional[List[str]] = Field(None, description="Photo URLs")
|
|
pass_check: bool = Field(..., description="Whether criterion passed")
|
|
timestamp: datetime = Field(..., description="When check was performed")
|
|
|
|
|
|
class QualityCheckExecutionRequest(BaseModel):
|
|
"""Schema for executing a quality check using a template"""
|
|
template_id: UUID = Field(..., description="Quality check template ID")
|
|
batch_id: UUID = Field(..., description="Production batch ID")
|
|
process_stage: ProcessStage = Field(..., description="Current process stage")
|
|
checker_id: Optional[str] = Field(None, description="Staff member performing check")
|
|
results: List[QualityCheckResult] = Field(..., description="Check results")
|
|
final_notes: Optional[str] = Field(None, description="Final notes")
|
|
photos: Optional[List[str]] = Field(None, description="Additional photo URLs")
|
|
|
|
|
|
class QualityCheckExecutionResponse(BaseModel):
|
|
"""Schema for quality check execution results"""
|
|
check_id: UUID = Field(..., description="Created quality check ID")
|
|
overall_score: float = Field(..., ge=0.0, le=10.0, description="Overall quality score")
|
|
overall_pass: bool = Field(..., description="Whether check passed overall")
|
|
critical_failures: List[str] = Field(..., description="List of critical failures")
|
|
corrective_actions: List[str] = Field(..., description="Recommended corrective actions")
|
|
timestamp: datetime = Field(..., description="When check was completed")
|
|
|
|
|
|
class ProcessStageQualityConfig(BaseModel):
|
|
"""Configuration for quality checks at a specific process stage"""
|
|
stage: ProcessStage = Field(..., description="Process stage")
|
|
template_ids: List[UUID] = Field(..., description="Required template IDs")
|
|
custom_parameters: Optional[Dict[str, Any]] = Field(None, description="Stage-specific parameters")
|
|
is_required: bool = Field(True, description="Whether stage requires quality checks")
|
|
blocking: bool = Field(True, description="Whether stage blocks on failed checks")
|
|
|
|
|
|
class RecipeQualityConfiguration(BaseModel):
|
|
"""Quality check configuration for a recipe"""
|
|
stages: Dict[str, ProcessStageQualityConfig] = Field(..., description="Stage configurations")
|
|
global_parameters: Optional[Dict[str, Any]] = Field(None, description="Global quality parameters")
|
|
default_templates: Optional[List[UUID]] = Field(None, description="Default template IDs") |