diff options
| author | Somhairle H. Marisol <[email protected]> | 2026-09-22 04:59:12 +0800 |
|---|---|---|
| committer | Somhairle H. Marisol <[email protected]> | 2026-09-22 04:59:12 +0800 |
| commit | 545f2a507fd0138f7fd50ed7fb2631d0273db625 (patch) | |
| tree | f9eedee8d82b632474408e774cb95e9e01a9750d /tests/FundLab.Web.Tests | |
| parent | 0183b86f18d9897ff9487e6d864898954397991d (diff) | |
| download | fund-lab-545f2a507fd0138f7fd50ed7fb2631d0273db625.tar.gz | |
Integrate bond and stock positions into fund valuation (3d-23)
Diffstat (limited to 'tests/FundLab.Web.Tests')
| -rw-r--r-- | tests/FundLab.Web.Tests/BoundaryTests.fs | 69 |
1 files changed, 69 insertions, 0 deletions
diff --git a/tests/FundLab.Web.Tests/BoundaryTests.fs b/tests/FundLab.Web.Tests/BoundaryTests.fs index 3a9ec61..d8bb472 100644 --- a/tests/FundLab.Web.Tests/BoundaryTests.fs +++ b/tests/FundLab.Web.Tests/BoundaryTests.fs @@ -710,6 +710,75 @@ module ConfirmationBoundaryTests = Assert.False(updated.bondPositionsInFlight) [<Fact>] + let ``valuation completion stores totals and per-position marks`` () = + let fundId = "3fa85f64-5717-4562-b3fc-2c963f66afa6" + + let model = + { init () with + createdFund = Some(FundBoundaryTests.sampleFund fundId) + valuationReadSeq = 1 + valuationInFlight = true } + + let raw : RawFundValuation = + { + fundId = fundId + currency = "CNY" + cash = "10000.00" + positionsMarketValue = "126320.68" + portfolioValue = "136320.68" + pricedPositions = 1 + unavailablePositions = 1 + positions = + [| + { + instrumentCode = "600519" + name = box "贵州茅台" + assetClass = "stock" + quantity = "100.00000000" + price = box "1252.57" + priceSource = box "live" + marketValue = box "125257.00" + status = "priced" + } + { + instrumentCode = "110075" + name = box "南航转债" + assetClass = "bond" + quantity = "10.00000000" + price = null + priceSource = null + marketValue = null + status = "unavailable" + } + |] + } + + let updated, _ = update (ValuationReadCompleted(1, fundId, raw)) model + + let valuation = updated.valuation.Value + Assert.Equal("136320.68", valuation.portfolioValue) + Assert.Equal(1, valuation.unavailablePositions) + Assert.Equal(2, valuation.positions.Length) + Assert.Equal("unavailable", valuation.positions[1].status) + Assert.False(updated.valuationInFlight) + + [<Fact>] + let ``valuation failure clears totals and surfaces a message`` () = + let fundId = "3fa85f64-5717-4562-b3fc-2c963f66afa6" + + let model = + { init () with + createdFund = Some(FundBoundaryTests.sampleFund fundId) + valuationReadSeq = 1 + valuationInFlight = true } + + let updated, _ = update (ValuationReadFailed(1, fundId, "collector exited with code 2")) model + + Assert.Equal(None, updated.valuation) + Assert.Contains("组合估值不可用", updated.valuationMessage |> Option.defaultValue "") + Assert.False(updated.valuationInFlight) + + [<Fact>] let ``order decode keeps decimal strings and decodes option fields`` () = let confirmed = Api.decodeOrder (sampleConfirmedRaw ()) let pending = Api.decodeOrder (samplePendingRaw ()) |
