Git Product home page Git Product logo

qc-options-framework's Introduction

QC options framework/algo

Options framework that allows for an easier implementation of option strategies using QuantConnect's Lean.

Setup

In order to make this easier you need to have quantconnect running on local dev. That means

  1. Create a new quant connect algorithm.
  2. Clone this repository
  3. Install the quantconnect extension on VSCode and setup your env
  4. Open your newly created algorithm on your local environment
  5. Copy all the files from the cloned repo to this quantconnect algo
  6. Start creating your own AlphaModel, MonitorModel and ExecutionModel (optional)

Some explanation of how it works

  • each of the folders Alpha, Execution, Monitor, PortfolioConstruction have a Base.py class.
  • when you want to use a new strategy you should/can create a new file that inherits from those Base.py classes
  • examples of classes/strategies: Alpha/SPXic.py, Monitor/SPXicMonitor.py, Execution/SPXExecutionModel.py
  • each of the Base.py classes have some DEFAULT_PARAMETERS with comments as to what each of those do.
  • when you inherit from the Base classes you can change the DEFAULT_PARAMETERS values by definiing a PARAMETERS class variable
  • at the end you just have to set those new classes you made in main.py to be used.
  • the system is not 100% Algo Framework so its a hybrid. That means I hold positions in self.context.allPositions, open positions in self.context.openPositions, working orders in self.context.workingOrders.
  • you can see the initial variables attached to self.context (that is actually the algorithm instance) by going to SetupBaseStructure.py
  • all the positions are instances of Strategy/Position.py a dataclass with defined attributes
  • the Strategy/Position.py also holds dataclasses for WorkingOrders and Legs.

Notes

This whole code started from the rccannizzaro repository and the amazing work done there. I started tinkering with it and then eventually hit the limit of over 250+ lines for one file on QC so then it evolved into this one. The code here seems like it follows the principle layed down by QC in their lean framework documentation but in fact there is no 100% separation of concern as we have the communication between classes done via a dataclass of trades and positions. The reason for this is the fact that QC does not allow for more details to be added to Insights and in order to get better management and control we need to just use our own positions dataclass.

qc-options-framework's People

Contributors

chocksy avatar ffahimi avatar baerenstein avatar

Stargazers

Colin Lawless avatar Robert Bach avatar Joseph Loss avatar  avatar  avatar raggamuffin avatar Francis Hsu avatar Michal Hantl avatar

Watchers

 avatar  avatar  avatar  avatar

qc-options-framework's Issues

Implement the changes needed for universe selection of stocks

This has not been tested but we should have the ability to implement a selection of stocks universe selection strategy as well.
Most probably this should be defined by the PARAMETERS of the strategy by setting the rules of the selection.
Then in the security changed and removed we should handle the behaviour of removing and adding full securities.

Disable QC buying power model

I tried to set this on the security but the live algo does not work anymore if i do. Figure out a better way to handle this. The issue happened on a 1M paper account on IBKR while existing positions for 60x CCS and 70xPCS SPX were open. This should not require that much margin by any means as they are spreads.
Error is:

Order Error: ids: [213,214], Insufficient buying power to complete orders (Value:[-1025,275]), Reason: Id: 213, Initial Margin: -806977.5, Free Margin: 0.

image

ProviderOptionContract does not seem to support greeks for when slice:False

When you set the useSlice:False, then the provideroptioncontract is not able to handle greeks. Following error is an example:
Runtime Error: 'ProviderOptionContract' object has no attribute 'greeks'
at delta
return contract.greeks.delta
^^^^^^^^^^^^^^^
in ContractUtils.py: line 200
at
log_message += f"Delta: {[round(self.contractUtils.delta(c), 2) for c in contracts]}"
^^^^^^^^^^^^^^^^^^^^^^^^^^^
in LimitOrderHandlerWithCombo.py: line 278
at logOrderExecution
log_message += f"Delta: {[round(self.contractUtils.delta(c), 2) for c in contracts]}"
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
in LimitOrderHandlerWithCombo.py: line 278
at makeLimitOrder
self.logOrderExecution(position, order, newLimitPrice)
in LimitOrderHandlerWithCombo.py: line 128
at call
self.makeLimitOrder(position, order)
in LimitOrderHandlerWithCombo.py: line 73
at Execute
self.limitOrderHandler.call(position, order)
in Base.py: line 99 (Open Stack Trace)

