So far in our Fantasy Basketball Optimization series, we’ve covered most of the different aspects of our project, including
- Pulling data from APIs and SharePoint spreadsheets
- Optimizing lock-in decisions with statistical modeling
- Reporting results via email with Python
We’ve showcased these through a series of disconnected Jupyter notebooks, but our final solution combined all of these together into one daily automated pipeline. To make this, we implemented all of our code as a collection of AWS Lambda functions that we could schedule to run daily.
This article showcases how we pulled everything together, starting with a quick overview of all the Lambda functions we created.
Cloud Setup Overview
Using the technique that we demonstrated in our Python Automation with AWS Lambda post, we created these 4 Lambda functions for the pipeline:
- pullDailyStats – gets stats by player/game using API-NBA
- pullSleeperData – gets league specific data from Sleeper API
- updateLockedPoints – fills in stats in the lock-in spreadsheet and gets locked points values
- sendTeamUpdate – runs the lock-in optimization code and sends out the daily automated email

We then used EventBridge (also described in the Lambda blog post) to schedule each of these functions to run every morning.
We provided a quick summary of each of the functions below, but note that the full code for each of the functions with the corresponding deployment files is available in our GitHub repo.
pullDailyStats
The first function pulls NBA stats by player/game from the API-NBA API that we found on rapidapi.com (see our Pulling Data from API-NBA post for more info).
In order to use the API, we first had to subscribe to it and get an API key, which we saved as a secret in AWS Secrets Manager (see the Python Automation with AWS Lambda post for more info on the Secrets Manager):

The function then reads the API key from the Secrets Manager, pulls stats for the recent games, and saves them to CSV files in an AWS S3 bucket (more info on S3 in the Lambda post too).
pullSleeperData
The next function is very similar, just with a different API. It uses the API that Sleeper provides for pulling league specific data, which is documented in our Pulling Data from the Sleeper API post.
The function pulls the rosters and players for each of the teams in our league and saves them as CSV files in the same AWS S3 bucket as the stats. Note that we actually didn’t need an API key for this one, just a league ID that we hard coded into our script (you’ll need to fill in your league ID to try out the code for yourself).
updateLockedPoints
The third function updates the stats in the lock-in spreadsheet and pulls the locked totals from it. We did a local demo of this in our Managing the Lock-in Spreadsheet post, but we uploaded the final lock-in spreadsheet to a SharePoint site so that we could edit it with a phone instead of having to use our desktop all the time.
We then had our Lambda function connect to the SharePoint Excel file using the technique in our Connecting Python to SharePoint post. It pulled the stats data from our S3 bucket to update the spreadsheet and saved the locked totals as a CSV in the bucket as well.
Note that in order to authenticate the connection to SharePoint, we had to store our service principal credentials in the Secrets Manager:

sendTeamUpdate
The fourth and final function pulls the data from the past 3 functions together and applies all of the probability logic outlined in our Addressing the Lock-in Dilemma post. This includes
- Suggestions for scores to lock based on an estimated probability of a better outcome
- Suggestions for free agents to consider picking up
- Overall matchup projections with a win probability
After reading in the data and performing all the calculations, it creates and sends an email summarizing the results/suggestions. The email is sent using the technique that we covered in the Sending Automated Emails with Python post.
Note that the email connection required an account password that we saved in the Secrets Manager:

Conclusion
While our previous posts demonstrated each piece with a local Jupyter notebook, we implemented everything as a cloud pipeline that runs automatically and sends us updates via daily emails. This article showcased how we combined the code from all of those other posts into a set of AWS Lambda functions that made up our pipeline.
If you’d like to try implementing the pipeline yourself, feel free to download the source files from our GitHub repo.
Thank you for following us across our journey of building our fantasy basketball optimization pipeline, and we hope you learned a few things on the way. If you did, feel free to leave a comment below, and check out some of our other projects via our Projects page.
