DEV Community

Cover image for Automated crypto price tracking using GMAIL and Python
Nikola Perišić
Nikola Perišić

Posted on

Automated crypto price tracking using GMAIL and Python

Do you manually track crypto currencies values?
Do you want to be notified by email when your crypto currency value goes up or down by specific value?
Do want to stop going to crypto exchange websites just to see value of the coin?

If you answered with 'Yes', then, you are in the right place.

Whether you're a seasoned trader or a crypto enthusiast, staying updated with the latest prices is crucial. Thankfully, Python can help automate this process, saving you time and effort.

In this post, I’ll walk you through a simple Python script that tracks the value of any cryptocurrency on a specific exchange in real-time.


Why Automate Crypto Price Tracking?

Cryptocurrency markets operate 24/7, and prices can change in seconds. By automating the tracking process, you can:

  1. Stay informed about market movements in real time.
  2. Eliminate manual refreshing of exchange pages.
  3. Get notified when price is changed in specific range.

Requirements

To follow along, ensure you have the following:

  1. Python installed on your system
  2. Basic knowledge of Python and installing libraries
  3. Generated Google account app password
  4. Installed Google Chrome

The Code

There are three files:

  1. app.py -> main script
  2. cryptocurrencies.json -> where you define which coins you track
  3. email_template -> code for your email design

Whole code can be found in this GitHub gist.

Note: The code could be refactored for improved readability and efficiency, but the primary focus here is on functionality.

Note: In this example I used "Kraken" as crypto exchange where I follow prices.


Example Email Notification:

When the value of the (for example) Polkadot coin increases by 1 EUR, you receive an email notification like this:

Bitcoin ethereum polkadot coins blockchain crypto


Explanation of code

Import necessary libraries.

  1. selenium: Automates web browser actions (e.g., fetching cryptocurrency prices).
  2. webdriver_manager: Automatically manages ChromeDriver installations.
  3. fake_headers: Generates realistic user-agent headers for the browser.
  4. smtplib: Handles email-sending functionality.
  5. dotenv: Loads environment variables (e.g., email credentials).
  6. os, time, json: Handle file operations, delays, and JSON parsing.

Load Environment Variables

load_dotenv()
Enter fullscreen mode Exit fullscreen mode

Loads variables like email credentials (PASSWORD) from a .env file for secure handling.

Email Sending Function

def send_email(subject, price, currency_name, image_url, price_change):
    sender_email = "your_email@gmail.com"
    receiver_email = "your_email@gmail.com"
    password = os.getenv("PASSWORD") -> here you need to type your generated google account app password

    msg = MIMEMultipart()
    msg['From'] = sender_email
    msg['To'] = receiver_email
    msg['Subject'] = subject

    if price_change > 0:
        change_emoji = "📈"  
    elif price_change < 0:
        change_emoji = "📉"  
    else:
        change_emoji = "⚖️"  

    with open('email_template.html', 'r', encoding='utf-8') as f:
        html_template = f.read()

    html_content = html_template.format(
       currency_name=currency_name,
       price=price,
       image_url=image_url,
       change_emoji=change_emoji
    )

    msg.attach(MIMEText(html, 'html'))

    try:
        server = smtplib.SMTP('smtp.gmail.com', 587)
        server.starttls()
        server.login(sender_email, password)
        server.sendmail(sender_email, receiver_email, msg.as_string())
        print("E-mail sent!")
    except Exception as e:
        print(f"Error occured: {e}")
    finally:
        server.quit()
Enter fullscreen mode Exit fullscreen mode

Purpose: Sends an HTML-formatted email notification when price thresholds are met.
Loads the email template from an external file (email_template.html).

Helper Functions

def delay():
    time.sleep(2)
Enter fullscreen mode Exit fullscreen mode

Purpose: Adds a delay to prevent excessive requests to the target website, avoiding detection as a bot.

def load_cryptocurrencies():
    with open('cryptocurrencies.json', 'r') as f:
        return json.load(f)
Enter fullscreen mode Exit fullscreen mode

Purpose: Loads cryptocurrency details (e.g., name, url, imagesrc) from a JSON file.

Configure Selenium Options

