Python Promises/A+ implementation
The `promise` library provides a Promises/A+ implementation for Python, designed to handle asynchronous operations with a familiar API akin to JavaScript Promises. It offers readable, performant code with essential extensions for Python development, including a `DataLoader` implementation. The library is currently at version 2.3.0 and sees occasional updates, focusing on performance, thread-safety, and compatibility.
Warnings
- breaking Version 2.0.0 introduced a complete rewrite. Key changes include `Promise.resolve` now behaving like `Promise.cast` and `Promise.reject` becoming a static method. Code written for 1.x versions will likely require significant updates.
- gotcha `Promise` and `DataLoader` were not thread-safe in versions prior to 2.3.0. Concurrent access from multiple threads could lead to unexpected behavior or data corruption.
- gotcha Versions prior to 2.3.0 contained a memory leak, particularly impacting dynamically created types within the library.
- gotcha In version 2.0.0, `Promise.resolve` when called with a coroutine incorrectly returned an `asyncio.Task` instead of a `Promise`, breaking expected chaining behavior.
- gotcha Older versions of the library (prior to 2.3.0) might emit deprecation warnings when run on Python 3.7 and newer environments.
Install
-
pip install promise
Imports
- Promise
from promise import Promise
- DataLoader
from promise.dataloader import DataLoader
Quickstart
from promise import Promise
def my_async_operation(resolve, reject):
# Simulate an async task
import time
time.sleep(0.1)
success = True # or False for rejection
if success:
resolve('Data fetched successfully!')
else:
reject('Failed to fetch data.')
# Create a promise
promise_instance = Promise(my_async_operation)
# Chain operations with .then() and handle errors with .catch()
promise_instance.then(
lambda result: print(f'Resolved: {result}')
).catch(
lambda error: print(f'Rejected: {error}')
)
# To make the example runnable without an explicit event loop for simple cases:
# In a real async application (e.g., with asyncio), you would integrate it with the event loop.
# This example is synchronous after the sleep, demonstrating the promise structure.