A video series exploring functional programming and Swift.
#16 • Monday May 21, 2018 • Subscriber-only

Dependency Injection Made Easy

Today we’re going to control the world! Well, dependencies to the outside world, at least. We’ll define the “dependency injection” problem and show a lightweight solution that can be implemented in your code base with little work and no third party library.

#16 • Monday May 21, 2018 • Subscriber-only

Dependency Injection Made Easy

Today we’re going to control the world! Well, dependencies to the outside world, at least. We’ll define the “dependency injection” problem and show a lightweight solution that can be implemented in your code base with little work and no third party library.


Subscribe to Point‑Free

This episode is for subscribers only. To access it, and all past and future episodes, become a subscriber today!

See subscription optionsorLog in

Sign up for our weekly newsletter to be notified of new episodes, and unlock access to any subscriber-only episode of your choosing!

Sign up for free episode

Introduction

Today we’re going to revisit a topic we’ve talked about in the past: side effects. We introduced the topic in our second episode with a deep dive on how side effects are kind of like hidden inputs and outputs to our functions, demonstrating how they make testing difficult and how they can introduce subtle bugs. Side effects are complicated and require attention.

The examples in that episode were a bit contrived, so today we’re going to look at code that’s a bit more real-world and explore how we can extract and control side effects quickly and painlessly.

This is a method we’ve used in production again and again, and it’s proven itself over time. We hope that others get the same benefit!

Subscribe to Point-Free

👋 Hey there! Does this episode sound interesting? Well, then you may want to subscribe so that you get access to this episodes and more!


Exercises

  1. Today’s episode was powered by playground-driven development, but we’re talking about real-world code and that kind of code usually lives in an application target. The following exercises explore how to apply playground-driven development to actual application code.

    1. Download the episode code and copy it into a new iOS project called “Repos”. The app should display the repos navigation controller as the window’s root view controller.

    2. Add a framework target to the project called “ReposKit” and embed it in the Repos app. Move all of our application code (aside from the app delegate) to ReposKit. Make sure that the source files are members of the framework target, not the app target. Repos should import ReposKit into the app delegate in order to access and instantiate the ReposViewController. Build the application to make sure everything still works (you will need to make some types and functions public).

    3. Create an iOS playground and drag it into your app project. Import ReposKit, instantiate a ReposViewController, and set it as the playground’s live view. You can use our original playground code as a reference.

    4. Swap out the Current, live world for our mock one. This playground page can now act as a living reference for this screen! You can modify the mock to test different states, and to test changes to the view controller, you can rebuild ReposKit.

  2. There are a few dependencies in the application that we didn’t cover. Let’s explore controlling them over a couple exercises.

    1. The analytics client is calling out to several singletons: Bundle.main, UIScreen.main, and UIDevice.current. Extract these dependencies to Environment. What are some advantages of controlling these dependencies?

    2. DateComponentsFormatter can produce different strings for different languages and locales, but defaults to the device locale. Extract this dependency to Environment, control it on the formatter, and demonstrate how mocking Current allows you to test formatting over different languages and locales.


References

Chapters
Introduction
00:05
An example application
01:03
Dependency injection
04:25
Controlling time
09:40
Current
17:02
Controlling the world
19:25
One less protocol
21:15
One more dependency
25:55
What’s the point?
31:10