Greenback

1.3.0 · active · verified Thu Apr 09

Greenback is a Python library that enables calling asynchronous code from a synchronous context within an active `asyncio` or `Trio` event loop. It bridges the gap between synchronous and asynchronous programming, allowing for gradual migration of codebases and interoperability with async-unaware libraries. The current version is 1.3.0, and it maintains a focused release cadence as a small, specialized utility built on `greenlet`.

Warnings

Install

Imports

Quickstart

This quickstart demonstrates how to use `greenback` to call an `async` function (`fetch_data`) from a regular `sync` function (`process_item`, `another_sync_task`) within an `asyncio` event loop. First, `await greenback.ensure_portal()` is called in the main async task to set up the necessary `greenlet` context. Then, `greenback.await_()` is used in the synchronous functions to execute the async calls. The `with_portal_run_sync` helper is also shown for explicit portal scoping.

import asyncio
import greenback

# An async function we want to call from sync code
async def fetch_data(item_id):
    print(f"[Async] Fetching data for {item_id}...")
    await asyncio.sleep(0.1) # Simulate I/O
    return f"Data for {item_id}"

# A synchronous function that needs to call an async function
def process_item(item_id):
    print(f"[Sync] Processing item {item_id}")
    # Call the async function from sync context using greenback.await_
    data = greenback.await_(fetch_data(item_id))
    print(f"[Sync] Received: {data}")
    return data

# The main async entry point
async def main():
    # Ensure a greenback portal is set up for this task
    await greenback.ensure_portal()
    print("Portal ensured.")

    # Call the synchronous function that will use greenback
    result = process_item("A123")
    print(f"Main task received: {result}")

    # Example using with_portal_run_sync
    def another_sync_task():
        print("[Sync 2] Starting another sync task.")
        result2 = greenback.await_(fetch_data("B456"))
        print(f"[Sync 2] Got: {result2}")
        return result2

    final_result = greenback.with_portal_run_sync(another_sync_task)
    print(f"Main task got final result: {final_result}")

if __name__ == "__main__":
    asyncio.run(main())

view raw JSON →