Fix live error on optionChainProviderFilter code

This error showed a couple of times but did not break the overall flow it just restarted the algo.

Runtime Error: Trying to dynamically access a method that does not exist throws a TypeError exception. To prevent the exception, ensure each parameter type matches those required by the 'QuantConnect.Symbol'>) method. Please checkout the API documentation. at optionChainProviderFilter contract = OptionContract(symbol, symbol.Underlying) 

^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 
in DataHandler.py: line 113 at getOptionContracts contracts = self.optionChainProviderFilter(symbols, -self.strategy.nStrikesLeft, self.strategy.nStrikesRight, minDte, maxDte) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 
in DataHandler.py: line 159 at Call chain = self.base.dataHandler.getOptionContracts(data) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 
in Scanner.py: line 34 at update filteredChain, lastClosedOrderTag = Scanner(self.context, self).Call(data) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 
in Base.py: line 227 Stack Trace: Trying to dynamically access a method that does not exist throws a TypeError exception. To prevent the exception, ensure each parameter type matches those required by the 'QuantConnect.Symbol'>) method. Please checkout the API documentation. at optionChainProviderFilter contract = OptionContract(symbol, symbol.Underlying) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 
in DataHandler.py: line 113 at getOptionContracts contracts = self.optionChainProviderFilter(symbols, -self.strategy.nStrikesLeft, self.strategy.nStrikesRight, minDte, maxDte) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 
in DataHandler.py: line 159 at Call chain = self.base.dataHandler.getOptionContracts(data) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 
in Scanner.py: line 34 at update filteredChain, lastClosedOrderTag = Scanner(self.context, self).Call(data) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 
in Base.py: line 227

Implement the usage of OptionsChain to filter by greeks in DataHandler

Example of the new feature added by Lean/QC team and algo using it:

class OptionChainFullDataRegressionAlgorithm(QCAlgorithm):

    def initialize(self):
        self.set_start_date(2015, 12, 24)
        self.set_end_date(2015, 12, 24)
        self.set_cash(100000)

        goog = self.add_equity("GOOG").symbol

        # Get contracts expiring within 10 days, with an implied volatility greater than 0.5 and a delta less than 0.5
        contracts = [
            contract_data
            for contract_data in self.option_chain(goog)
            if contract_data.id.date - self.time <= timedelta(days=10) and contract_data.implied_volatility > 0.5 and contract_data.greeks.delta < 0.5
        ]
        # Get the contract with the latest expiration date
        self._option_contract = sorted(contracts, key=lambda x: x.id.date, reverse=True)[0]

        self.add_option_contract(self._option_contract)

    def on_data(self, data):
        # Do some trading with the selected contract for sample purposes
        if not self.portfolio.invested:
            self.market_order(self._option_contract, 1)
        else:
            self.liquidate()

Store the working orders and all positions into QC storage

This should help us fix this error:

Runtime Error:

During the algorithm initialization, the following exception has occurred: Error getting open orders from brokerage: An existing position or open order for an unsupported security type was found: 0 . Please manually close the position or cancel the order before restarting the algorithm.An existing position or open order for an unsupported security type was found: 0 . Please manually close the position or cancel the order before restarting the algorithm. in BrokerageSetupHandler.cs:line 476 An existing position or open order for an unsupported security type was found: 0 . Please manually close the position or cancel the order before restarting the algorithm.

0DTE Expiry showing up although it doesn't fall into the dte:dtewindow

Example 28-34 dte returns the following expiry dates on 1st of August 2024:

DEBUG -> Scanner.Call: Expiry List: {datetime.date(2024, 8, 1): [datetime.datetime(2024, 9, 4, 0, 0), datetime.datetime(2024, 9, 3, 0, 0), datetime.datetime(2024, 8, 30, 0, 0), datetime.datetime(2024, 8, 29, 0, 0), datetime.datetime(2024, 8, 28, 0, 0)]}

underlyingPriceAtClose wasn't so there must be a little bug

I didn't investigate but the underlyingPriceAtOpen was returning underlyingprice and underlyingPriceAtClose wasn't so there must be a little bug, I noticed this when I was trying to get the price in the assignment function handleassignment through the assignedPosition

Add min_strike, max_strike and use the OptionsProvider to filter the options instead of option chain and universe

