feat(platform): close AI expense value loop

Add tenant-safe value, telemetry, connector, commercial, and production-readiness foundations.
This commit is contained in:
caoxiaozhu
2026-07-17 14:14:08 +08:00
parent 242d68c36f
commit 787bc3a481
507 changed files with 82072 additions and 6344 deletions

View File

@@ -2,6 +2,7 @@ from __future__ import annotations
from io import BytesIO
import pytest
from openpyxl import Workbook
from sqlalchemy import create_engine, select
from sqlalchemy.orm import Session, sessionmaker
@@ -39,7 +40,7 @@ def build_workbook_bytes(rows: list[list[object]]) -> bytes:
def test_import_employees_rejects_invalid_row_without_writing() -> None:
with build_session() as db:
service = EmployeeService(db)
service = EmployeeService(db, tenant_id="default")
first = service.list_employees()[0]
content = build_workbook_bytes(
@@ -80,7 +81,7 @@ def test_import_employees_rejects_invalid_row_without_writing() -> None:
def test_import_employees_updates_existing_employee() -> None:
with build_session() as db:
service = EmployeeService(db)
service = EmployeeService(db, tenant_id="default")
employee = service.list_employees()[0]
new_name = f"{employee.name}-导入"
@@ -121,11 +122,14 @@ def test_import_employees_updates_existing_employee() -> None:
assert updated.bankAccountName == "导入户名"
assert updated.bankName == "招商银行上海分行"
assert updated.bankAccountNo == "622588000000000002"
persisted = db.execute(select(Employee).where(Employee.id == employee.id)).scalar_one()
assert persisted.tenant_id == "default"
assert persisted.manager_id is None
def test_import_employees_creates_new_employee() -> None:
with build_session() as db:
service = EmployeeService(db)
service = EmployeeService(db, tenant_id="default")
service.list_employees()
content = build_workbook_bytes(
@@ -158,11 +162,50 @@ def test_import_employees_creates_new_employee() -> None:
assert result.success is True
assert result.summary.created == 1
imported = db.execute(
select(Employee).where(Employee.employee_no == "E90001")
).scalar_one()
imported = db.execute(select(Employee).where(Employee.employee_no == "E90001")).scalar_one()
assert imported.name == "导入新员工"
assert imported.email == "import.new.user@xfinance.com"
assert imported.bank_account_name == "导入新员工"
assert imported.bank_name
assert imported.bank_account_no
def test_import_employees_rolls_back_when_membership_sync_fails(monkeypatch) -> None:
with build_session() as db:
service = EmployeeService(db, tenant_id="default")
service.list_employees()
content = build_workbook_bytes(
[
[
"E-ROLLBACK-001",
"导入回滚员工",
"import.rollback@xfinance.com",
"",
"",
"",
"",
"上海",
"业务专员",
"P3",
"FINANCE-DEPT",
"",
"",
"CC-ROLLBACK",
"",
"",
"",
"在职",
"user",
]
]
)
monkeypatch.setattr(
service,
"_ensure_tenant_memberships",
lambda: (_ for _ in ()).throw(RuntimeError("membership sync failed")),
)
with pytest.raises(RuntimeError, match="membership sync failed"):
service.import_employees(content)
assert db.scalar(select(Employee).where(Employee.employee_no == "E-ROLLBACK-001")) is None