Python Based Trading Algorithm Using Yahoo Finance Data
Disclaimer : I am not a Financial Advisor and I am not advocating the trading algorithm below. This is an example.
This example python code is to demonstrate how to structure and write a trading robot in Python. It is based on using standard Python libraries as well as using Yahoo Finance for acquiring market data. There are no market data licenses or costs involved, because the data was provided with a 15 minute delay and is publicly available from Yahoo Finance. It is a follow up to a previous article published where calculations were performed using Excel, and this solution uses Python. Migrating from Excel to Python is a logical technical progression for quantitative developers or data analysts.
The actual code for the trading robot is available in GitHub at the link below. It is free to download and reuse.
https://github.com/jeffj0110/Yahoo_Trading_Bot
I did not write all the code involved with this bot in its entirety. I started with a framework from Alex Reed and refurbished it to meet my needs. I highly suggest you check out some of the work of Alex Reed on GitHub.
Core Topics
1. Review of trading strategy
2. Acquiring the data
3. Next steps : Back Testing and Results
Review of the trading strategy
Indicators Used -
EMA 9, 50 and 200 – The Exponential Moving Average of the closing price based on the last 9, 50 or 200 candles. The ‘exponential’ prefix indicates that the most recent price in the candle is given more weight. Again, a candle can be any amount of time, but in this example we are using daily prices.
Stoch RSI is an abbreviation for Stochastic Relative Strength Indicator and it ranges from zero to 1. I won’t go into the math, but the key is that it helps identify overbought and oversold situations. Our rule indicates that an RSI indicator below .30 is signaling an oversold condition. The K line is the fast moving RSI moving average (usually < 3 candles) and the D line is the slow moving average (> 3 candles).
The strategy we are using will employ the following rules.
- EMA 9 is higher than EMA 50 and EMA 50 is higher than EMA 200
- STOCH RSI is below 30 trending and STOCH line K cross above D
- Entry price: close of previous candle (previous day)
- Exit price when STOCH RSI line K crosses below D and STOCH RSI is greater than .9
Acquiring the data
Retrieving data from Yahoo Finance has been made very simple thanks to the yfinance Python library. To install this library, you will need to execute the following command in the directory of where you have your code.
Python -m pip install yfinance
The documentation for this library is available at the link below (it is opensource freeware).
https://pypi.org/project/yfinance/
The following command will download the Open, High, Low, Close and Volume for a given ticker into a Pandas DataFrame ‘yahoo_prices_df’.
yahoo_prices_df = yf.download(tickers=symbols, interval=bar_string, start=start, end=end, auto_adjust = True, threads=False)
To review this command in the context of the actual application, please refer to the ‘robot.py’ file of the GitHub repository mentioned above.
The data retrieval speeds can vary, but usually complete within 3-5 seconds for any symbol for 1-2 years of daily prices.
Duplicating Calculations In Excel Using Python Built-In Calculations
The Pandas library is the main library used for table based manipulations in Python. The Pandas library will read and write Excel files (and csv files). However, it will not execute Excel formulas. So, one of the main areas of effort to convert the Excel based trading robot files to Python was to convert the formulas.
I used statistical and math functions readily available on Python 3.8 or above. They probably also work fine with Python versions before 3.8, but I did not confirm that.
Moving averages are a very common requirement for trading algorithms. To write a moving average on a column within a Pandas dataframe, the following one line of code iterates and calculates the moving average (for a given ‘period’) and stores the result in a new column called ‘Moving Average’. There is a lot going on in the one line of code below as it leverages Lambda’s, iterators, computes a rolling average while performing column operations within Pandas. This is a typical example of doing an iterative calculation on a table column in Python.
Data_frame[‘Moving_Average] = self._frame[‘Input_Column_Name].transform(lambda x: x.rolling(window=period).mean())
The following one line of code will calculate the percentage difference between volumes for each day and place the results in a new column.
Data_frame [‘Volume_Percentage_Change’] = Data_frame ['volume'].transform(lambda x: x.pct_change(periods=period) )
To follow what is happening in the commands above, you start to the right of the ‘=’ and review each statement left to right. All the column calculations and indicators for the Python based trading robot are in the file ‘indicators_calcs.py’ in the GitHub repository referenced previously.
Back Testing and Results
The next step is to run the strategy against the SP500 and all the crypto currencies and publish the results based on daily prices for the past year. This will be done via running the bot with a large number of symbols, something which lends itself well to a large multi-processing environment (with a fast Internet connection!).