合并yy并同步远程qyqy_develop
This commit is contained in:
@@ -25,7 +25,8 @@ from app.api.schemas.trading import (
|
||||
HoldingListResponse,
|
||||
PortfolioSummary,
|
||||
)
|
||||
from app.core.errors import FundQuoteUnavailableError
|
||||
from app.core.contracts import RequestContext
|
||||
from app.core.errors import FundQuoteUnavailableError, SuitabilityMismatchError
|
||||
from app.service.trade_service import TradeService, _FeeRule
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
@@ -206,3 +207,28 @@ async def test_quote_freshness_only_blocks_trade_path() -> None:
|
||||
assert snapshot.price == Decimal("4.5000")
|
||||
with pytest.raises(FundQuoteUnavailableError, match="行情已过期"):
|
||||
await service._fetch_quote(product, enforce_freshness=True) # type: ignore[arg-type]
|
||||
|
||||
|
||||
@pytest.mark.asyncio
|
||||
async def test_trade_suitability_uses_request_context_and_denies_mismatch() -> None:
|
||||
evaluator = SimpleNamespace(
|
||||
evaluate=AsyncMock(
|
||||
return_value=SimpleNamespace(allowed=False, reason_code="RISK_LEVEL_MISMATCH")
|
||||
)
|
||||
)
|
||||
service = TradeService(session=None, suitability_evaluator=evaluator) # type: ignore[arg-type]
|
||||
product = SimpleNamespace(
|
||||
product_code="510500",
|
||||
risk_level="R4",
|
||||
risk_disclosure_required=1,
|
||||
second_confirmation_required=0,
|
||||
)
|
||||
context = RequestContext(
|
||||
user_id="9001", trace_id="trade-test", roles=("customer",), customer_ids=("9001",)
|
||||
)
|
||||
|
||||
with pytest.raises(SuitabilityMismatchError, match="RISK_LEVEL_MISMATCH"):
|
||||
await service._check_suitability(9001, product, context) # type: ignore[arg-type]
|
||||
|
||||
evaluator.evaluate.assert_awaited_once()
|
||||
assert evaluator.evaluate.await_args.kwargs["context"] is context
|
||||
|
||||
Reference in New Issue
Block a user