chrome_options = Options()
header = Headers(browser="chrome", os="win", headers=False)
customUserAgent = header.generate()['User-Agent']
chrome_options.add_argument(f"user-agent={customUserAgent}")
chrome_options.add_argument("--headless")
chrome_options.add_argument("--no-sandbox")
chrome_options.add_argument("--disable-dev-shm-usage")

driver = webdriver.Chrome(service=Service(ChromeDriverManager().install()), options=chrome_options)
Enter fullscreen mode Exit fullscreen mode

Purpose: Sets up a headless Chrome browser for scraping cryptocurrency prices.

headless: Runs Chrome without a GUI.
Custom User-Agent: Mimics real browser usage for better bot detection evasion.

Main Loop - Price Tracking

cryptocurrencies = load_cryptocurrencies()

for currency in cryptocurrencies:
    try:
        url = f"https://www.kraken.com/prices/{currency['url']}"
        driver.get(url)
        delay()

        price_element = driver.find_element(By.CLASS_NAME, "asset-price.black-color")
Enter fullscreen mode Exit fullscreen mode
  1. Iterates through each cryptocurrency from the cryptocurrencies.json file.
  2. Constructs the URL to fetch price data.
  3. Uses selenium to scrape the price from the target website.

Process Scraped Price

 price = price_element.text.strip().replace('', '').replace(',', '.')
        try:
            price = float(price)
        except ValueError:
            print(f"Error while conversion price for {currency['name']}: {price}")
            continue
Enter fullscreen mode Exit fullscreen mode

Parses the price text and converts it into a float for comparison and calculation

Compare Prices

        previous_price_file = f"previous_price_{currency['url']}.txt"
        try:
            with open(previous_price_file, 'r') as file:
                previous_price = float(file.read().strip())
        except FileNotFoundError:
            previous_price = None

        price_change = price - previous_price
Enter fullscreen mode Exit fullscreen mode

Retrieves the last saved price from a text file. If it doesn’t exist, assumes no previous data.
Calculates the price change (price_change).

Trigger Notifications

        if previous_price is not None:
            if price < 100:
                if abs(price - previous_price) >= 1:
                    subject = f"New price {currency['name']}: {price}"
                    send_email(subject, price, currency['name'], currency['imagesrc'], price_change)
            else:
                if abs(price - previous_price) >= 5:
                    subject = f"New price {currency['name']}: {price}"
                    send_email(subject, price, currency['name'], currency['imagesrc'], price_change)
Enter fullscreen mode Exit fullscreen mode

Sets thresholds for price change notifications:

  1. If price < 100, notifies on changes ≥1 EUR.
  2. Otherwise, notifies on changes ≥5 EUR.

Note: If you want to track coins with more digits you need to adapt it here.

Update Saved Price

with open(previous_price_file, 'w') as file:
            file.write(str(price))
Enter fullscreen mode Exit fullscreen mode

Saves the current price to the text file for future comparisons.

Exception Handling

    except Exception as e:
        print(f"Error occured for {currency['name']}: {e}")
Enter fullscreen mode Exit fullscreen mode

Cleanup

driver.quit()
Enter fullscreen mode Exit fullscreen mode

Closes the browser instance after all tasks are complete.


How to make this work?

  1. Make cron job on your PC
  2. Make cron job on server

To make this in action once per hour add this:

crontab -e
Enter fullscreen mode Exit fullscreen mode

a) Run Every 5 Minutes

*/5 * * * * 
/location_to_venv/venv/bin/python3 
/project/app.py >> /project/cron_log.txt 2>&1
Enter fullscreen mode Exit fullscreen mode

b) Run Every Hour

0 * * * * 
/location_to_venv/venv/bin/python3 
/project/app.py >> /project/cron_log.txt 2>&1
Enter fullscreen mode Exit fullscreen mode

c) Run Every Week on a Specific Day (e.g., Monday)
To schedule the script to run at a specific time every Monday (e.g., at 6:00 AM), use:

0 6 * * 1 
/location_to_venv/venv/bin/python3 
/project/app.py >> /project/cron_log.txt 2>&1
Enter fullscreen mode Exit fullscreen mode

Conclusion

By following this guide, you can track cryptocurrency prices and receive real-time email notifications while you sleep!

If you found this post helpful or have ideas to improve the script, feel free to leave a comment below 🚀

Happy coding and successful trading!

Top comments (0)