--------------------------------------------------------- -- -- Module : Parameters -- Copyright : Bartosz Wójcik (2010) -- License : BSD3 -- -- Maintainer : bartek@sudety.it -- Stability : Unstable -- Portability : portable -- -- Parameters hidden in the reader monad --------------------------------------------------------- module Haslo.Parameters (IPPMonad ,runWithIPP ,InstalmentPlanParam (..) ,paramDT ,paramMT ,paramYT ,paramDR ,paramMR ,paramYR ) where import Control.Monad.Reader import Haslo.ErrorHandling import Haslo.CalcCalendar type ParamMonad = ReaderT Param IPPMonad runWithParam param loan = runReaderT loan param data Param = Param {ipp :: InstalmentPlanParam ,fin :: FinancingParameters } deriving Show -- | Parameters for loan construction. They have been separated, because they -- usually do not change often, if at all. data InstalmentPlanParam = IPP {freq :: Freq ,rounding :: RoundingType } deriving Show -- | Reader monad for IPP -- to run loan with parameters. type IPPMonad = ReaderT InstalmentPlanParam ValidMonad -- | Convenience function. runWithIPP :: InstalmentPlanParam -> IPPMonad a -> ValidMonad a runWithIPP param loan = runReaderT loan param absParamMonthlyTrunc = IPP Monthly Truncated absParamDailyTrunc = IPP Daily Truncated absParamYearlyTrunc = IPP Yearly Truncated -- | Rule of 1st instalment date as function of last financing tranche's date. data FstInstRule = FstInstDays Int -- ^ Not less than given number of days after. | FstInstFullFreqAfter -- ^ at least one full 'instFreq' period after, less than two periods. deriving (Eq,Show) instance Enum FstInstRule where toEnum 0 = FstInstFullFreqAfter toEnum n = FstInstDays n fromEnum FstInstFullFreqAfter = 0 fromEnum (FstInstDays n) = n -- | Rule of calculation and maturity of interest for first period of the loan -- from 1st tranche date till one instalment period before first instalment. data FstIntRule = -- | Interest is calculated daily. -- Mature on each instalment day. FstIntDaily -- | Interest is calculated from tranche date till next instalment day, if next instalment -- day is before first instalment date. -- Interest matures on each instalment day. | FstIntTillNextDue -- | Interest is calculated from tranche date till first instalment date. -- Interest matures on first instalment date. | FstIntTill1stInst -- | Interest is calculated from tranche date till first instalment date -- which amount > 0. All instalments = 0 before have to be removed. Date of -- first >0 instalment doesn't change though. -- Interest matures on date of first >0 instalment. | FstIntTill1stInstGT0 -- | Proprietary solution. -- Interest is calculated and matures like for @FstIntTill1stInstGT0@, the difference -- is that common nominal interest rate is re-caluclated using real number of days of -- between tranche date and first instalment date. In this solution only one tranche is -- alowed. | FstIntCtlm deriving (Eq,Show,Enum) -- | Rule defining what to do with late interest coming out of grace period. data LateIntOfGracePeriodRule = -- | Late interest will be due on first instalment - will increase its amount. LateIntFstInst -- | Late interest will be due on first significant instalment - will increase its amount. | LateIntFstSignInst -- | Late interest will be due on last instalment - will increase its amount. | LateIntLastInst deriving (Eq,Show) -- | Collection of parameters customizing financing. data FinancingParameters = FP { instFreq :: Freq -- ^ Frequency of instalment must be >= than @intFreq@ , intFreq :: Freq -- ^ Frequency of interest , fin1stInstRule :: FstInstRule , fin1stIntRule :: FstIntRule , finCalendar :: CalendarType -- ^ calendar type , lateIntRule :: LateIntOfGracePeriodRule } deriving (Eq,Show) paramDT = IPP Daily Truncated -- | Monthly Truncated paramMT :: InstalmentPlanParam paramMT = IPP Monthly Truncated paramYT = IPP Yearly Truncated paramDR = IPP Daily Truncated paramMR = IPP Monthly Rounded -- | Yearly Rounded paramYR :: InstalmentPlanParam paramYR = IPP Yearly Rounded