diff options
Diffstat (limited to 'python/notebooks/Option Trades.ipynb')
| -rw-r--r-- | python/notebooks/Option Trades.ipynb | 194 |
1 files changed, 100 insertions, 94 deletions
diff --git a/python/notebooks/Option Trades.ipynb b/python/notebooks/Option Trades.ipynb index 6a28003f..32cd5b04 100644 --- a/python/notebooks/Option Trades.ipynb +++ b/python/notebooks/Option Trades.ipynb @@ -14,7 +14,13 @@ "from analytics import Swaption, BlackSwaption, BlackSwaptionVolSurface, CreditIndex, Portfolio\n", "from analytics.scenarios import run_swaption_scenarios, run_index_scenarios, run_portfolio_scenarios, run_portfolio_scenarios_module\n", "from scipy.interpolate import SmoothBivariateSpline\n", - "from db import dbengine" + "from db import dbengine\n", + "\n", + "from db import dbconn\n", + "from analytics import init_ontr\n", + "conn = dbconn('dawndb')\n", + "init_ontr()\n", + "pd.options.display.float_format = \"{:,.2f}\".format" ] }, { @@ -32,6 +38,38 @@ "metadata": {}, "outputs": [], "source": [ + "#Trade Analysis - see if the trade is net positive gamma\n", + "index = 'IG'\n", + "series = 32\n", + "option_delta = CreditIndex(index, series, '5yr') \n", + "option_delta.spread = 64\n", + "option1 = BlackSwaption(option_delta, datetime.date(2019, 7, 17), 60, option_type=\"payer\") \n", + "option2 = BlackSwaption(option_delta, datetime.date(2019, 7, 17), 75, option_type=\"payer\") \n", + "option1.sigma = .394 \n", + "option2.sigma = .52\n", + "option1.notional = 200_000_000 \n", + "option2.notional = 200_000_000 \n", + "option1.direction = 'Long' \n", + "option2.direction = 'Short' \n", + "option_delta.notional = option1.delta * option1.notional + option2.delta * option2.notional\n", + "portf = Portfolio([option1, option2, option_delta], trade_ids=['opt1', 'opt2', 'delta'])" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "portf" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ "def plot_trade_scenarios(portf, shock_min=-.15, shock_max=.2, vol_time_roll=True):\n", " portf.reset_pv()\n", " end_date = min(portf.swaptions, key=lambda x: x.exercise_date).exercise_date\n", @@ -43,8 +81,8 @@ " vol_surface = {}\n", " for trade in portf.swaptions:\n", " vs = BlackSwaptionVolSurface(trade.index.index_type, trade.index.series, \n", - " value_date=date)\n", - " vol_surface[trade.index.index_type + trade.index.series] = vs[vs.list(option_type='payer')[-1]]\n", + " value_date=portf.value_date, interp_method = \"bivariate_linear\")\n", + " vol_surface[(trade.index.index_type, trade.index.series)] = vs[vs.list(option_type='payer')[-1]]\n", " \n", " df = run_portfolio_scenarios(portf, date_range, params=[\"pnl\",\"delta\"],\n", " spread_shock = spread_shock,\n", @@ -84,73 +122,26 @@ "metadata": {}, "outputs": [], "source": [ - "#Ad hoc\n", - "index = 'IG'\n", - "series = 31\n", - "value_date = datetime.date(2018, 11, 18)\n", - "option_delta = CreditIndex(index, series, '5yr', value_date)\n", - "option_delta.spread = 76.5\n", - "option1 = BlackSwaption(option_delta, datetime.date(2019, 2, 20), 65, option_type=\"payer\")\n", - "option2 = BlackSwaption(option_delta, datetime.date(2019, 2, 20), 90, option_type=\"payer\")\n", - "option3 = BlackSwaption(option_delta, datetime.date(2019, 2, 20), 60, option_type=\"payer\")\n", - "option1.sigma = .425\n", - "option2.sigma = .59\n", - "option3.sigma = .0\n", - "option1.notional = 300_000_000\n", - "option2.notional = 300_000_000\n", - "option3.notional = 1\n", - "option1.direction = 'Long'\n", - "option2.direction = 'Short'\n", - "option3.direction = 'Long'\n", - "option_delta.notional = 1\n", - "option_delta.notional = option1.notional * option1.delta + option2.notional * option2.delta + option3.notional * option3.delta\n", - "option_delta.direction = 'Seller' if option_delta.notional > 0 else 'Buyer'\n", - "option_delta.notional = abs(option_delta.notional)\n", - "portf = Portfolio([option1, option2, option3, option_delta], trade_ids=['opt1', 'opt2', 'opt3', 'delta'])\n", - "#Plot Scenarios Inputs: Portfolio, spread shock tightening%, spread shock widening%, snapshot period)\n", - "portf" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "plot_trade_scenarios(portf)" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "#Ad hoc\n", - "index = 'HY'\n", - "series = 30\n", - "value_date = datetime.date(2018, 6, 7)\n", - "option_delta = CreditIndex(index, series, '5yr', value_date)\n", - "option_delta.spread = 66\n", - "option1 = BlackSwaption(option_delta, datetime.date(2018, 10, 17), 55, option_type=\"receiver\")\n", - "option2 = BlackSwaption(option_delta, datetime.date(2018, 10, 17), 57.5, option_type=\"receiver\")\n", - "option3 = BlackSwaption(option_delta, datetime.date(2018, 10, 17), 60, option_type=\"receiver\")\n", - "option1.sigma = .47\n", - "option2.sigma = .53\n", - "option3.sigma = .69\n", - "option1.notional = 50_000_000\n", - "option2.notional = 100_000_000\n", - "option3.notional = 1\n", - "option1.direction = 'Long'\n", - "option2.direction = 'Short'\n", - "option3.direction = 'Long'\n", - "#option_delta.notional = 1\n", - "option_delta.notional = option1.notional * option1.delta + option2.notional * option2.delta + option3.notional * option3.delta\n", - "option_delta.direction = 'Seller' if option_delta.notional > 0 else 'Buyer'\n", - "option_delta.notional = abs(option_delta.notional)\n", - "portf = Portfolio([option1, option2, option3, option_delta], trade_ids=['opt1', 'opt2', 'opt3', 'delta'])\n", - "#Plot Scenarios Inputs: Portfolio, spread shock tightening%, spread shock widening%, snapshot period)\n", - "portf" + "def calc_simple_scenario(portf, shock_min=-.15, shock_max=.2):\n", + " portf.reset_pv()\n", + " end_date = min(portf.swaptions, key=lambda x: x.exercise_date).exercise_date\n", + " date_range = pd.bdate_range(portf.value_date,\n", + " end_date - pd.tseries.offsets.BDay(), freq='3B')\n", + " vol_shock = [0]\n", + " spread_shock = np.arange(shock_min, shock_max, 0.01)\n", + " index = portf.indices[0].index_type\n", + " vol_surface = {}\n", + " for trade in portf.swaptions:\n", + " vs = BlackSwaptionVolSurface(trade.index.index_type, trade.index.series, \n", + " value_date=portf.value_date, interp_method = \"bivariate_linear\")\n", + " vol_surface[(trade.index.index_type, trade.index.series)] = vs[vs.list(option_type='payer')[-1]]\n", + "\n", + " df = run_portfolio_scenarios(portf, date_range, params=[\"pnl\"],\n", + " spread_shock = spread_shock,\n", + " vol_shock = vol_shock,\n", + " vol_surface = vol_surface)\n", + "\n", + " return df.xs('pnl', axis=1, level=1).sum(axis=1) " ] }, { @@ -159,6 +150,7 @@ "metadata": {}, "outputs": [], "source": [ + "plot_trade_scenarios(portf)\n", "plot_trade_scenarios(portf, -.15, .8, vol_time_roll=False)" ] }, @@ -207,7 +199,14 @@ "option1 = BlackSwaption.from_tradeid(10, option_delta)\n", "option2 = BlackSwaption.from_tradeid(11, option_delta)\n", "portf = Portfolio([option1, option2, option_delta], trade_ids=['opt1', 'opt2', 'delta'])\n", - "#plot_trade_scenarios(portf)" + "#plot_trade_scenarios(portf)\n", + "\n", + "#March 2019: May Bull Risky\n", + "option_delta = CreditIndex.from_tradeid(1063)\n", + "option1 = BlackSwaption.from_tradeid(41, option_delta)\n", + "option2 = BlackSwaption.from_tradeid(40, option_delta)\n", + "portf = Portfolio([option1, option2, option_delta], trade_ids=['opt1', 'opt2', 'delta'])\n", + "results = calc_simple_scenario(portf, shock_min=-.3, shock_max=.3)" ] }, { @@ -250,21 +249,35 @@ "outputs": [], "source": [ "#Current Positions\n", - "#option_delta = CreditIndex.from_tradeid(945)\n", - "index = 'HY'\n", - "series = 30\n", - "option_delta = CreditIndex(index, series, '5yr', value_date=datetime.date(2018, 6, 7))\n", - "#option_delta.spread = 66\n", - "option_delta.price = 106.75\n", - "option_delta.notional = 1\n", - "option1 = BlackSwaption.from_tradeid(14, option_delta)\n", - "option2 = BlackSwaption.from_tradeid(15, option_delta)\n", - "#option3 = BlackSwaption.from_tradeid(16, option_delta)\n", - "#option4 = BlackSwaption.from_tradeid(17, option_delta)\n", - "#portf = Portfolio([option1, option2, option3, option4, option_delta])\n", - "portf = Portfolio([option1, option2, option_delta], trade_ids=['opt1', 'opt2', 'delta'])\n", - "portf.mark()\n", - "plot_trade_scenarios(portf, shock_min=-.15, shock_max=.4)" + "today = datetime.date.today()\n", + "swaption_sql_string = (\"select id, folder, expiration_date from swaptions where date(expiration_date) \"\n", + " \"> %s and swap_type = 'CD_INDEX_OPTION' \"\n", + " \"AND trade_date <= %s AND termination_date iS NULL\")\n", + "index_sql_string = (\"SELECT id, folder, sum(notional * case when protection='Buyer' then -1 else 1 end) \"\n", + " \"OVER (partition by security_id, attach) AS ntl_agg \"\n", + " \"FROM cds WHERE swap_type='CD_INDEX' AND termination_cp IS null \"\n", + " \"AND trade_date <= %s AND maturity > %s\")\n", + "conn = dawn_engine.raw_connection()\n", + "with conn.cursor() as c:\n", + " c.execute(swaption_sql_string, (today, today))\n", + " swaption_trades = [[dealid, f\"{folder}_{dealid}\", expiration_date] for dealid, folder, expiration_date in c]\n", + " c.execute(index_sql_string, (today, today))\n", + " index_trades = [[dealid, f\"{folder}_{dealid}\"] for dealid, folder, ntl in c if ntl != 0]\n", + "conn.close()\n", + "\n", + "portf = Portfolio([BlackSwaption.from_tradeid(dealid) for dealid, _, _ in swaption_trades],\n", + " [trade_id for _, trade_id, _ in swaption_trades])\n", + "index_trades = list(filter(lambda x: \"CURVE\" not in x[1], index_trades))\n", + "index_trades = list(filter(lambda x: \"SER_IGINDX\" not in x[1], index_trades))\n", + "index_trades = list(filter(lambda x: \"HEDGE_MBS\" not in x[1], index_trades))\n", + "index_trades = list(filter(lambda x: \"IGINX\" not in x[1], index_trades))\n", + "\n", + "for trade_id, name in index_trades:\n", + " portf.add_trade(CreditIndex.from_tradeid(trade_id), name)\n", + " \n", + "portf.value_date = today\n", + " \n", + "results = calc_simple_scenario(portf, shock_min=-.3, shock_max=.3)" ] }, { @@ -273,13 +286,6 @@ "metadata": {}, "outputs": [], "source": [] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [] } ], "metadata": { @@ -298,7 +304,7 @@ "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", - "version": "3.7.1" + "version": "3.7.3" } }, "nbformat": 4, |
