Module 11 Exercises: Orchestrating the Background

Module 11 Exercises: Orchestrating the Background

Practical exercises to challenge your understanding of BackgroundTasks and distributed task architecture.

Module 11 Exercises: Orchestrating the Background

In an async world, the "Happy Path" is often just the beginning. These exercises will help you understand how to delegate work effectively.


Exercise 1: The Email Sprayer

You have an endpoint @app.post("/newsletter/send") that takes a list of 500 email addresses.

  1. Explain why you should not loop through these emails and send them directly inside the endpoint function.
  2. Write a simple FastAPI route that uses BackgroundTasks to call a function send_newsletter(emails: list[str]) after immediately returning a success message to the admin.

Exercise 2: Choosing the Right Tool

For each of the following use cases, decide if you should use FastAPI's built-in BackgroundTasks or Celery (External Queue):

  • Case A: Generating a PDF invoice for a user (takes 500ms).
  • Case B: Re-encoding a 4K video uploaded by a user (takes 20 minutes).
  • Case C: Sending a Slack notification to your team when a new sale happens.
  • Case D: Training a Large Language Model (LLM) fine-tuning job on a dataset.

Exercise 3: The ARQ Advantage

Research the ARQ library.

  1. What is the main difference between how Celery and ARQ handle Python functions? (Hint: Think about async def).
  2. Why might ARQ be a "Better Fit" for a FastAPI codebase than Celery?

Self-Correction / Discussion

Exercise 1 Answer:

  1. If you loop through 500 emails inside the endpoint, the request will hang for several minutes (or timeout). The admin will think the server crashed.
  2. @app.post("/newsletter/send")
    async def admin_send_newsletter(emails: list[str], tasks: BackgroundTasks):
        tasks.add_task(send_newsletter, emails)
        return {"message": "Newsletter broadcast initiated."}
    

Exercise 2 Answer:

  • Case A: BackgroundTasks (Fast and lightweight).
  • Case B: Celery (Heavy CPU work should be isolated).
  • Case C: BackgroundTasks (Simple I/O).
  • Case D: Celery (Requires dedicated GPU/Compute resources and long-term state tracking).

Exercise 3 Answer:

  1. ARQ is built around async def and await, making it native to the modern Python async ecosystem. Celery is primarily synchronous and requires extra effort to work with async functions.
  2. ARQ shares the same "async" paradigm as FastAPI, leading to cleaner code and less friction when sharing async database drivers.

Summary of Module 11

You have learned to move work out of the "Blocking Path."

  • BackgroundTasks: Your first choice for simple, non-blocking work.
  • Distributed Queues: Your industrial-grade solution for heavy lifting.
  • User Experience: You understand that response time is a feature.

In Module 12: WebSockets and Real-Time APIs, we will learn how to keep a persistent connection open between the server and the user for instant updates.

Subscribe to our newsletter

Get the latest posts delivered right to your inbox.

Subscribe on LinkedIn