from pydantic import BaseModel, Field from typing import List, Optional, Dict, Any from decimal import Decimal class VoucherExportRequest(BaseModel): """账票エクスポート要求""" start_year: int = Field(..., ge=2000, le=2099) start_month: int = Field(..., ge=1, le=12) end_year: Optional[int] = Field(default=None) end_month: Optional[int] = Field(default=None) employee_ids: List[int] = Field(..., min_items=1) voucher_type: str = Field(default="all", pattern="^(all|salary|bonus)$") format: str = Field(default="preview", pattern="^(preview|csv|pdf)$") class Config: json_schema_extra = { "example": { "start_year": 2026, "start_month": 1, "end_year": 2026, "end_month": 3, "employee_ids": [1, 2], "voucher_type": "all", "format": "preview" } } class VoucherDataSummary(BaseModel): """従業員ごとの个票摘要""" employee_id: int employee_code: str employee_name: str has_salary_data: bool has_bonus_data: bool salary_count: int = 0 bonus_count: int = 0 salary_months: List[str] = Field(default_factory=list) bonus_months: List[str] = Field(default_factory=list) class Config: from_attributes = True class SalaryVoucherData(BaseModel): """給与個票""" employee_id: int employee_code: str employee_name: str payroll_year: int payroll_month: int # 勤怠情報 working_days: Decimal = Decimal(0) working_hours: Decimal = Decimal(0) overtime_hours: Decimal = Decimal(0) holiday_hours: Decimal = Decimal(0) late_hours: Decimal = Decimal(0) absent_days: Decimal = Decimal(0) # 支給項目 base_salary: Decimal = Decimal(0) overtime_pay: Decimal = Decimal(0) holiday_pay: Decimal = Decimal(0) commute_allowance: Decimal = Decimal(0) other_allowance: Decimal = Decimal(0) total_payment: Decimal = Decimal(0) # 控除項目 health_insurance: Decimal = Decimal(0) care_insurance: Decimal = Decimal(0) pension_insurance: Decimal = Decimal(0) employment_insurance: Decimal = Decimal(0) income_tax: Decimal = Decimal(0) resident_tax: Decimal = Decimal(0) other_deduction: Decimal = Decimal(0) total_deduction: Decimal = Decimal(0) # 差引支給額 net_payment: Decimal = Decimal(0) # レガシー互換性用 gross_salary: Decimal = Decimal(0) total_deductions: Decimal = Decimal(0) net_salary: Decimal = Decimal(0) class Config: from_attributes = True class BonusVoucherData(BaseModel): """賞与個票""" employee_id: int employee_code: str employee_name: str bonus_year: int bonus_month: int bonus_type: str = "" # 夏季賞与/冬季賞与/決算賞与/その他 # 支給項目 base_bonus: Decimal = Decimal(0) # 基本賞与額 performance_bonus: Decimal = Decimal(0) # 業績賞与 other_bonus: Decimal = Decimal(0) # その他賞与 total_bonus: Decimal = Decimal(0) # 総支給額 # 控除項目 health_insurance: Decimal = Decimal(0) care_insurance: Decimal = Decimal(0) pension_insurance: Decimal = Decimal(0) employment_insurance: Decimal = Decimal(0) income_tax: Decimal = Decimal(0) # 賞与所得税 other_deduction: Decimal = Decimal(0) total_deduction: Decimal = Decimal(0) # 差引支給額 net_bonus: Decimal = Decimal(0) # レガシー互換性用 bonus_amount: Decimal = Decimal(0) tax_amount: Decimal = Decimal(0) class Config: from_attributes = True class VoucherExportResponse(BaseModel): """账票エクスポート応答""" status: str = Field(..., pattern="^(success|no_data|partial_data)$") has_data: bool message: str summary: List[VoucherDataSummary] = Field(default_factory=list) data: Dict[str, Any] = Field(default_factory=dict) class Config: json_schema_extra = { "example": { "status": "success", "has_data": True, "message": "✓ 成功查詢: 2位従業員有數據", "summary": [ { "employee_id": 1, "employee_code": "E001", "employee_name": "田中太郎", "has_salary_data": True, "has_bonus_data": False, "salary_count": 3, "bonus_count": 0, "salary_months": ["2026-01", "2026-02", "2026-03"], "bonus_months": [] } ], "data": { "salary": [], "bonus": [] } } }