Sling Academy
Home/Python/Python asyncio: Adding schedule callbacks to a Future

Python asyncio: Adding schedule callbacks to a Future

Last updated: February 11, 2024

Introduction

In this tutorial, we’ll explore how to use Python’s asyncio library to add scheduled callbacks to a Future object. Asyncio has become an essential part of Python for asynchronous programming, allowing for the execution of multiple tasks seemingly at the same time. Here, we’ll dive deep into the Future object, a key component of asyncio for handling eventual results from asynchronous operations, and see how to attach callbacks to it, enhancing our asynchronous programming techniques.

The Basics

Before we delve into how to add scheduled callbacks, let’s first understand what a Future object is. In asyncio, a Future represents the result of an operation that hasn’t completed yet. It acts as a placeholder, allowing you to query the result at a future point in time.

Basic Example: Creating a Future

import asyncio

async def set_after(fut, delay, value):
    # Wait for a specific time
    await asyncio.sleep(delay)
    # Set the value of the future
    fut.set_result(value)

async def main():
    # Create a Future object
    fut = asyncio.Future()
    # Schedule to set the future's result after 2 seconds
    await set_after(fut, 2, 'Hello, World!')
    # Once set, retrieve and print the future's result
    print(await fut)

asyncio.run(main())

Output: Hello, World!

This simple example demonstrates how to create a Future object and assign its result after a delay. It showcases the basic concept of futures in asyncio and how they can store the result of any asynchronous operation for later retrieval.

Adding Callbacks to Futures

Once you’ve got a handle on creating Future objects, the next step is to understand how to add callbacks. A callback is a function that is called once the future is done, allowing for additional operations or processing to be executed based on the future’s outcome.

def my_callback(future):
    print('This is my callback:', future.result())

async def main():
    fut = asyncio.Future()
    # Add a callback to the future
    fut.add_done_callback(my_callback)
    # Set the future's result to trigger the callback
    await set_after(fut, 1, 'Callback Triggered')

asyncio.run(main())

This code demonstrates how to add a simple callback to a future. Once the future’s result is set, our callback is triggered, displaying a message along with the result of the future.

Advanced Example: Using asyncio with Multiple Callbacks

import asyncio

async def set_value(fut, value):
    fut.set_result(value)

def callback1(future):
    print('Callback 1:', future.result())

def callback2(future):
    print('Callback 2:', future.result())

async def main():
    fut = asyncio.Future()
    # Add multiple callbacks
    fut.add_done_callback(callback1)
    fut.add_done_callback(callback2)
    # Set the future's result
    await set_value(fut, 'Multiple Callbacks!')

asyncio.run(main())

Here, we’ve taken the example a step further by adding multiple callbacks to a single future. This approach demonstrates the flexibility of asyncio’s Future objects, allowing you to sequentially execute different functions once the future completes. This is incredibly useful for complex workflows where different steps may be required after the completion of an asynchronous task.

Scheduled Callbacks: The Next Level

Going beyond simple and multiple callbacks, we can also schedule callbacks to run at specific times or after certain conditions are met, adding another layer of sophistication to our asynchronous programming.

import asyncio

def schedule_callback(fut, callback, delay):
    async def delayed_callback():
        await asyncio.sleep(delay)
        callback(fut)
    asyncio.create_task(delayed_callback())

async def main():
    fut = asyncio.Future()
    # Schedule a callback to be called after 2 seconds
    schedule_callback(fut, lambda f: print('Delayed callback:', f.result()), 2)
    # This time, set the future's result immediately
    fut.set_result('Immediate Result')

asyncio.run(main())

This example showcases how to implement scheduled callbacks using asyncio. By employing a delay, you can ensure that callbacks are executed not immediately when the future’s result is set, but after a specified period, enabling more controlled flows and timing of operations.

Conclusion

In this tutorial, we have explored how to use Python’s asyncio library to add scheduled callbacks to a Future object. Through practical examples, we demonstrated the basic and advanced usages of Futures and callbacks in asynchronous programming, highlighting their importance and versatility in managing asynchronous operations efficiently.

Next Article: Python asyncio.StreamWriter: A Practical Guide (with examples)

Previous Article: Python Steam: How to start a socket server with asyncio.start_server()

Series: Python Asynchronous Programming Tutorials

Python

You May Also Like

  • Introduction to yfinance: Fetching Historical Stock Data in Python
  • Monitoring Volatility and Daily Averages Using cryptocompare
  • Advanced DOM Interactions: XPath and CSS Selectors in Playwright (Python)
  • Automating Strategy Updates and Version Control in freqtrade
  • Setting Up a freqtrade Dashboard for Real-Time Monitoring
  • Deploying freqtrade on a Cloud Server or Docker Environment
  • Optimizing Strategy Parameters with freqtrade’s Hyperopt
  • Risk Management: Setting Stop Loss, Trailing Stops, and ROI in freqtrade
  • Integrating freqtrade with TA-Lib and pandas-ta Indicators
  • Handling Multiple Pairs and Portfolios with freqtrade
  • Using freqtrade’s Backtesting and Hyperopt Modules
  • Developing Custom Trading Strategies for freqtrade
  • Debugging Common freqtrade Errors: Exchange Connectivity and More
  • Configuring freqtrade Bot Settings and Strategy Parameters
  • Installing freqtrade for Automated Crypto Trading in Python
  • Scaling cryptofeed for High-Frequency Trading Environments
  • Building a Real-Time Market Dashboard Using cryptofeed in Python
  • Customizing cryptofeed Callbacks for Advanced Market Insights
  • Integrating cryptofeed into Automated Trading Bots