- Updated SealService to support tenant and company filtering with pagination and enhanced CRUD methods. - Refactored TrailerService to include tenant and company support, added filtering capabilities, and improved CRUD methods. - Introduced TenantCRUDRoutes for Trailer and Transporter routes to streamline API endpoint creation and management. - Enhanced TransporterService with tenant and company filtering, pagination, and improved CRUD operations. - Added Customs Broker module with DTOs, models, services, and routes for managing customs broker data. - Implemented CRUD operations for Customs Broker, including personnel and VU management. - Improved data validation and descriptions in DTOs for better API documentation.
162 lines
4.7 KiB
Python
162 lines
4.7 KiB
Python
"""
|
|
Capa de servicio para lógica de negocio de empresa
|
|
"""
|
|
|
|
import logging
|
|
from typing import List, Optional, Tuple, Dict, Any
|
|
|
|
from fastapi import HTTPException
|
|
from sqlalchemy.exc import IntegrityError
|
|
from sqlalchemy.orm import Session
|
|
|
|
from .dto import CompanyCreateDTO, CompanyResponseDTO, CompanyUpdateDTO
|
|
from .models import Company
|
|
|
|
logger = logging.getLogger(__name__)
|
|
|
|
|
|
class CompanyService:
|
|
"""Servicio para gestión de empresa"""
|
|
|
|
def __init__(self, db: Session):
|
|
self.db = db
|
|
|
|
# Métodos para TenantCRUDRoutes
|
|
@staticmethod
|
|
def get_all(
|
|
db: Session,
|
|
tenant_id: int,
|
|
company_id: int,
|
|
skip: int = 0,
|
|
limit: int = 50,
|
|
filters: Optional[Dict[str, Any]] = None,
|
|
) -> Tuple[List[Company], int]:
|
|
"""Get all companies for a tenant with pagination"""
|
|
query = db.query(Company).filter(Company.tenant_id == tenant_id)
|
|
|
|
# Apply filters if provided
|
|
if filters:
|
|
if filters.get("name"):
|
|
query = query.filter(
|
|
Company.name.ilike(f"%{filters['name']}%")
|
|
)
|
|
if filters.get("rfc"):
|
|
query = query.filter(
|
|
Company.rfc.ilike(f"%{filters['rfc']}%")
|
|
)
|
|
|
|
total = query.count()
|
|
companies = query.offset(skip).limit(limit).all()
|
|
|
|
return companies, total
|
|
|
|
@staticmethod
|
|
def get_by_id(
|
|
db: Session, company_id: int, tenant_id: int, company_id_unused: int
|
|
) -> Optional[Company]:
|
|
"""Get company by ID"""
|
|
return (
|
|
db.query(Company)
|
|
.filter(
|
|
Company.id == company_id,
|
|
Company.tenant_id == tenant_id,
|
|
)
|
|
.first()
|
|
)
|
|
|
|
@staticmethod
|
|
def create(
|
|
db: Session,
|
|
company_data: CompanyCreateDTO,
|
|
tenant_id: int,
|
|
company_id: int,
|
|
) -> Company:
|
|
"""Create a new company"""
|
|
try:
|
|
db_company = Company(
|
|
**company_data.model_dump(exclude_unset=True),
|
|
tenant_id=tenant_id
|
|
)
|
|
|
|
db.add(db_company)
|
|
db.commit()
|
|
db.refresh(db_company)
|
|
|
|
return db_company
|
|
|
|
except IntegrityError as e:
|
|
db.rollback()
|
|
logger.error(f"IntegrityError creating company: {str(e)}")
|
|
raise HTTPException(
|
|
status_code=400,
|
|
detail="Company already exists",
|
|
)
|
|
except Exception as e:
|
|
db.rollback()
|
|
logger.error(f"Error creating company: {str(e)}")
|
|
raise HTTPException(status_code=500, detail="Error creating company")
|
|
|
|
@staticmethod
|
|
def update(
|
|
db: Session,
|
|
company_id: int,
|
|
tenant_id: int,
|
|
company_id_unused: int,
|
|
company_data: CompanyUpdateDTO,
|
|
) -> Optional[Company]:
|
|
"""Update a company"""
|
|
company = CompanyService.get_by_id(db, company_id, tenant_id, company_id_unused)
|
|
if not company:
|
|
return None
|
|
|
|
# Update only provided fields
|
|
update_data = company_data.model_dump(exclude_unset=True)
|
|
for field, value in update_data.items():
|
|
setattr(company, field, value)
|
|
|
|
try:
|
|
db.commit()
|
|
db.refresh(company)
|
|
return company
|
|
except Exception as e:
|
|
db.rollback()
|
|
logger.error(f"Error updating company {company_id}: {str(e)}")
|
|
raise HTTPException(status_code=500, detail="Error updating company")
|
|
|
|
@staticmethod
|
|
def delete(
|
|
db: Session, company_id: int, tenant_id: int, company_id_unused: int
|
|
) -> bool:
|
|
"""Delete a company"""
|
|
company = CompanyService.get_by_id(db, company_id, tenant_id, company_id_unused)
|
|
if not company:
|
|
return False
|
|
|
|
try:
|
|
db.delete(company)
|
|
db.commit()
|
|
return True
|
|
except Exception as e:
|
|
db.rollback()
|
|
logger.error(f"Error deleting company {company_id}: {str(e)}")
|
|
raise HTTPException(status_code=500, detail="Error deleting company")
|
|
|
|
# Custom methods
|
|
def get_companies_by_tenant(self, tenant_id: int) -> List[Company]:
|
|
"""Get all companies for a tenant"""
|
|
return (
|
|
self.db.query(Company)
|
|
.filter(Company.tenant_id == tenant_id)
|
|
.order_by(Company.name)
|
|
.all()
|
|
)
|
|
|
|
def exists_company(self, tenant_id: int) -> bool:
|
|
"""Check if a company exists for a tenant"""
|
|
return (
|
|
self.db.query(Company)
|
|
.filter(Company.tenant_id == tenant_id)
|
|
.first()
|
|
is not None
|
|
)
|