Inversion of control

Who calls whom: the Hollywood principle and its forms (callback, template method, event listener, dependency injection) and what sets a framework apart from a library.

  • 25 cards
  • 5 topics
  • Free

The outline, topic by topic

Each topic is weighted the way the exam weighs it.

  1. Concepts
  2. Questions
  3. Sort and link
  4. Scenarios
  5. Understand

A few cards from the deck

  • Inversion of control: what is it?

    Show the answer

    The principle that the developer's code no longer decides when it runs: an outside frame calls it at the points set aside for that.

    It is called the Hollywood principle: “don't call us, we'll call you”. A library is called when the developer decides; a framework calls the developer's code.

  • What does this program print?

    ```python
    callbacks = []

    def register(f):
    callbacks.append(f)
    print("registered")

    def trigger():
    for f in callbacks:
    f()

    def greet():
    print("hello")

    register(greet)
    print("ready")
    trigger()
    `

    • registered, ready, hello
    • hello, registered, ready
    • registered, hello, ready
    • ready, registered, hello
    Show the answer

    registered, ready, hello

    register(greet) stores the function without running it. It only runs at trigger(): control goes from your code, which registered, to the code that calls back.

  • With a …, the developer's code does the calling; with a …, the framework calls the developer's code.

    Show the answer

    With a library, the developer's code does the calling; with a framework, the framework calls the developer's code.

    json.loads(text) is a call to a library. A route declared with @app.get('/') is called by the framework when a request arrives.

  • Callback: what is it?

    Show the answer

    A function passed as an argument to other code, which will call it later, when the awaited event happens.

    You pass the function itself, without parentheses: register(greet) hands it over, register(greet()) runs it at once and hands over its result.

  • A billing service creates Depot() in its constructor, and every test writes to the real database. Which change lets you test without a database?

    • Receive the repository as a parameter and pass a fake in tests
    • Create Depot() in a class attribute rather than in the constructor
    • Call Depot() in every method of the service rather than once in the constructor
    • Read the database address from an environment variable
    Show the answer

    Receive the repository as a parameter and pass a fake in tests

    As long as the service builds its own dependency, it is tied to the real class. By receiving it, it does not know what it gets: tests pass a fake, production passes the real one.