from pyisda.curve import YieldCurve, BadDay, SpreadCurve from pyisda.utils import build_yc from pyisda.cdsone import upfront_charge from pyisda.legs import ContingentLeg, FeeLeg from quantlib.settings import Settings from quantlib.time.api import ( Date, today, Period, Years, WeekendsOnly, Quarterly, CDS, Actual360, ModifiedFollowing, Actual365Fixed) from quantlib.quotes import SimpleQuote from quantlib.termstructures.credit.api import ( SpreadCdsHelper, Interpolator, ProbabilityTrait, PiecewiseDefaultCurve ) from quantlib.termstructures.yields.api import YieldTermStructure from quantlib.pricingengines.credit.isda_cds_engine import IsdaCdsEngine import datetime import array import math import numpy as np import pandas as pd from db import dbengine from yieldcurve import YC import pdb def get_spread(index, series): engine = dbengine("serenitasdb") df = pd.read_sql("SELECT date, tenor, closespread FROM index_quotes WHERE " \ "index = %(index)s and series = %(series)s", engine, params = {"index": index, "series": series}, parse_dates=['date'], index_col = ['date', 'tenor']) df = df.unstack('tenor') df.columns = ['spread_' + c for c in df.columns.levels[1]] return df[['spread_3yr', 'spread_5yr', 'spread_7yr', 'spread_10yr']] def test_sc(df): settings = Settings() tenors = [Period(3, Years), Period(5, Years), Period(7, Years), Period(10, Years)] quotes = [] for i in range(4): quotes.append(SimpleQuote()) yts = YieldTermStructure() helpers = [SpreadCdsHelper(q, t, 1, WeekendsOnly(), Quarterly, ModifiedFollowing, CDS, Actual360(), 0.4, discount_curve = yts, lastperiod = Actual360(True)) for q, t in zip(quotes, tenors)] pdc = PiecewiseDefaultCurve(ProbabilityTrait.SurvivalProbability, Interpolator.LogLinear, 0, WeekendsOnly(), helpers, Actual365Fixed()) for r in df.itertuples(index=True, name = None): settings.evaluation_date = Date.from_datetime(r[0]) ts = YC() yts.link_to(ts) for i in range(4): quotes[i].value = r[i+1] *1e-4 return helpers def FEP(sc, recovery): pass if __name__ == "__main__": settings = Settings() trade_date = datetime.date.today() settings.evaluation_date = today() start_date = datetime.date(2016, 6, 20) term_date = datetime.date(2021, 6, 20) dc = YC() isda_engine = "po" value_date = trade_date yc = build_yc(trade_date, True) spread = 0.007 spread = array.array('d', [spread]) value_date = datetime.date(2016, 7, 29) step_in_date = trade_date + datetime.timedelta(days=1) sc = SpreadCurve(trade_date, yc, start_date, step_in_date, value_date, [term_date], spread, 0.4, True) sc_data = sc.inspect()['data'] hazard_rate = math.log(1 + sc_data[0][1]) expiration_date = datetime.date(2016, 9, 21) fee_leg = FeeLeg(start_date, term_date, True, 1, 1) default_leg = ContingentLeg(start_date, term_date, 1) fee_leg_expiry = FeeLeg(start_date, expiration_date, True, 1, 1) default_leg_expiry = ContingentLeg(start_date, expiration_date, 1) fee_leg_pv = fee_leg.pv(trade_date, step_in_date, trade_date, yc, sc, True) default_leg_pv = default_leg.pv(trade_date, step_in_date, trade_date, yc, sc, 0.4) V1 = default_leg_pv - fee_leg_pv fee_leg_expiry_pv = fee_leg_expiry.pv(trade_date, step_in_date, trade_date, yc, sc, True) default_leg_expiry_pv = default_leg_expiry.pv(trade_date, step_in_date, trade_date, yc, sc, 0.4) V2 = default_leg_expiry_pv - fee_leg_expiry_pv forward_annuity = fee_leg.pv(trade_date, expiration_date+datetime.timedelta(days=1), trade_date, yc, sc, True) exercise_settlement = datetime.date(2016, 9, 25) print((0.007-0.01) * forward_annuity) forward_price = forward_annuity*(0.007-0.01) / ( yc.discount_factor(exercise_settlement)*math.exp(-hazard_rate * (expiration_date-trade_date).days/365 )) print(fee_leg.pv(trade_date, step_in_date, trade_date, yc, sc, True)) print(fee_leg.pv(trade_date, expiration_date + datetime.timedelta(days=1), trade_date, yc, sc, True))