22from lenses import lens
33import toolz as tz
44import pytest
5+ import re , math
56
67from absbox .tests .regression .deals import *
78
89from absbox import API ,EnginePath ,readInspect ,PickApiFrom
910
11+ def closeTo (a ,b ,r = 2 ):
12+ assert math .floor (a * 10 ** r )/ 10 ** r == math .floor (b * 10 ** r )/ 10 ** r
1013
14+ def filterTxn (rs , f , rg ):
15+ return [ r for r in rs if re .match (rg , r [f ])]
1116
1217@pytest .fixture
1318def setup_api ():
14-
15-
1619 api = API (EnginePath .DEV ,check = False ,lang = 'english' )
17-
18-
1920 return api
2021
2122@pytest .mark .pool
@@ -24,5 +25,78 @@ def test_01(setup_api):
2425 assert r ['pool' ]['flow' ].keys () == {"PoolConsol" }
2526 assert r ['pool' ]['flow' ]['PoolConsol' ].to_records ()[0 ][0 ]== '2021-04-15'
2627
28+ @pytest .mark .collect
29+ def test_collect_01 (setup_api ):
30+ r = setup_api .run (test01 , read = True , runAssump = [])
31+ assert r ['pool' ]['flow' ]['PoolConsol' ].to_records ()[0 ][0 ]== '2021-04-15'
32+ assert r ['pool' ]['flow' ]['PoolConsol' ].loc [:'2021-04-15' ]["Interest" ].values .sum () == filterTxn ( r ['accounts' ]['acc01' ].loc [:'2021-04-15' ].to_dict ('records' ), 'memo' , ".*CollectedInterest.*" )[0 ]['change' ]
33+ assert r ['pool' ]['flow' ]['PoolConsol' ].loc [:'2021-04-15' ]["Principal" ].values .sum () == filterTxn ( r ['accounts' ]['acc01' ].loc [:'2021-04-15' ].to_dict ('records' ), 'memo' , ".*CollectedPrincipal.*" )[0 ]['change' ]
34+ assert r ['pool' ]['flow' ]['PoolConsol' ].loc [:'2021-04-15' ]["Prepayment" ].values .sum () == 0.00
35+ assert r ['pool' ]['flow' ]['PoolConsol' ].loc [:'2021-04-15' ]["Default" ].values .sum () == 0.00
36+ assert r ['pool' ]['flow' ]['PoolConsol' ].loc [:'2021-04-15' ]["Recovery" ].values .sum () == 0.00
37+
38+ # two accounts with Principal and Interest
39+ testSepAcc = tz .pipe ( test01 & lens .accounts .modify ( lambda xs : tuple (tz .cons ( ('acc02' ,{"balance" :0 }), xs )))
40+ ,lambda d : d & lens .collection [0 ][1 ].set ("acc02" )
41+ )
42+
43+ r = setup_api .run (testSepAcc , read = True , runAssump = [])
44+ assert r ['pool' ]['flow' ]['PoolConsol' ].loc [:'2021-04-15' ]["Interest" ].values .sum () == filterTxn ( r ['accounts' ]['acc02' ].loc [:'2021-04-15' ].to_dict ('records' ), 'memo' , ".*CollectedInterest.*" )[0 ]['change' ]
45+ assert r ['pool' ]['flow' ]['PoolConsol' ].loc [:'2021-04-15' ]["Principal" ].values .sum () == filterTxn ( r ['accounts' ]['acc01' ].loc [:'2021-04-15' ].to_dict ('records' ), 'memo' , ".*CollectedPrincipal.*" )[0 ]['change' ]
46+
47+ # three accounts with Principal( 30% 70%) and Interest
48+ test2SepAcc = tz .pipe ( test01 & lens .accounts .modify ( lambda xs : tuple (tz .cons ( ('acc02' ,{"balance" :0 }), xs )))
49+ & lens .accounts .modify ( lambda xs : tuple (tz .cons ( ('acc03' ,{"balance" :0 }), xs )))
50+ ,lambda d : d & lens .collection .set ([["CollectedInterest" ,"acc02" ]
51+ ,["CollectedPrincipal" ,[0.7 ,"acc01" ],[0.3 ,"acc03" ]]
52+ ,["CollectedPrepayment" ,"acc01" ]
53+ ,["CollectedRecoveries" ,"acc01" ]]
54+ )
55+ )
56+ r = setup_api .run (test2SepAcc , read = True , runAssump = [])
57+ assert r ['pool' ]['flow' ]['PoolConsol' ].loc [:'2021-04-15' ]["Interest" ].values .sum () == filterTxn ( r ['accounts' ]['acc02' ].loc [:'2021-04-15' ].to_dict ('records' ), 'memo' , ".*CollectedInterest.*" )[0 ]['change' ]
58+ principalCollectedAtPeriod0 = r ['pool' ]['flow' ]['PoolConsol' ].loc [:'2021-04-15' ]["Principal" ].values .sum ()
59+ closeTo (principalCollectedAtPeriod0 * 0.7
60+ , filterTxn ( r ['accounts' ]['acc01' ].loc [:'2021-04-15' ].to_dict ('records' ), 'memo' , ".*CollectedPrincipal.*" )[0 ]['change' ]
61+ , 2 )
62+ closeTo (principalCollectedAtPeriod0 * 0.3
63+ , filterTxn ( r ['accounts' ]['acc03' ].loc [:'2021-04-15' ].to_dict ('records' ), 'memo' , ".*CollectedPrincipal.*" )[0 ]['change' ]
64+ , 2 )
2765
66+ # multiple pool with ratio split collection
67+ testMultiplePool = test01 & lens .accounts .set ((("acc01" ,{"balance" :0 }),("acc02" ,{"balance" :0 }),("acc03" ,{"balance" :0 }))) \
68+ & lens .pool .set ({"PoolA" :{'assets' :[["Mortgage"
69+ ,{"originBalance" :1320.0 ,"originRate" :["fix" ,0.045 ],"originTerm" :30
70+ ,"freq" :"Monthly" ,"type" :"Level" ,"originDate" :"2021-02-01" }
71+ ,{"currentBalance" :1320.0
72+ ,"currentRate" :0.08
73+ ,"remainTerm" :30
74+ ,"status" :"current" }]]},
75+ "PoolB" :{'assets' :[["Mortgage"
76+ ,{"originBalance" :880.0 ,"originRate" :["fix" ,0.045 ],"originTerm" :30
77+ ,"freq" :"Monthly" ,"type" :"Level" ,"originDate" :"2021-02-01" }
78+ ,{"currentBalance" :880.0
79+ ,"currentRate" :0.08
80+ ,"remainTerm" :30
81+ ,"status" :"current" }]]}}) \
82+ & lens .collection .set ([[["PoolA" ,],"CollectedInterest" ,"acc01" ]
83+ ,[["PoolB" ,],"CollectedInterest" ,"acc03" ]
84+ ,[["PoolA" ,"PoolB" ],"CollectedPrincipal" ,[0.7 ,"acc02" ],[0.3 ,"acc03" ]]
85+ ])
86+ r = setup_api .run (testMultiplePool , read = True , runAssump = [])
2887
88+ # acc01 get all interest from pool A
89+ closeTo (r ['pool' ]['flow' ]['PoolA' ].loc [:'2021-04-15' ]["Interest" ].values .sum ()
90+ , filterTxn ( r ['accounts' ]['acc01' ].loc [:'2021-04-15' ].to_dict ('records' ), 'memo' , ".*CollectedInterest.*" )[0 ]['change' ])
91+ # acc03 get all interest from pool B
92+ closeTo (r ['pool' ]['flow' ]['PoolB' ].loc [:'2021-04-15' ]["Interest" ].values .sum ()
93+ , filterTxn ( r ['accounts' ]['acc03' ].loc [:'2021-04-15' ].to_dict ('records' ), 'memo' , ".*CollectedInterest.*" )[0 ]['change' ])
94+ # acc02 get 70% of principal from pool A and Pool B
95+ closeTo ((r ['pool' ]['flow' ]['PoolA' ].loc [:'2021-04-15' ]["Principal" ].values .sum () + \
96+ r ['pool' ]['flow' ]['PoolB' ].loc [:'2021-04-15' ]["Principal" ].values .sum ())* 0.7
97+ , filterTxn ( r ['accounts' ]['acc02' ].loc [:'2021-04-15' ].to_dict ('records' ), 'memo' , ".*CollectedPrincipal.*" )[0 ]['change' ])
98+ # acc03 get all interest from pool B and 30% of principal from pool A and Pool B
99+ closeTo ((r ['pool' ]['flow' ]['PoolA' ].loc [:'2021-04-15' ]["Principal" ].values .sum () + \
100+ r ['pool' ]['flow' ]['PoolB' ].loc [:'2021-04-15' ]["Principal" ].values .sum ())* 0.3
101+ , filterTxn ( r ['accounts' ]['acc03' ].loc [:'2021-04-15' ].to_dict ('records' ), 'memo' , ".*CollectedPrincipal.*" )[0 ]['change' ])
102+
0 commit comments