Add min_call_strike, max_call_strike, min_put_strike, max_put_strike to Alpha for filtering and update the DataHandler to use the optionChainProviderFilter method directly instead of going through the chain and universe as it does now using the getOptionContracts method.

Any approach to using this should be taken to Scanner.py as that is what is caling the getOptionContracts method.

Fix the issue of live algo restart after checkOpenPositions

Some of the logs have been added already that would result in a solution for this but so far this has not been solved.
The issue seems to happen later in the day on SPXic strat.

Here are the logs:

2024-06-12 20:05:00 DEBUG -> SPXExecutionModel.Execute: SPXExecutionModel -> Execute -> checkOpenPositions 2024-06-12 20:05:01 Runtime Error: (datetime.date(2024, 6, 12),) 2024-06-12 20:05:01 Runtime Error: (datetime.date(2024, 6, 12),): StackTrace: (datetime.date(2024, 6, 12),) 2024-06-12 20:04:54 DEBUG -> SPXExecutionModel.Execute: SPXExecutionModel -> Execute -> checkOpenPositions 2024-06-12 20:05:00 DEBUG -> SPXic.update: SPXic -> update -> start 2024-06-12 20:05:00 DEBUG -> SPXic.update: Is Warming Up: False 2024-06-12 20:05:00 DEBUG -> SPXic.update: Is Market Open: True 2024-06-12 20:05:00 DEBUG -> SPXic.update: Time: 16:05:00.800799 2024-06-12 20:05:00 DEBUG -> CentralAlgorithm.ManageRisk: SPXicMonitor -> ManageRisk -> start 2024-06-12 20:05:00 DEBUG -> CentralAlgorithm.ManageRisk: SPXicMonitor -> ManageRisk -> preManageRisk 2024-06-12 20:05:00 DEBUG -> SPXExecutionModel.Execute: SPXExecutionModel -> Execute -> targets: QuantConnect.Algorithm.Framework.Portfolio.IPortfolioTarget[] 2024-06-12 20:05:00 DEBUG -> SPXExecutionModel.Execute: SPXExecutionModel -> Execute -> targets count: 0 2024-06-12 20:05:00 DEBUG -> SPXExecutionModel.Execute: SPXExecutionModel -> Execute -> workingOrders: {} 2024-06-12 20:05:00 DEBUG -> SPXExecutionModel.Execute: SPXExecutionModel -> Execute -> allPositions: {1: Position(orderId=1, orderTag='CallCreditSpread-1', strategy=, strategyTag='SPXic', strategyId='CallCreditSpread', expiryStr='2024-06-12', expiry=datetime.datetime(2024, 6, 12, 0, 0), linkedOrderTag=None, targetPremium=None, orderQuantity=10, maxOrderQuantity=10, targetProfit=None, legs=[Leg(key='shortCall', expiry=datetime.datetime(2024, 6, 12, 16, 0), contractSide=-1, symbol=, quantity=0, strike=5475.0, contract=), Leg(key='longCall', expiry=datetime.datetime(2024, 6, 12, 16, 0), contractSide=1, symbol=, quantity=0, strike=5485.0, contract=)], contractSide={: -1, : 1}, openOrder=OrderType(premium=0.0, fills=0, limitOrderExpiryDttm=datetime.datetime(2024, 6, 12, 12, 35, 0, 800952), limitOrderPrice=1.0, bidAskSpread=0.1499999999999999, midPrice=0.8750000000000001, midPriceMin=0.0, midPriceMax=1.0000000000000004, limitPrice=0.0, fillPrice=0.0, openPremium=0.0, stalePrice=False, filled=False, maxLoss=-10.0, transactionIds=[41, 42], priceProgressList=[0.92, 0.92, 0.92, 0.92, 1.0, 1.0, 0.98, 0.98, 0.9, 0.9, 0.88]), closeOrder=OrderType(premium=0.0, fills=0, limitOrderExpiryDttm='', limitOrderPrice=0.0, bidAskSpread=0.0, midPrice=0.0, midPriceMin=0.0, midPriceMax=0.0, limitPrice=0.0, fillPrice=0.0, openPremium=0.0, stalePrice=False, filled=False, maxLoss=0.0, transactionIds=[], priceProgressList=[]), openDttm=datetime.datetime(2024, 6, 12, 12, 30, 0, 800952), openDt='2024-06-12', openDTE=0, openOrderMidPrice=0.93, openOrderMidPriceMin=0.93, openOrderMidPriceMax=0.93, openOrderBidAskSpread=0.15000000000000013, openOrderLimitPrice=1.0, openPremium=0.0, underlyingPriceAtOpen=5432.11, openFilledDttm=0.0, openStalePrice=False, orderMidPrice=0.0, limitOrderPrice=0.0, bidAskSpread=0.0, positionPnL=0.0, closeDttm='', closeDt='', closeDTE=nan, closeOrderMidPrice=0.0, closeOrderMidPriceMin=0.0, closeOrderMidPriceMax=0.0, closeOrderBidAskSpread=nan, closeOrderLimitPrice=0.0, closePremium=0.0, underlyingPriceAtClose=nan, underlyingPriceAtOrderClose=nan, DIT=0, closeStalePrice=False, closeReason=[], PnL=0.0, PnLMin=0.0, PnLMax=0.0, PnLMinDIT=0.0, PnLMaxDIT=0.0, orderCancelled=True, filled=False, limitOrder=True, priceProgressList=[]), 2: Position(orderId=2, orderTag='PutCreditSpread-2', strategy=, strategyTag='SPXic', strategyId='PutCreditSpread', expiryStr='2024-06-12', expiry=datetime.datetime(2024, 6, 12, 0, 0), linkedOrderTag=None, targetPremium=None, orderQuantity=10, maxOrderQuantity=10, targetProfit=None, legs=[Leg(key='shortPut', expiry=datetime.datetime(2024, 6, 12, 16, 0), contractSide=-1, symbol=, quantity=0, strike=5385.0, contract=), Leg(key='longPut', expiry=datetime.datetime(2024, 6, 12, 16, 0), contractSide=1, symbol=, quantity=0, strike=5375.0, contract=)], contractSide={: -1, : 1}, openOrder=OrderType(premium=0.0, fills=0, limitOrderExpiryDttm=datetime.datetime(2024, 6, 12, 12, 35, 0, 800952), limitOrderPrice=1.0, bidAskSpread=0.15000000000000036, midPrice=1.0250000000000004, midPriceMin=0.0, midPriceMax=1.0750000000000002, limitPrice=0.0, fillPrice=0.0, openPremium=0.0, stalePrice=False, filled=False, maxLoss=-10.0, transactionIds=[43, 44], priceProgressList=[1.08, 1.08, 1.05, 1.05, 1.0, 1.0, 1.0, 1.0, 1.08, 1.08, 1.03]), closeOrder=OrderType(premium=0.0, fills=0, limitOrderExpiryDttm='', limitOrderPrice=0.0, bidAskSpread=0.0, midPrice=0.0, midPriceMin=0.0, midPriceMax=0.0, limitPrice=0.0, fillPrice=0.0, openPremium=0.0, stalePrice=False, filled=False, maxLoss=0.0, transactionIds=[], priceProgressList=[]), openDttm=datetime.datetime(2024, 6, 12, 12, 30, 0, 800952), openDt='2024-06-12', openDTE=0, openOrderMidPrice=1.08, openOrderMidPriceMin=1.08, openOrderMidPriceMax=1.08, openOrderBidAskSpread=0.15000000000000036, openOrderLimitPrice=1.0, openPremium=0.0, underlyingPriceAtOpen=5432.11, openFilledDttm=0.0, openStalePrice=False, orderMidPrice=0.0, limitOrderPrice=0.0, bidAskSpread=0.0, positionPnL=0.0, closeDttm='', closeDt='', closeDTE=nan, closeOrderMidPrice=0.0, closeOrderMidPriceMin=0.0, closeOrderMidPriceMax=0.0, closeOrderBidAskSpread=nan, closeOrderLimitPrice=0.0, closePremium=0.0, underlyingPriceAtClose=nan, underlyingPriceAtOrderClose=nan, DIT=0, closeStalePrice=False, closeReason=[], PnL=0.0, PnLMin=0.0, PnLMax=0.0, PnLMinDIT=0.0, PnLMaxDIT=0.0, orderCancelled=True, filled=False, limitOrder=True, priceProgressList=[]), 3: Position(orderId=3, orderTag='CallCreditSpread-3', strategy=, strategyTag='SPXic', strategyId='CallCreditSpread', expiryStr='2024-06-12', expiry=datetime.datetime(2024, 6, 12, 0, 0), linkedOrderTag=None, targetPremium=None, orderQuantity=10, maxOrderQuantity=10, targetProfit=None, legs=[Leg(key='shortCall', expiry=datetime.datetime(2024, 6, 12, 16, 0), contractSide=-1, symbol=, quantity=0, strike=5470.0, contract=), Leg(key='longCall', expiry=datetime.datetime(2024, 6, 12, 16, 0), contractSide=1, symbol=, quantity=0, strike=5480.0, contract=)], contractSide={: -1, : 1}, openOrder=OrderType(premium=0.0, fills=0, limitOrderExpiryDttm=datetime.datetime(2024, 6, 12, 13, 35, 0, 800753), limitOrderPrice=1.0, bidAskSpread=0.15000000000000013, midPrice=1.1250000000000004, midPriceMin=0.0, midPriceMax=1.175, limitPrice=0.0, fillPrice=0.0, openPremium=0.0, stalePrice=False, filled=False, maxLoss=-10.0, transactionIds=[85, 86], priceProgressList=[1.18, 1.18, 1.12, 1.12, 1.03, 1.03, 1.02, 1.02, 1.08, 1.08, 1.13]), closeOrder=OrderType(premium=0.0, fills=0, limitOrderExpiryDttm='', limitOrderPrice=0.0, bidAskSpread=0.0, midPrice=0.0, midPriceMin=0.0, midPriceMax=0.0, limitPrice=0.0, fillPrice=0.0, openPremium=0.0, stalePrice=False, filled=False, maxLoss=0.0, transactionIds=[], priceProgressList=[]), openDttm=datetime.datetime(2024, 6, 12, 13, 30, 0, 800753), openDt='2024-06-12', openDTE=0, openOrderMidPrice=1.18, openOrderMidPriceMin=1.18, openOrderMidPriceMax=1.18, openOrderBidAskSpread=0.1499999999999999, openOrderLimitPrice=1.0, openPremium=0.0, underlyingPriceAtOpen=5432.33, openFilledDttm=0.0, openStalePrice=False, orderMidPrice=0.0, limitOrderPrice=0.0, bidAskSpread=0.0, positionPnL=0.0, closeDttm='', closeDt='', closeDTE=nan, closeOrderMidPrice=0.0, closeOrderMidPriceMin=0.0, closeOrderMidPriceMax=0.0, closeOrderBidAskSpread=nan, closeOrderLimitPrice=0.0, closePremium=0.0, underlyingPriceAtClose=nan, underlyingPriceAtOrderClose=nan, DIT=0, closeStalePrice=False, closeReason=[], PnL=0.0, PnLMin=0.0, PnLMax=0.0, PnLMinDIT=0.0, PnLMaxDIT=0.0, orderCancelled=True, filled=False, limitOrder=True, priceProgressList=[]), 4: Position(orderId=4, orderTag='PutCreditSpread-4', strategy=, strategyTag='SPXic', strategyId='PutCreditSpread', expiryStr='2024-06-12', expiry=datetime.datetime(2024, 6, 12, 0, 0), linkedOrderTag=None, targetPremium=None, orderQuantity=10, maxOrderQuantity=10, targetProfit=None, legs=[Leg(key='shortPut', expiry=datetime.datetime(2024, 6, 12, 16, 0), contractSide=-1, symbol=, quantity=0, strike=5390.0, contract= SPXExecutionModel.Execute: SPXExecutionModel -> Execute -> checkOpenPositions 2024-06-12 20:05:01 Runtime Error: (datetime.date(2024, 6, 12),) 2024-06-12 20:05:01 Runtime Error: (datetime.date(2024, 6, 12),): StackTrace: (datetime.date(2024, 6, 12),) 2024-06-12 20:08:51 Launching analysis for L-b9ccfdacb5c0d0e9b7361caa24c37f1b with LEAN Engine v2.5.0.0.16478 2024-06-12 20:08:56 Interactive Brokers Brokerage account base currency: USD 2024-06-12 20:08:56 Will use UniverseSettings for automatically added securities for open orders and holdings. UniverseSettings: Resolution = Minute; Leverage = default; FillForward = True; ExtendedHours = False 2024-06-12 20:08:56 DEBUG -> CentralAlgorithm.Setup: SetupBaseStructure -> Setup 2024-06-12 20:08:56 DEBUG -> SPXic.__init__: SPXic -> __init__ 2024-06-12 20:08:56 DEBUG -> CentralAlgorithm.AddUnderlying: SetupBaseStructure -> AddUnderlying -> Ticker: SPX 2024-06-12 20:08:56 DEBUG -> CentralAlgorithm.CompleteSecurityInitializer: SetupBaseStructure -> CompleteSecurityInitializer -> Security: SPX 2024-06-12 20:08:56 DEBUG -> CentralAlgorithm.CompleteSecurityInitializer: SetupBaseStructure -> CompleteSecurityInitializer -> Security: ?SPXW 2024-06-12 20:08:56 DEBUG -> CentralAlgorithm.AddUnderlying: SetupBaseStructure -> AddUnderlying -> Underlying: SPX 2024-06-12 20:08:56 DEBUG -> CentralAlgorithm.AddUnderlying: SetupBaseStructure -> AddUnderlying -> Option: ?SPXW 2024-06-12 20:08:56 DEBUG -> CentralAlgorithm.AddUnderlying: SetupBaseStructure -> AddUnderlying -> Benchmark: QuantConnect.Benchmarks.SecurityBenchmark 2024-06-12 20:08:56 DEBUG -> SPXic.__init__: SPXic -> __init__ -> AddUnderlying 2024-06-12 20:08:56 DEBUG -> CentralAlgorithm.__init__: OptionsPortfolioConstruction -> __init__ 2024-06-12 20:08:56 DEBUG -> SPXExecutionModel.__init__: SPXExecutionModel -> __init__ 2024-06-12 20:08:56 DEBUG -> CentralAlgorithm.__init__: SPXicMonitor -> __init__ ```

This is the runtime error message:

2024-06-12 20:05:00  DEBUG -> SPXExecutionModel.Execute: SPXExecutionModel -> Execute -> checkOpenPositions
2024-06-12 20:05:01 Runtime Error: (datetime.date(2024, 6, 12),)
2024-06-12 20:05:01 Runtime Error: (datetime.date(2024, 6, 12),): StackTrace: (datetime.date(2024, 6, 12),)

Issue with ComboLimitOrder execution

There is an issue with the ComboLimitOrder execution on the lean framework. It seems that it does not respect the limit price so i had to change the code in LimitOrderHandler.py to use ComboLegLimitOrder.
The problem with using this approach is that when i have to update the price of each individual legs and make adjusts based on that and also i have to cancel the order and submit it again to make sure that as i update one of the leg prices the execution does not happen at a bad price.

Here is what i found on the forum mentioning that the best option is to use ComboLegLimitOrder as the others are wrappers around MarketOrders: https://www.quantconnect.com/forum/discussion/14896/limit-orders-on-multi-leg-option-strategies-best-method/

Add implied_volatility and delta and greeks to provideroptioncontract

example error

Runtime Error: 'ProviderOptionContract' object has no attribute 'implied_volatility'
at getSpread
iv_short_leg = sorted_contracts[i].implied_volatility
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
in OrderBuilder.py: line 387
at getSpreadOrder
legs = self.strategyBuilder.getSpread(contracts, type, strike = strike, delta = delta, wingSize = wingSize, fromPrice = fromPrice, toPrice = toPrice, premiumOrder = premiumOrder)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
in Order.py: line 688
at getOrder
call = self.order.getSpreadOrder(
^^^^^^^^^^^^^^^^^^^^^^^^^^
in SPXic.py: line 82
at CreateInsights
order = self.getOrder(chain, data)
^^^^^^^^^^^^^^^^^^^^^^^^^^
in Base.py: line 317
at update
insights = self.CreateInsights(filteredChain, lastClosedOrderTag, data)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
in Base.py: line 284

Add a mechanism that checks for existing contracts

Right now the code does not check for existing contracts/positions so you could open multiple same day positions with the same contract and break the whole strategy.

In alpha/base.py have a parameter defined that by default checks for existing positions and if any new order is tried for the same contract it should not be placed if it breaks existing positions.

Should be simple enough to add.

At end of day export the trades to the system cache to clear memory

There is a posibility of running out of memory so we should save the self.context.allPositions into cache at the end of day. All the other arrays should clear out as the algo runs.

We should also just save the positions that are closed in there.

Same thing we should do for Performance logic data.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.