Python access to structure stock market information
Project description
invest
Python access to structure stock market information
To install: pip install invest
- invest
- Quick Start
- Configuring Ticker objects
- Getting (only) specific information about tickers
- Notes
Table of contents generated with markdown-toc
Quick Start
from invest import Tickers
Get a default list of tickers
tickers = Tickers()
tickers is a dict-like container of tickers. So you can do dict-like things with it, like...
- ask for it's length
len(tickers)
4039
- list the keys
list(tickers)[:5]
['EGLE', 'KMPH', 'LONG', 'CYBR', 'PTC']
- check for containment of a key
'GOOG' in tickers
True
The values of this dict-like object are Ticker instances.
ticker = tickers['GOOG']
ticker
Ticker('GOOG')
This ticker object is also dict-like. Let's see how many keys there are:
len(ticker)
40
What are these keys?
list(ticker)
['balancesheet',
'dividends',
'get_sustainability',
'get_info',
'get_institutional_holders',
'sustainability',
'quarterly_balance_sheet',
'get_balance_sheet',
'info',
'quarterly_earnings',
'isin',
'earnings',
'history',
'get_balancesheet',
'get_financials',
'balance_sheet',
'get_earnings',
'options',
'splits',
'get_recommendations',
'get_major_holders',
'get_dividends',
'actions',
'recommendations',
'cashflow',
'get_cashflow',
'get_splits',
'major_holders',
'institutional_holders',
'option_chain',
'get_actions',
'quarterly_financials',
'get_calendar',
'quarterly_cashflow',
'calendar',
'financials',
'quarterly_balancesheet',
'get_mutualfund_holders',
'get_isin',
'mutualfund_holders']
Let's look at one of these, 'info', which contains a dict with a bunch of information about the ticker...
info = ticker['info']
print(*info, sep=', ')
zip, sector, fullTimeEmployees, longBusinessSummary, city, phone, state, country, companyOfficers, website, maxAge, address1, industry, previousClose, regularMarketOpen, twoHundredDayAverage, trailingAnnualDividendYield, payoutRatio, volume24Hr, regularMarketDayHigh, navPrice, averageDailyVolume10Day, totalAssets, regularMarketPreviousClose, fiftyDayAverage, trailingAnnualDividendRate, open, toCurrency, averageVolume10days, expireDate, yield, algorithm, dividendRate, exDividendDate, beta, circulatingSupply, startDate, regularMarketDayLow, priceHint, currency, trailingPE, regularMarketVolume, lastMarket, maxSupply, openInterest, marketCap, volumeAllCurrencies, strikePrice, averageVolume, priceToSalesTrailing12Months, dayLow, ask, ytdReturn, askSize, volume, fiftyTwoWeekHigh, forwardPE, fromCurrency, fiveYearAvgDividendYield, fiftyTwoWeekLow, bid, tradeable, dividendYield, bidSize, dayHigh, exchange, shortName, longName, exchangeTimezoneName, exchangeTimezoneShortName, isEsgPopulated, gmtOffSetMilliseconds, quoteType, symbol, messageBoardId, market, annualHoldingsTurnover, enterpriseToRevenue, beta3Year, profitMargins, enterpriseToEbitda, 52WeekChange, morningStarRiskRating, forwardEps, revenueQuarterlyGrowth, sharesOutstanding, fundInceptionDate, annualReportExpenseRatio, bookValue, sharesShort, sharesPercentSharesOut, fundFamily, lastFiscalYearEnd, heldPercentInstitutions, netIncomeToCommon, trailingEps, lastDividendValue, SandP52WeekChange, priceToBook, heldPercentInsiders, nextFiscalYearEnd, mostRecentQuarter, shortRatio, sharesShortPreviousMonthDate, floatShares, enterpriseValue, threeYearAverageReturn, lastSplitDate, lastSplitFactor, legalType, lastDividendDate, morningStarOverallRating, earningsQuarterlyGrowth, dateShortInterest, pegRatio, lastCapGain, shortPercentOfFloat, sharesShortPriorMonth, category, fiveYearAverageReturn, regularMarketPrice, logo_url
info['shortName']
'Alphabet Inc.'
info['sector']
'Communication Services'
df = ticker['history']
df
.dataframe tbody tr th {
vertical-align: top;
}
.dataframe thead th {
text-align: right;
}
</style>
| Open | High | Low | Close | Volume | Dividends | Stock Splits | |
|---|---|---|---|---|---|---|---|
| Date | |||||||
| 2020-10-28 | 1559.739990 | 1561.349976 | 1514.619995 | 1516.619995 | 1834000 | 0 | 0 |
| 2020-10-29 | 1522.359985 | 1593.709961 | 1522.239990 | 1567.239990 | 2003100 | 0 | 0 |
| 2020-10-30 | 1672.109985 | 1687.000000 | 1604.459961 | 1621.010010 | 4329100 | 0 | 0 |
| 2020-11-02 | 1628.160034 | 1660.770020 | 1616.030029 | 1626.030029 | 2535400 | 0 | 0 |
| 2020-11-03 | 1631.780029 | 1661.699951 | 1616.619995 | 1650.209961 | 1661700 | 0 | 0 |
| 2020-11-04 | 1710.280029 | 1771.364990 | 1706.030029 | 1749.130005 | 3570900 | 0 | 0 |
| 2020-11-05 | 1781.000000 | 1793.640015 | 1750.510010 | 1763.369995 | 2065800 | 0 | 0 |
| 2020-11-06 | 1753.949951 | 1772.430054 | 1740.349976 | 1761.750000 | 1660900 | 0 | 0 |
| 2020-11-09 | 1790.900024 | 1818.060059 | 1760.020020 | 1763.000000 | 2268300 | 0 | 0 |
| 2020-11-10 | 1731.089966 | 1763.000000 | 1717.300049 | 1740.390015 | 2636100 | 0 | 0 |
| 2020-11-11 | 1750.000000 | 1764.219971 | 1747.364990 | 1752.709961 | 1264000 | 0 | 0 |
| 2020-11-12 | 1747.630005 | 1768.270020 | 1745.599976 | 1749.839966 | 1247500 | 0 | 0 |
| 2020-11-13 | 1757.630005 | 1781.040039 | 1744.550049 | 1777.020020 | 1499900 | 0 | 0 |
| 2020-11-16 | 1771.699951 | 1799.069946 | 1767.689941 | 1781.380005 | 1246800 | 0 | 0 |
| 2020-11-17 | 1776.939941 | 1785.000000 | 1767.000000 | 1770.150024 | 1147100 | 0 | 0 |
| 2020-11-18 | 1765.229980 | 1773.469971 | 1746.140015 | 1746.780029 | 1173500 | 0 | 0 |
| 2020-11-19 | 1738.380005 | 1769.589966 | 1737.005005 | 1763.920044 | 1249900 | 0 | 0 |
| 2020-11-20 | 1765.209961 | 1774.000000 | 1741.859985 | 1742.189941 | 2313500 | 0 | 0 |
| 2020-11-23 | 1749.599976 | 1753.900024 | 1717.719971 | 1734.859985 | 2161600 | 0 | 0 |
| 2020-11-24 | 1730.500000 | 1771.599976 | 1727.689941 | 1768.880005 | 1578000 | 0 | 0 |
| 2020-11-25 | 1772.890015 | 1778.540039 | 1756.540039 | 1771.430054 | 1045800 | 0 | 0 |
| 2020-11-27 | 1773.089966 | 1804.000000 | 1772.439941 | 1793.189941 | 884900 | 0 | 0 |
from mplfinance import plot as candlestick_plot # pip install mplfinance if you don't have it already
candlestick_plot(df)
But these are daily metrics and only for the recent (yes, I'm doing this on a Thanksgiving week-end!) past.
How do I get something different? Like a longer history, and/or at a finer time-granularity?
See the next Configuring Ticker objects section on how to do that.
ticker_symbols argument
The first argument of Tickers is the ticker_symbols argument.
One can specify a collection (list, set, tuple, etc.) of ticker symbol strings, or a path to a file containing a pickle of such a collection.
The default is the string 'local_list' which has the effect of using a default list (currently of about 4000 tickers), but it's contents can change in the future.
Note that this ticker_symbols will have an effect on such affairs as list(tickers), len(tickers), or s in tickers, when it's relevant to use these.
But any Tickers object will allow access to any ticker symbol, regardless if it's in the ticker_symbols collection or not.
tickers = Tickers(ticker_symbols=('GOOG', 'AAPL', 'AMZN'))
assert list(tickers) == ['GOOG', 'AAPL', 'AMZN']
assert len(tickers) == 3
assert 'AAPL' in tickers
assert 'NFLX' not in tickers
# and yet we have access to NFLX info
assert tickers['NFLX']['info']['shortName'] == 'Netflix, Inc.'
Notes
- Both
TickersandTickerinstances have tab-triggered auto-suggestion enabled when you get an item. Example:tickers['AA<now press the TAB button...>. - The specification of
Configuring Ticker objects
Configure a Ticker instance
You can instantiate a Ticker instance directly, from any valid ticker symbol. The Tickers class is just a way to make a collection of tickers to work with.
from invest import Tickers, Ticker
ticker = Ticker('GOOG')
ticker
Ticker('GOOG')
But you'll notice that Ticker (and Tickers) have more than one argument.
from inspect import signature
print(signature(Tickers))
print(signature(Ticker))
(ticker_symbols='local_list', **kwargs_for_method_keys)
(ticker_symbol: str, **kwargs_for_method_keys)
What's this kwargs_for_method_keys?
Well, at the time of writing this, Ticker object is just a convenient dict-like interface to the attributes of the Ticker of the yfinance package which is itself a convenient python interface to the yahoo finance API.
When you do list(ticker), you're just getting a list of attributes of yfinance.Ticker: Both properties and methods that don't require any arguments. Though these methods don't require any arguments -- meaning all their arguments have defaults -- you can still specify if you want to use different defaults.
That's where kwargs_for_method_keys comes in. It specifies what arg=val pairs that should be used for particular methods of yfinance.Ticker.
If you want to know more about what you can do with the Ticker object, you might want to check out yfinance's and yahoo finance API's documentation.
For the basics though, invest provides the help_me_with function (as a standalone function or as a method in Tickers and Ticker) for quick access to essentials.
Ticker.help_me_with('history')
history
wraps <function TickerBase.history at 0x11a064940>, whose signature is:
(self, period='1mo', interval='1d', start=None, end=None, prepost=False, actions=True, auto_adjust=True, back_adjust=False, proxy=None, rounding=False, tz=None, **kwargs)
:Parameters:
period : str
Valid periods: 1d,5d,1mo,3mo,6mo,1y,2y,5y,10y,ytd,max
Either Use period parameter or use start and end
interval : str
Valid intervals: 1m,2m,5m,15m,30m,60m,90m,1h,1d,5d,1wk,1mo,3mo
Intraday data cannot extend last 60 days
start: str
Download start date string (YYYY-MM-DD) or _datetime.
Default is 1900-01-01
end: str
Download end date string (YYYY-MM-DD) or _datetime.
Default is now
prepost : bool
Include Pre and Post market data in results?
Default is False
auto_adjust: bool
Adjust all OHLC automatically? Default is True
back_adjust: bool
Back-adjusted data to mimic true historical prices
proxy: str
Optional. Proxy server URL scheme. Default is None
rounding: bool
Round values to 2 decimal places?
Optional. Default is False = precision suggested by Yahoo!
tz: str
Optional timezone locale for dates.
(default data is returned as non-localized dates)
**kwargs: dict
debug: bool
Optional. If passed as False, will suppress
error message printing to console.
Example
Here's you can get history to give you something different.
Say, get data for the last day, with a granularity of 15 minutes.
ticker = Ticker('GOOG', history=dict(period='1d', interval='15m'))
ticker
Ticker('GOOG', history={'period': '1d', 'interval': '15m'})
Your ticker is almost identical to the previous one we made, or the one we got from Tickers, except for the fact that asking for ticker['history'] is going to give you something different.
df = ticker['history']
df
.dataframe tbody tr th {
vertical-align: top;
}
.dataframe thead th {
text-align: right;
}
</style>
| Open | High | Low | Close | Volume | Dividends | Stock Splits | |
|---|---|---|---|---|---|---|---|
| Datetime | |||||||
| 2020-11-27 09:30:00-05:00 | 1773.089966 | 1789.890015 | 1772.439941 | 1785.000000 | 119289 | 0 | 0 |
| 2020-11-27 09:45:00-05:00 | 1785.380005 | 1786.979980 | 1780.229980 | 1785.089966 | 50660 | 0 | 0 |
| 2020-11-27 10:00:00-05:00 | 1785.489990 | 1786.989990 | 1780.959961 | 1785.800049 | 50797 | 0 | 0 |
| 2020-11-27 10:15:00-05:00 | 1785.319946 | 1795.925049 | 1785.319946 | 1791.589966 | 72146 | 0 | 0 |
| 2020-11-27 10:30:00-05:00 | 1792.060059 | 1798.999878 | 1792.060059 | 1796.699951 | 48097 | 0 | 0 |
| 2020-11-27 10:45:00-05:00 | 1796.800049 | 1800.199951 | 1795.060059 | 1799.959961 | 56292 | 0 | 0 |
| 2020-11-27 11:00:00-05:00 | 1800.359985 | 1800.449951 | 1797.130005 | 1797.660034 | 41882 | 0 | 0 |
| 2020-11-27 11:15:00-05:00 | 1797.819946 | 1802.599976 | 1796.949951 | 1802.579956 | 60333 | 0 | 0 |
| 2020-11-27 11:30:00-05:00 | 1802.579956 | 1804.000000 | 1797.550049 | 1798.185059 | 45667 | 0 | 0 |
| 2020-11-27 11:45:00-05:00 | 1798.099976 | 1798.603027 | 1788.000000 | 1788.739990 | 47900 | 0 | 0 |
| 2020-11-27 12:00:00-05:00 | 1789.000000 | 1791.599976 | 1787.329956 | 1787.500000 | 36459 | 0 | 0 |
| 2020-11-27 12:15:00-05:00 | 1787.347534 | 1788.530029 | 1782.574951 | 1787.952759 | 46400 | 0 | 0 |
| 2020-11-27 12:30:00-05:00 | 1787.260010 | 1788.920044 | 1785.640015 | 1785.640015 | 45660 | 0 | 0 |
| 2020-11-27 12:45:00-05:00 | 1785.829956 | 1793.420044 | 1785.219971 | 1792.520020 | 97273 | 0 | 0 |
| 2020-11-27 13:00:00-05:00 | 1793.189941 | 1793.189941 | 1793.189941 | 1793.189941 | 46982 | 0 | 0 |
from mplfinance import plot as candlestick_plot # pip install mplfinance if you don't have it already
candlestick_plt(df)
Configure a Tickers instance
Let's say we wanted all ticker instances that Tickers gives us to have their history be over a specific interval of time in the past (say, during the 2020 pandemic), at 5 day intervals...
tickers = Tickers(ticker_symbols={'NFLX', 'AMZN', 'DAL'}, # demoing the fact that we can specify an explicit collection of ticker symbols
history=dict(start='2020-03-01', end='2020-10-31', interval='5d'))
list(tickers)
['DAL', 'AMZN', 'NFLX']
See that indeed, all tickers given by tickers are configured according to our wishes.
tickers['NFLX']
Ticker('NFLX', history={'start': '2020-03-01', 'end': '2020-10-31', 'interval': '5d'})
from mplfinance import plot as candlestick_plot # pip install mplfinance if you don't have it already
candlestick_plot(tickers['NFLX']['history'])
candlestick_plot(tickers['AMZN']['history'])
So Netflix and Amazon did well.
Delta, less so:
candlestick_plot(tickers['DAL']['history'])
Getting (only) specific information about tickers
Tickers and Ticker are convenient if you want to analyze several aspects of a ticker since you can poke around the various keys (e.g. info, history, etc.).
But if a particular analysis only needs one of these, it's more convenient to use TickersWithSpecificInfo,
which gives you the same interface as Tickers (in fact, it's a subclass if Tickers),
but fixes the key.
Example: Historical data
For example, if you're only interested in the historical data (a.k.a. the 'history' key), you might do this:
from invest import TickersWithSpecificInfo
tickers = TickersWithSpecificInfo(specific_key='history', start='2008-01-01', end='2009-01-01', interval='1mo') # 2008 historical data, month granularity
tickers
TickersWithSpecificInfo(ticker_symbols=<local_list>, specific_key=history, start=2008-01-01, end=2009-01-01, interval=1mo)
candlestick_plot(tickers['GOOG'])
candlestick_plot(tickers['NFLX'])
candlestick_plot(tickers['AMZN'])
candlestick_plot(tickers['AAPL'])
Example: Specific 'info' fields
from invest import TickersWithSpecificInfo
the_info_that_i_want = ['shortName', 'sector', 'earningsQuarterlyGrowth', 'sharesShortPriorMonth']
tickers = TickersWithSpecificInfo(specific_key='info', val_trans=lambda d: {k: d[k] for k in the_info_that_i_want})
tickers
TickersWithSpecificInfo(ticker_symbols=<local_list>, specific_key=info, val_trans=<function <lambda> at 0x11c2374c0>)
Now, you won't get the overwhelming amount of information you usually get with info:
tickers['AAPL']
{'shortName': 'Apple Inc.',
'sector': 'Technology',
'earningsQuarterlyGrowth': -0.074,
'sharesShortPriorMonth': 83252522}
faang_tickers = ('FB', 'AMZN', 'AAPL', 'NFLX', 'GOOG')
the_info_that_i_want = ['shortName', 'sector', 'earningsQuarterlyGrowth', 'sharesShortPriorMonth']
tickers = TickersWithSpecificInfo(faang_tickers, specific_key='info', val_trans=lambda d: {k: d[k] for k in the_info_that_i_want})
tickers
TickersWithSpecificInfo(ticker_symbols=('FB', 'AMZN', 'AAPL', 'NFLX', 'GOOG'), specific_key=info, val_trans=<function <lambda> at 0x11c237a60>)
info_df = pd.DataFrame(list(tickers.values()))
info_df
.dataframe tbody tr th {
vertical-align: top;
}
.dataframe thead th {
text-align: right;
}
</style>
| shortName | sector | earningsQuarterlyGrowth | sharesShortPriorMonth | |
|---|---|---|---|---|
| 0 | Facebook, Inc. | Communication Services | 0.288 | 21187652 |
| 1 | Amazon.com, Inc. | Consumer Cyclical | 1.967 | 2509939 |
| 2 | Apple Inc. | Technology | -0.074 | 83252522 |
| 3 | Netflix, Inc. | Communication Services | 0.187 | 9416477 |
| 4 | Alphabet Inc. | Communication Services | 0.591 | 2381334 |
Notes
- Though
Tickersallows you to deal with a collection of tickers, it does so (for time being) by calling yahoo's API for each individual ticker. The API does, on the other hand, contain some bulk tickers routes which we intend to integrate.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file invest-0.0.2.tar.gz.
File metadata
- Download URL: invest-0.0.2.tar.gz
- Upload date:
- Size: 21.0 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/3.2.0 pkginfo/1.6.1 requests/2.24.0 setuptools/49.2.1 requests-toolbelt/0.9.1 tqdm/4.51.0 CPython/3.8.6
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
370bb6769474886ea70599ad0853186be1b9f7309333d61090d4e0cc62b3cf1d
|
|
| MD5 |
ee7c1d521bd8a44bf17a3ece00f3b938
|
|
| BLAKE2b-256 |
bca6c314e4f0f6db3b696c4d0ab20db5ea6e6c06f0c4587adc91c8aa54ed1c1a
|
File details
Details for the file invest-0.0.2-py3-none-any.whl.
File metadata
- Download URL: invest-0.0.2-py3-none-any.whl
- Upload date:
- Size: 11.7 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/3.2.0 pkginfo/1.6.1 requests/2.24.0 setuptools/49.2.1 requests-toolbelt/0.9.1 tqdm/4.51.0 CPython/3.8.6
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
3343881c7cc7137bc41e0d86a0f684ebb6eee96599391c8c0862cd01d7f8cce2
|
|
| MD5 |
9b61ef8a190d0c918e9fe40cfcee4d35
|
|
| BLAKE2b-256 |
83dec33befa792af155f88000ddefdecacfad86ed7874d95820c88500402a1a4
|