TickOptionComputation. TickerId: 21 tickType: 83 ImpliedVolatility: 0.33391930803094855 Delta: 0.5120104766126846 OptionPrice: 113.18464549592791 pvDividend: 6.193513473841583 Gamma:? 0.0013812397555831267 Vega: 3.4475913921237153 Theta: -2.254673784090535 UnderlyingPrice: 3271.87
TickOptionComputation. TickerId: 21 tickType: 80 ImpliedVolatility: None Delta: None OptionPrice: None pvDividend: 6.193513473841583 Gamma:? None Vega: None Theta: None UnderlyingPrice: 3271.87
TickOptionComputation. TickerId: 21 tickType: 81 ImpliedVolatility: None Delta: None OptionPrice: None pvDividend: 6.193513473841583 Gamma:? None Vega: None Theta: None UnderlyingPrice: 3271.87
TickOptionComputation. TickerId: 21 tickType: 82 ImpliedVolatility: None Delta: None OptionPrice: None pvDividend: 6.193513473841583 Gamma:? None Vega: None Theta: None UnderlyingPrice: 3271.87
TickOptionComputation. TickerId: 21 tickType: 83 ImpliedVolatility: 0.33391930803094855 Delta: 0.5120104766126846 OptionPrice: 113.18464549592791 pvDividend: 6.193513473841583 Gamma:? 0.0013812397555831267 Vega: 3.4475913921237153 Theta: -2.254673784090535 UnderlyingPrice: 3271.87
Below is my code:
import ibapi
from ibapi.client import EClient
from ibapi.wrapper import EWrapper
from ibapi.contract import Contract
from ibapi.ticktype import TickTypeEnum
import math
import threading
import time
import datetime
import pandas as pd
import numpy as np
class IBapi(EWrapper, EClient):
current_price = 0.0
ticker_cntrl = 0
option_greeks_df = pd.DataFrame()
option_bid_df = pd.DataFrame()
option_ask_df = pd.DataFrame()
expiry_dates = []
def nextValidId(self, orderId: int):
super().nextValidId(orderId)
print("setting nextValidOrderId: %d", orderId)
self.nextValidOrderId = orderId
def __init__(self):
EClient.__init__(self, self)
def initialize_output(self, exp_dates, ticker_cntrl):
option_greeks_columns = ['exp_date', 'OptionPrice', 'ImpliedVolatility', 'Delta', 'Gamma']
type(self).option_greeks_df = pd.DataFrame(columns=option_greeks_columns)
type(self).expiry_dates = exp_dates
type(self).ticker_cntrl = ticker_cntrl
option_bid_columns = ['exp_date', 'BidPrice']
type(self).option_bid_df = pd.DataFrame(columns=option_bid_columns)
option_ask_columns = ['exp_date', 'AskPrice']
type(self).option_ask_df = pd.DataFrame(columns=option_ask_columns)
def tickPrice(self, reqId, tickType, price, attrib):
if (reqId == 1):
if (TickTypeEnum.DELAYED_LAST == tickType):
print("Tick Price Ticker ID: " + str(reqId) + " tickType: " + TickTypeEnum.to_str(
tickType) + " Price : " + str(price) + "\n")
type(self).current_price = price
# else:
# print("Tick Price Ticker ID: " + str(reqId) + " tickType: " + TickTypeEnum.to_str(
# tickType) + " Price : " + str(price) + "\n")
#
def tickOptionComputation(self, reqId, tickType, tickAttrib,
impliedVol, delta, optPrice, pvDividend,
gamma, vega, theta, undPrice):
print("TickOptionComputation. TickerId:", reqId, "tickType:", tickType,
"ImpliedVolatility:", impliedVol, "Delta:", delta, "OptionPrice:",
optPrice, "pvDividend:", pvDividend, "Gamma: ", gamma, "Vega:", vega,
"Theta:", theta, "UnderlyingPrice:", undPrice)
if (optPrice == None ):
super().tickOptionComputation(reqId, tickType,tickAttrib, impliedVol, delta,
optPrice, pvDividend, gamma, vega,
theta, undPrice)
if (tickType == 80): # Delayed Bid Option 80
type(self).option_bid_df.loc[reqId - type(self).ticker_cntrl] = [
type(self).expiry_dates[reqId - type(self).ticker_cntrl],
optPrice]
if (tickType == 81): # Delayed Ask Option 81
type(self).option_ask_df.loc[reqId - type(self).ticker_cntrl] = [
type(self).expiry_dates[reqId - type(self).ticker_cntrl],
optPrice]
if (tickType == 83): # Delayed Model Option 83
type(self).option_greeks_df.loc[reqId - type(self).ticker_cntrl] = [
type(self).expiry_dates[reqId - type(self).ticker_cntrl],
optPrice, impliedVol,
delta, gamma]
def get_spx_stk_contract():
spx_contract = Contract()
spx_contract.symbol = 'SPX'
spx_contract.secType = 'IND'
spx_contract.exchange = 'CBOE'
spx_contract.currency = 'USD'
spx_contract.tradingClass = "SPXW"
return spx_contract
def get_spx_opt_contract(strike_price, exp_date, c_type):
spx_contract = Contract()
spx_contract.symbol = 'SPX'
spx_contract.secType = 'OPT'
spx_contract.exchange = 'SMART'
spx_contract.currency = 'USD'
spx_contract.lastTradeDateOrContractMonth = exp_date # "20180523"
spx_contract.strike = strike_price # 2750
if (c_type == 0):
spx_contract.right = 'C'
else:
spx_contract.right = 'P'
spx_contract.multiplier = '100'
spx_contract.tradingClass = 'SPXW'
return spx_contract
def return_contract(tick_symbol):
i_contract = Contract()
i_contract.symbol = tick_symbol
i_contract.secType = 'STK'
i_contract.exchange = 'SMART'
i_contract.currency = 'USD'
return i_contract
def next_weekday(d, weekday, week_multiplier):
# Function to get the next weekday from current day (0- Monday, 2 - Wednesday, 4 - Friday)
days_ahead = weekday - d.weekday()
if days_ahead < 0: # Target day already happened this week
days_ahead += 7 * week_multiplier
return d + datetime.timedelta(days_ahead)
def exp_dates(n_weeks=4, s_type=0):
# n_weeks = number of weeks required
# s_type = 0 or 1 (0 is for SPY & SPX, 1 is for other stocks)
d = datetime.date.today()
expiration_dates = []
if (s_type == 0):
for i in range(n_weeks):
# Monday, Wednesday & Friday expiry for SPY & SPX
expiration_dates.append(next_weekday(d + datetime.timedelta(7 * i), 0, (i + 1)))
expiration_dates.append(next_weekday(d + datetime.timedelta(7 * i), 2, (i + 1)))
expiration_dates.append(next_weekday(d + datetime.timedelta(7 * i), 4, (i + 1)))
else:
for i in range(n_weeks):
# Only Friday expiry for stocks
expiration_dates.append(next_weekday(d + datetime.timedelta(7 * i), 4, (i + 1)))
return expiration_dates
def get_floor_price(s_type, current_price):
# s_type = 0 or 1 (0 is for SPX, 1 is for SPY & other stocks)
floor_price = 0.0
if (s_type == 0):
floor_price = (math.floor(current_price / 5)) * 5
else:
floor_price = math.floor(current_price)
return floor_price
def get_ceil_price(s_type, current_price):
# s_type = 0 or 1 (0 is for SPX, 1 is for SPY & other stocks)
ceil_price = 0.0
if (s_type == 0):
ceil_price = (math.ceil(current_price / 5)) * 5
else:
ceil_price = math.ceil(current_price)
return ceil_price
def main():
app = IBapi()
app.connect('127.0.0.1', 7496, 0)
def run_loop():
app.run()
# Start the socket in a thread
api_thread = threading.Thread(target=run_loop, daemon=True)
api_thread.start()
time.sleep(1) # Sleep interval to allow time for connection to server
# To get stk contracts use
# return_contract('SPY')
# return_contract('AAPL')
# Create contract object
stk_contract = get_spx_stk_contract()
app.reqMarketDataType(4)
# Request Market Data
app.reqMktData(1, stk_contract, "", False, False, [])
time.sleep(4) # Sleep interval to allow time for incoming price data
# set the ceil & floor price from current price
app.ceil_price = get_ceil_price(0, app.current_price)
app.floor_price = get_floor_price(0, app.current_price)
# Print the current prices
print(app.current_price, app.floor_price, app.ceil_price)
# Get the next 4 week expiration
expiration_dates = exp_dates(4, 0)
# print(expiration_dates)
# Create a common data frame format
# data_frame_column = ['exp_date', 'OptionPrice', 'ImpliedVolatility', 'Delta', 'Gamma', 'BidPrice', 'AskPrice',
# 'AvgPrice']
# floor_call_price_df = pd.DataFrame(columns=data_frame_column)
# floor_put_price_df = pd.DataFrame(columns=data_frame_column)
# ceil_call_price_df = pd.DataFrame(columns=data_frame_column)
# ceil_put_price_df = pd.DataFrame(columns=data_frame_column)
# initialize the output
app.initialize_output(expiration_dates, 10)
# Set floor price call
ticker_id_counter = 0
for exp_d in expiration_dates:
app.reqMarketDataType(4)
opt_contract = get_spx_opt_contract(app.floor_price, exp_d.strftime('%Y%m%d'), 0)
app.reqMktData(10 + ticker_id_counter, opt_contract, "", False, False, [])
ticker_id_counter = ticker_id_counter + 1
time.sleep(10) # Sleep interval to allow time for incoming price data
# Add to our floor call data frame
floor_call_price_df = pd.merge(pd.merge(app.option_greeks_df, app.option_bid_df, how='outer', on='exp_date'),
app.option_ask_df, how='outer', on='exp_date')
print(app.option_greeks_df)
print(app.option_bid_df)
print(app.option_ask_df)
print(floor_call_price_df)
app.disconnect()
if __name__ == '__main__':
main()