- Implemented test scripts for vTiger account retrieval, contact data, and modules. - Created a detailed test suite for the ticket module, covering database schema validation, ticket number generation, prepaid card constraints, and service logic. - Added tests for vTiger field inspection and various queries related to accounts and sales orders. - Introduced SQL migration scripts for the ALSO Cloud Billing foundation, including import jobs, lines, and mapping tables with necessary constraints and indices. - Enhanced workflow columns in the import lines table to support matching and validation timestamps.
149 lines
4.1 KiB
Python
149 lines
4.1 KiB
Python
from datetime import date, datetime
|
|
from decimal import Decimal
|
|
from typing import Any, Dict, List, Literal, Optional
|
|
|
|
from pydantic import BaseModel, Field
|
|
|
|
|
|
ALSO_SOURCE_TYPES = Literal["api", "xml", "json_export", "xml_export", "csv"]
|
|
ALSO_QUEUE_STATUSES = Literal[
|
|
"new",
|
|
"matching_products",
|
|
"matching_customers",
|
|
"ready_for_approval",
|
|
"approved",
|
|
"invoiced",
|
|
"error",
|
|
]
|
|
|
|
|
|
class AlsoImportJobCreate(BaseModel):
|
|
source_type: ALSO_SOURCE_TYPES
|
|
source_label: Optional[str] = None
|
|
file_name: Optional[str] = None
|
|
import_version: Optional[str] = None
|
|
raw_payload: Dict[str, Any] = Field(default_factory=dict)
|
|
|
|
|
|
class AlsoImportLineInput(BaseModel):
|
|
line_no: Optional[int] = None
|
|
source_line_ref: Optional[str] = None
|
|
|
|
company: Optional[str] = None
|
|
customer_id: Optional[str] = None
|
|
account_id: Optional[str] = None
|
|
vat: Optional[str] = None
|
|
also_company_id: Optional[str] = None
|
|
|
|
material_number: Optional[str] = None
|
|
product_name: Optional[str] = None
|
|
vendor: Optional[str] = None
|
|
|
|
cost_amount: Optional[Decimal] = None
|
|
sales_price: Optional[Decimal] = None
|
|
unit_price: Optional[Decimal] = None
|
|
total_price: Optional[Decimal] = None
|
|
currency: Optional[str] = None
|
|
|
|
billing_start: Optional[date] = None
|
|
charge_interval: Optional[str] = None
|
|
billing_interval: Optional[str] = None
|
|
|
|
billable_parameters: Optional[Decimal] = None
|
|
queue_status: ALSO_QUEUE_STATUSES = "new"
|
|
raw_line: Dict[str, Any] = Field(default_factory=dict)
|
|
|
|
|
|
class AlsoImportLinesRequest(BaseModel):
|
|
lines: List[AlsoImportLineInput] = Field(default_factory=list)
|
|
|
|
|
|
class AlsoQueueProcessRequest(BaseModel):
|
|
import_job_id: Optional[int] = Field(default=None, gt=0)
|
|
line_ids: List[int] = Field(default_factory=list)
|
|
limit: int = Field(default=500, ge=1, le=5000)
|
|
|
|
|
|
class AlsoQueueApproveRequest(BaseModel):
|
|
import_job_id: Optional[int] = Field(default=None, gt=0)
|
|
line_ids: List[int] = Field(default_factory=list)
|
|
|
|
|
|
class AlsoQueueProcessResult(BaseModel):
|
|
processed: int
|
|
updated: int
|
|
ready_for_approval: int
|
|
errored: int
|
|
|
|
|
|
class AlsoApproveResult(BaseModel):
|
|
approved_lines: int
|
|
created_drafts: int
|
|
draft_ids: List[int] = Field(default_factory=list)
|
|
|
|
|
|
class AlsoCompanyMappingUpsert(BaseModel):
|
|
also_company_id: str = Field(min_length=1)
|
|
also_customer_id: Optional[str] = None
|
|
customer_id: int = Field(gt=0)
|
|
match_confidence: Optional[Decimal] = None
|
|
notes: Optional[str] = None
|
|
|
|
|
|
class AlsoProductMappingUpsert(BaseModel):
|
|
material_number: str = Field(min_length=1)
|
|
vendor: str = Field(min_length=1)
|
|
hub_product_id: int = Field(gt=0)
|
|
product_name_snapshot: Optional[str] = None
|
|
|
|
|
|
class AlsoImportJobResponse(BaseModel):
|
|
id: int
|
|
source_type: str
|
|
source_label: Optional[str] = None
|
|
status: str
|
|
file_name: Optional[str] = None
|
|
import_version: Optional[str] = None
|
|
imported_by_user_id: Optional[int] = None
|
|
imported_at: datetime
|
|
line_count: int = 0
|
|
|
|
|
|
class AlsoQueueLineResponse(BaseModel):
|
|
id: int
|
|
import_job_id: int
|
|
queue_status: str
|
|
company: Optional[str] = None
|
|
customer_id: Optional[str] = None
|
|
material_number: Optional[str] = None
|
|
product_name: Optional[str] = None
|
|
vendor: Optional[str] = None
|
|
total_price: Optional[Decimal] = None
|
|
currency: Optional[str] = None
|
|
matched_customer_id: Optional[int] = None
|
|
matched_product_id: Optional[int] = None
|
|
order_draft_id: Optional[int] = None
|
|
validation_errors_json: List[Dict[str, Any]] = Field(default_factory=list)
|
|
|
|
|
|
class AlsoDashboardSummaryResponse(BaseModel):
|
|
monthly_revenue: Decimal
|
|
monthly_cost: Decimal
|
|
monthly_margin: Decimal
|
|
unmatched_products: int
|
|
unmatched_customers: int
|
|
pending_approvals: int
|
|
invoiced_customers: int
|
|
|
|
|
|
class AlsoDifferenceItem(BaseModel):
|
|
customer_id: Optional[int] = None
|
|
customer_name: Optional[str] = None
|
|
material_number: Optional[str] = None
|
|
product_name: Optional[str] = None
|
|
vendor: Optional[str] = None
|
|
previous_month_qty: Decimal
|
|
current_month_qty: Decimal
|
|
change_percent: Optional[Decimal] = None
|
|
warning: bool = False
|