The cryptocurrency market moves quickly, with new coins and emerging trends constantly in flux. In this article, we’ll learn how to build a crypto price alert system that provides regular email updates on the top trending coins and categories on CoinGecko, on-chain categories on GeckoTerminal, and sudden surges in trading volume.
These insights can inform our investment strategy or keep us up to date with the latest market trends. As usual, you’ll find a link to the GitHub repository at the end of the article. Let's dive in!
Pre-requisites
- Python 3.10+
- An IDE
- A Gmail account (used to send email updates)
- A CoinGecko API Key
To obtain a CoinGecko API key, head over to the Developer’s Dashboard and click on +Add New Key in the top right corner. For detailed instructions on generating and setting up your key, refer to this guide.
For this project, we’ll be using the Categories List and Search Queries endpoints in the CoinGecko API. The Categories List endpoint is exclusively available only on the CoinGecko API Analyst tier and higher. As a free alternative, you can comment out the call to this endpoint and rely solely on the Search Queries data.
Step 1. Initializing the project
To start, we’ll initialize our project, install package requirements, and safely load our API credentials. First, we'll create an empty directory, which will serve as the root of our project.
Installing Dependencies
Let’s initialize a local Python environment. This will keep the global Python scope clean of any potential library versioning issues:
With the virtual environment now activated, copy the requirements below and paste them inside a new file called requirements.txt at the root of your project.
To install them, simply run pip install -r requirements.txt.
Scaffolding the Project
Now, we'll create the basic structure for our project. Start by creating the following directories: objects, services, and utils. Alongside those, create an empty .env file and an empty main.py file. Your project root should look something like this:
Storing Credentials
When working with sensitive information such as API credentials, or passwords, it’s best to avoid hardcoding them inside the project files themselves. An easy way around this is to store your credentials inside a file called .env. This will allow you to safely import these into the application without ever exposing your credentials.
For this project, we’ll need a CoinGecko API key stored in CG_API_KEY
, along with a Gmail email address and a Google App pass (not the account password) to send trending market updates.
Generating a Gmail App Password
An app password is a unique, 16-digit code generated by Google that allows you to sign in to your Google account securely through an application. It acts as a temporary, app-specific password, ensuring your actual Google password stays private and secure.
Head over to your Google account and search for App passwords to generate it.
Give your new app password a name and paste it into the GMAIL_APP_PASS variable inside your .env file.
Loading Credentials
To load our API and Gmail credentials, let's create a new file called load_env.py inside our utils directory and use the os library to fetch and store our environment variables.
Step 2. Defining our Objects
An object is a self-contained unit that bundles together attributes. Objects allow for modular, reusable, and organized code, so we’ll be leveraging those throughout our codebase.
Within the objects directory, our primary goal is to create a structure for the CoinGecko API responses. Since we’re working with two different endpoints, we’re going to create two objects and map any relevant nested properties.
Coin Category
Under objects, create a new file called coin_category.py. This represents a single Category object, as returned by our Categories List Endpoint.
Mapping the CoinGecko response into a structured format looks like this:
At the core of this structure is the Category object, which contains an attributes object holding various properties. Among these is volume_change_percentage, a nested object that provides volume change data over different time intervals for the given category.
To enable dot notation and type hinting, we'll use a library called JSONWizard. This library not only enhances code readability but also simplifies the serialization and deserialization of JSON data into Python objects.
Trending Searches
Under objects, create a new file called trending_searches.py. Here, we’ll be mapping the Trending Search List response, like so:
The TrendingSearches object organizes trending coins, NFTs, and coin categories from CoinGecko searches, so we’ve created a class for each child object too.
Step 3. Building Our Services
Our application logic can be broken down into 3 specific classes, which are going to act as our core services.
Specifically, we want our application to:
- Make requests to the CoinGecko API and retrieve trending search and on-chain data.
- Format the response so it's easy to read and understand at a glance.
- Send periodic email notifications with the latest trends we've discovered.
Let’s start with the CoinGecko Service.
CoinGecko
Under services, create a new file called coingecko_service.py. Here we’ll define a class that takes two methods: get_onchain_categories(), and get_trending_searches().
For our on-chain categories, the data is currently sorted by 1-hour volume change percentage, but you may choose any other supported sorting option. To convert the API response to the Python objects we defined earlier, we’re going to cast the result to the @dataclass object that inherits properties from the JSONWizard.
Note: If you’re using the Demo API, you’ll need to change self.root to be https://api.coingecko.com/api/v3, and the authentication header to x-cg-demo-api-key. You should also comment out get_onchain_categories(), as this is only accessible via the paid Analyst tier.
Email Formatter
We need to format our data to improve readability. Since we're sending email notifications, we can generate simple HTML to structure the email body with clear line breaks and a simple layout.
Under services, create a new file called email_formatter.py. As with the CoinGecko service, we’ll define a class and its main functions. However, since we don’t need to instantiate this class with any special attributes, we can make our methods static using the @staticmethod decorator. This will allow us to call them without having to instantiate the class.
The get_nested_attr() method retrieves a nested attribute from an object using a dot-separated path. The format_number() method formats numerical values with commas and appropriate decimal places.
Finally, the generate_html() method creates an HTML section with a heading, numbered items, and formatted key-value pairs.
Email Service
This service handles the actual sending of the email, using the Gmail credentials we saved earlier. Under services, create a new file called email_service.py. This class will take a single method of send_email(), but we do need to instantiate it so we won’t be using the @staticmethod decorator.
Step 4. Set Up Crypto Price Alert System
We now have all the necessary ingredients to bring everything together in our main execution file, which serves as the entry point of our application. Open the main.py file that you created earlier, and let’s define the execution logic.
After importing all the required libraries, we’re going to instantiate our CoinGecko and EmailService. We only need to do this once, as we want to reuse these objects, so the instantiation will live outside of our main loop.
Next, let’s put our actual execution logic inside a function called main().
In this function, we retrieve trending cryptocurrency data from CoinGecko, extract the top results, format them into HTML, and send an email digest.
First, we fetch on-chain categories and extract the top four. Then, we retrieve trending searches, selecting the top four results for coins, NFTs, and coin categories.
Next, we use EmailFormatter.generate_html() to create structured HTML for each section. Finally, we compile all sections into a single email body and send it using email_service.send_email().
All that’s left now is to call this function, in a loop:
This loop runs the main function every 24 hours. To adjust the frequency, simply define a different value, in seconds, inside time.sleep().
Congratulations – if you now execute the code, you should have sent yourself an email containing the latest trends in crypto today in the following format:
Considerations
Since this setup uses a Gmail account to send email notifications, it’s advisable to create a separate account for security purposes. However, you’re not limited to sending emails only to yourself—this approach can be used to deliver periodic updates to subscribers through any email-sending provider such as Amazon SES.
The sorting for the Categories List endpoint is based on volume change over a one-hour timeframe, meaning results will most likely fluctuate throughout the day. Similarly, the Search Queries endpoint updates every 15 minutes, so results may also vary here. You can experiment with the notification frequency and adjust it to suit your needs.
As with anything in crypto, use this information responsibly and always do your own research before incorporating these insights into an investment strategy.
If you found this article helpful, be sure to check out our guide on building a Top Gainers and Losers trading bot.
Subscribe to the CoinGecko Daily Newsletter!