Source code for robin_stocks.robinhood.options

"""Contains functions for getting information about options."""
import sys
from robin_stocks.robinhood.helper import *
from robin_stocks.robinhood.urls import *

[docs]def spinning_cursor(): """ This is a generator function to yield a character. """ while True: for cursor in '|/-\\': yield cursor
spinner = spinning_cursor()
[docs]def write_spinner(): """ Function to create a spinning cursor to tell user that the code is working on getting market data. """ if get_output()==sys.stdout: marketString = 'Loading Market Data ' sys.stdout.write(marketString) sys.stdout.write(next(spinner)) sys.stdout.flush() sys.stdout.write('\b'*(len(marketString)+1))
[docs]@login_required def get_aggregate_positions(info=None): """Collapses all option orders for a stock into a single dictionary. :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a list of dictionaries of key/value pairs for each order. If info parameter is provided, \ a list of strings is returned where the strings are the value of the key that matches info. """ url = aggregate_url() data = request_get(url, 'pagination') return(filter_data(data, info))
[docs]@login_required def get_aggregate_open_positions(info=None): """Collapses all open option positions for a stock into a single dictionary. :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a list of dictionaries of key/value pairs for each order. If info parameter is provided, \ a list of strings is returned where the strings are the value of the key that matches info. """ url = aggregate_url() payload = {'nonzero': 'True'} data = request_get(url, 'pagination', payload) return(filter_data(data, info))
[docs]@login_required def get_market_options(info=None): """Returns a list of all options. :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a list of dictionaries of key/value pairs for each option. If info parameter is provided, \ a list of strings is returned where the strings are the value of the key that matches info. """ url = option_orders_url() data = request_get(url, 'pagination') return(filter_data(data, info))
[docs]@login_required def get_all_option_positions(info=None): """Returns all option positions ever held for the account. :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a list of dictionaries of key/value pairs for each option. If info parameter is provided, \ a list of strings is returned where the strings are the value of the key that matches info. """ url = option_positions_url() data = request_get(url, 'pagination') return(filter_data(data, info))
[docs]@login_required def get_open_option_positions(account_number=None, info=None): """Returns all open option positions for the account. :param acccount_number: the robinhood account number. :type acccount_number: Optional[str] :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a list of dictionaries of key/value pairs for each option. If info parameter is provided, \ a list of strings is returned where the strings are the value of the key that matches info. """ url = option_positions_url(account_number=account_number) payload = {'nonzero': 'True'} data = request_get(url, 'pagination', payload) return(filter_data(data, info))
[docs]def get_chains(symbol, info=None): """Returns the chain information of an option. :param symbol: The ticker of the stock. :type symbol: str :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a dictionary of key/value pairs for the option. If info parameter is provided, \ a list of strings is returned where the strings are the value of the key that matches info. """ try: symbol = symbol.upper().strip() except AttributeError as message: print(message, file=get_output()) return None url = chains_url(symbol) data = request_get(url) return(filter_data(data, info))
[docs]@login_required def find_tradable_options(symbol, expirationDate=None, strikePrice=None, optionType=None, info=None): """Returns a list of all available options for a stock. :param symbol: The ticker of the stock. :type symbol: str :param expirationDate: Represents the expiration date in the format YYYY-MM-DD. :type expirationDate: str :param strikePrice: Represents the strike price of the option. :type strikePrice: str :param optionType: Can be either 'call' or 'put' or left blank to get both. :type optionType: Optional[str] :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a list of dictionaries of key/value pairs for all calls of the stock. If info parameter is provided, \ a list of strings is returned where the strings are the value of the key that matches info. """ try: symbol = symbol.upper().strip() except AttributeError as message: print(message, file=get_output()) return [None] url = option_instruments_url() if not id_for_chain(symbol): print("Symbol {} is not valid for finding options.".format(symbol), file=get_output()) return [None] payload = {'chain_id': id_for_chain(symbol), 'chain_symbol': symbol, 'state': 'active'} if expirationDate: payload['expiration_dates'] = expirationDate if strikePrice: payload['strike_price'] = strikePrice if optionType: payload['type'] = optionType data = request_get(url, 'pagination', payload) return(filter_data(data, info))
[docs]@login_required def find_options_by_expiration(inputSymbols, expirationDate, optionType=None, info=None): """Returns a list of all the option orders that match the seach parameters :param inputSymbols: The ticker of either a single stock or a list of stocks. :type inputSymbols: str :param expirationDate: Represents the expiration date in the format YYYY-MM-DD. :type expirationDate: str :param optionType: Can be either 'call' or 'put' or leave blank to get both. :type optionType: Optional[str] :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a list of dictionaries of key/value pairs for all options of the stock that match the search parameters. \ If info parameter is provided, a list of strings is returned where the strings are the value of the key that matches info. """ try: symbols = inputs_to_set(inputSymbols) if optionType: optionType = optionType.lower().strip() except AttributeError as message: print(message, file=get_output()) return [None] data = [] for symbol in symbols: allOptions = find_tradable_options(symbol, expirationDate, None, optionType, None) filteredOptions = [item for item in allOptions if item.get("expiration_date") == expirationDate] for item in filteredOptions: marketData = get_option_market_data_by_id(item['id']) if marketData: item.update(marketData[0]) write_spinner() data.extend(filteredOptions) return(filter_data(data, info))
[docs]@login_required def find_options_by_strike(inputSymbols, strikePrice, optionType=None, info=None): """Returns a list of all the option orders that match the seach parameters :param inputSymbols: The ticker of either a single stock or a list of stocks. :type inputSymbols: str :param strikePrice: Represents the strike price to filter for. :type strikePrice: str :param optionType: Can be either 'call' or 'put' or leave blank to get both. :type optionType: Optional[str] :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a list of dictionaries of key/value pairs for all options of the stock that match the search parameters. \ If info parameter is provided, a list of strings is returned where the strings are the value of the key that matches info. """ try: symbols = inputs_to_set(inputSymbols) if optionType: optionType = optionType.lower().strip() except AttributeError as message: print(message, file=get_output()) return [None] data = [] for symbol in symbols: filteredOptions = find_tradable_options(symbol, None, strikePrice, optionType, None) for item in filteredOptions: marketData = get_option_market_data_by_id(item['id']) if marketData: item.update(marketData[0]) write_spinner() data.extend(filteredOptions) return(filter_data(data, info))
[docs]@login_required def find_options_by_expiration_and_strike(inputSymbols, expirationDate, strikePrice, optionType=None, info=None): """Returns a list of all the option orders that match the seach parameters :param inputSymbols: The ticker of either a single stock or a list of stocks. :type inputSymbols: str :param expirationDate: Represents the expiration date in the format YYYY-MM-DD. :type expirationDate: str :param strikePrice: Represents the strike price to filter for. :type strikePrice: str :param optionType: Can be either 'call' or 'put' or leave blank to get both. :type optionType: Optional[str] :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a list of dictionaries of key/value pairs for all options of the stock that match the search parameters. \ If info parameter is provided, a list of strings is returned where the strings are the value of the key that matches info. """ try: symbols = inputs_to_set(inputSymbols) if optionType: optionType = optionType.lower().strip() except AttributeError as message: print(message, file=get_output()) return [None] data = [] for symbol in symbols: allOptions = find_tradable_options(symbol, expirationDate, strikePrice, optionType, None) filteredOptions = [item for item in allOptions if item.get("expiration_date") == expirationDate] for item in filteredOptions: marketData = get_option_market_data_by_id(item['id']) if marketData: item.update(marketData[0]) write_spinner() data.extend(filteredOptions) return filter_data(data, info)
[docs]@login_required def find_options_by_specific_profitability(inputSymbols, expirationDate=None, strikePrice=None, optionType=None, typeProfit="chance_of_profit_short", profitFloor=0.0, profitCeiling=1.0, info=None): """Returns a list of option market data for several stock tickers that match a range of profitability. :param inputSymbols: May be a single stock ticker or a list of stock tickers. :type inputSymbols: str or list :param expirationDate: Represents the expiration date in the format YYYY-MM-DD. Leave as None to get all available dates. :type expirationDate: str :param strikePrice: Represents the price of the option. Leave as None to get all available strike prices. :type strikePrice: str :param optionType: Can be either 'call' or 'put' or leave blank to get both. :type optionType: Optional[str] :param typeProfit: Will either be "chance_of_profit_short" or "chance_of_profit_long". :type typeProfit: str :param profitFloor: The lower percentage on scale 0 to 1. :type profitFloor: int :param profitCeiling: The higher percentage on scale 0 to 1. :type profitCeiling: int :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a list of dictionaries of key/value pairs for all stock option market data. \ If info parameter is provided, a list of strings is returned where the strings are the value of the key that matches info. """ symbols = inputs_to_set(inputSymbols) data = [] if (typeProfit != "chance_of_profit_short" and typeProfit != "chance_of_profit_long"): print("Invalid string for 'typeProfit'. Defaulting to 'chance_of_profit_short'.", file=get_output()) typeProfit = "chance_of_profit_short" for symbol in symbols: tempData = find_tradable_options(symbol, expirationDate, strikePrice, optionType, info=None) for option in tempData: if expirationDate and option.get("expiration_date") != expirationDate: continue market_data = get_option_market_data_by_id(option['id']) if len(market_data): option.update(market_data[0]) write_spinner() try: floatValue = float(option[typeProfit]) if (floatValue >= profitFloor and floatValue <= profitCeiling): data.append(option) except: pass return(filter_data(data, info))
[docs]@login_required def get_option_market_data_by_id(id, info=None): """Returns the option market data for a stock, including the greeks, open interest, change of profit, and adjusted mark price. :param id: The id of the stock. :type id: str :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a dictionary of key/value pairs for the stock. \ If info parameter is provided, the value of the key that matches info is extracted. """ instrument = get_option_instrument_data_by_id(id) if instrument is None: # e.g. 503 Server Error: Service Unavailable for url: https://api.robinhood.com/options/instruments/d1058013-09a2-4063-b6b0-92717e17d0c0/ return None # just return None which the caller can easily check; do NOT use faked empty data, it will only cause future problem else: payload = { "instruments" : instrument['url'] } url = marketdata_options_url() data = request_get(url, 'results', payload) return(filter_data(data, info))
[docs]@login_required def get_option_market_data(inputSymbols, expirationDate, strikePrice, optionType, info=None): """Returns the option market data for the stock option, including the greeks, open interest, change of profit, and adjusted mark price. :param inputSymbols: The ticker of the stock. :type inputSymbols: str :param expirationDate: Represents the expiration date in the format YYYY-MM-DD. :type expirationDate: str :param strikePrice: Represents the price of the option. :type strikePrice: str :param optionType: Can be either 'call' or 'put'. :type optionType: str :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a dictionary of key/value pairs for the stock. \ If info parameter is provided, the value of the key that matches info is extracted. """ try: symbols = inputs_to_set(inputSymbols) if optionType: optionType = optionType.lower().strip() except AttributeError as message: print(message, file=get_output()) return [None] data = [] for symbol in symbols: optionID = id_for_option(symbol, expirationDate, strikePrice, optionType) marketData = get_option_market_data_by_id(optionID) data.append(marketData) return(filter_data(data, info))
[docs]def get_option_instrument_data_by_id(id, info=None): """Returns the option instrument information. :param id: The id of the stock. :type id: str :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a dictionary of key/value pairs for the stock. \ If info parameter is provided, the value of the key that matches info is extracted. """ url = option_instruments_url(id) data = request_get(url) return(filter_data(data, info))
[docs]def get_option_instrument_data(symbol, expirationDate, strikePrice, optionType, info=None): """Returns the option instrument data for the stock option. :param symbol: The ticker of the stock. :type symbol: str :param expirationDate: Represents the expiration date in the format YYYY-MM-DD. :type expirationDate: str :param strikePrice: Represents the price of the option. :type strikePrice: str :param optionType: Can be either 'call' or 'put'. :type optionType: str :param info: Will filter the results to get a specific value. :type info: Optional[str] :returns: Returns a dictionary of key/value pairs for the stock. \ If info parameter is provided, the value of the key that matches info is extracted. """ try: symbol = symbol.upper().strip() optionType = optionType.lower().strip() except AttributeError as message: print(message, file=get_output()) return [None] optionID = id_for_option(symbol, expirationDate, strikePrice, optionType) url = option_instruments_url(optionID) data = request_get(url) return(filter_data(data, info))
[docs]def get_option_historicals(symbol, expirationDate, strikePrice, optionType, interval='hour', span='week', bounds='regular', info=None): """Returns the data that is used to make the graphs. :param symbol: The ticker of the stock. :type symbol: str :param expirationDate: Represents the expiration date in the format YYYY-MM-DD. :type expirationDate: str :param strikePrice: Represents the price of the option. :type strikePrice: str :param optionType: Can be either 'call' or 'put'. :type optionType: str :param interval: Interval to retrieve data for. Values are '5minute', '10minute', 'hour', 'day', 'week'. Default is 'hour'. :type interval: Optional[str] :param span: Sets the range of the data to be either 'day', 'week', 'year', or '5year'. Default is 'week'. :type span: Optional[str] :param bounds: Represents if graph will include extended trading hours or just regular trading hours. Values are 'regular', 'trading', and 'extended'. \ regular hours are 6 hours long, trading hours are 9 hours long, and extended hours are 16 hours long. Default is 'regular' :type bounds: Optional[str] :param info: Will filter the results to have a list of the values that correspond to key that matches info. :type info: Optional[str] :returns: Returns a list that contains a list for each symbol. \ Each list contains a dictionary where each dictionary is for a different time. """ try: symbol = symbol.upper().strip() optionType = optionType.lower().strip() except AttributeError as message: print(message, file=get_output()) return [None] interval_check = ['5minute', '10minute', 'hour', 'day', 'week'] span_check = ['day', 'week', 'year', '5year'] bounds_check = ['extended', 'regular', 'trading'] if interval not in interval_check: print( 'ERROR: Interval must be "5minute","10minute","hour","day",or "week"', file=get_output()) return([None]) if span not in span_check: print('ERROR: Span must be "day", "week", "year", or "5year"', file=get_output()) return([None]) if bounds not in bounds_check: print('ERROR: Bounds must be "extended","regular",or "trading"', file=get_output()) return([None]) optionID = id_for_option(symbol, expirationDate, strikePrice, optionType) url = option_historicals_url(optionID) payload = {'span': span, 'interval': interval, 'bounds': bounds} data = request_get(url, 'regular', payload) if (data == None or data == [None]): return data histData = [] for subitem in data['data_points']: subitem['symbol'] = symbol histData.append(subitem) return(filter_data(histData, info))