Hide contents

iOS Test-Driven Development by Tutorials

12 Dependency Maps
Written by Joshua Greene & Michael Katz

Heads up... You're reading this book for free, with parts of this chapter shown beyond this point as scrambled text.

Before you start making changes in a large project, you first need to understand how the system works and how its classes are related. This chapter will help you visualize this using a tool called dependency maps. You’ll learn:

  • What is a dependency map?
  • How can you use it to understand complex systems?
  • How can you use it to identify problematic relationships?
  • How can you use it to break up a complex system into modules?

Feel free to continue using your project from the last chapter, or start fresh from this chapter’s starter project. For the best hands-on experience, you’ll need a pencil, red marker, green marker and paper. This is going to get… analog!

Alternatively, a drawing program — or even Keynote — will work too.

Getting started

You may be wondering, “What exactly is a dependency map?” Great question!

Dependency maps are a way to illustrate dependencies between types. Its primary purpose is to help you understand how a change will affect an entire system. You can use dependency maps to identify change points, test points and places where you can pull out types to make your app more modular.

Before making a code change, your first step is to identify what the new behavior should be. In this case, your job is to move MyBiz’s login functionality into a separate module. Long-term, the plan is to use the login module in multiple apps.

Moving login into a separate module also has side benefits: Faster incremental compile times, separation of unit tests and more.

Wouldn’t it be awesome if you could simply move LoginViewController and related types into a new module and have it just work? Unfortunately, real-world apps aren’t usually so well architected…!

Consequently, you’ll need to break up dependencies to make this possible. This is the perfect problem a dependency map can help you solve.

Choosing where to begin

Choosing the “right” place to begin can be a daunting task in a large app. Fortunately, creating a dependency map is a journey of discovery and you can iteratively refine it. An educated guess for a starting point is good enough.

Siluq KoojQoxhverwaq

Finding direct dependencies

The next step is to identify the type’s direct dependencies.

Lvuw Muroy XaofCiznkijqul IsmFojiparu EWU

Thij Hijim LoudXivqpaxkat OIXiufNiprgowxuw +Uzevp IbdRaxojusi UYO Notexakusz

Lmij Tekom YaafVaqnqiwcev UAJiizSihjloqgow +Orunq IzbLuqalago Pakufz Adiyp Ikfciweu Obtiujmezoxy Ycitaph CuxhsawiIfxuy OyirEgfo OFI EMUMuqerepi Linoxikucd

Finding secondary dependencies

Your dependency map looks nice right now with all of the arrows pointing away from LoginViewController. However, this is because you’ve only inspected LoginViewController and not any other classes yet.

Pvim Qahex BeozQembnezhit UULaovZacrtojjob +Ewelq AsyRifufeku Pazazk Akadr Alykubou Onsuujnizonh Vvibikd QarwqoliIcsuh OkicEhti Luyzuzupuyoeh ENU IKUHuyeluta Mowiyaxukr

Fkas Sagog XoutTodfzetmow IOPiubNejzqugyad +Ehufk EzhYemavaca Racajg Axumq Uhcsixio Usnuewgeruxv Svevabs XujldigiEdqax EjurEdke Qeykapojubaol ABU EDIRolabene Xebalicoxf

Skut Nawid FiedDuhkvizvog OEFautNavvtonsuf +Ofajx Enqiz CoepZokbyokwor IdzWidomopi Qifoht Ufarp Uvdyizaa Oqweavmecusv Yyadizc BifwdidaObtin EbegIhti Rekbidoreneej UVO OMIXiboraxu Heqog Mulewenefh

Deciding when to stop

You could iteratively walk all files and create a diagram for the entire app. While this might be interesting, it’d likely be too busy to be useful. The further you get from the type you’re trying to modify, the less likely you’ll find relevant dependencies. Should you find yourself making changes in files that aren’t on your diagram, of course, you can always include them later.

Ltit UAKuasPilwlacwip +Uhekb Ezrig LeoxLoqgyoqfiz EqwXaqezawi Vekunc Ojolk Iznjalou Epdiimlopiff Smotihc VejvkeniOhcaj Piwlumejomiuz ODAGuzafigo Zusah Noyosesind Vaciy WiizXamzwugmes UJI

What are problematic dependencies?

A type is coupled to another when it directly depends on it. However, this may or may not be problematic. For example, if a type is coupled to a delegate protocol (e.g. API and APIDelegate), this is better than being coupled to a concrete type directly (e.g. LoginViewController).

Finding problematic dependencies

You can evaluate the relationships in the dependency map using these questions to find problematic dependencies.

Mgax UUZoalSesgwudzaz +Urupq Uqhun WaomNenmqumgij AqdYitihule Hiqotn Ewaxl Ukhgitea Uvboexbakaqz Cnuduyc RalkziliIzwej Goyqijutogiuw OZEYayivewo Geqat Becerapixw Pojid DoetVedssiwvit EZE

Rgiw IAQuusCaffwahrep +Ogoyr Uqbay FaewFobqhuznek EnrXenanicu Zefelw Ahitn Ehtqodaa Unfeogxujors Cwanidy HewrqukuErges Melralayodioc UXIYilayoda Jisul Qoguhiwajf Xarok DiatZarskucqej ONA

Completing the map

If you find that a direct dependency is problematic, you don’t need to evaluate whether its secondary dependencies are problematic. Rather, you’ll need to refactor or fix this in some way first. Depending on what you do in this regard, however, you may later consider the secondary dependencies or may never do this.

Breaking up complex systems

You can use your dependency map as a blueprint to break up complex systems. It tells you exactly how types are related and which relationships are problematic!

Key points

You learned about dependency maps in this chapter. Here are their key points:

Where to go from here?

In the next chapter, you’ll use this dependency map to actually pull out the login functionality into a new module! Of course, you’ll do this in a TDD fashion and learn tricks along the way for handling problematic relationships.

Have a technical question? Want to report a bug? You can ask questions and report bugs to the book authors in our official book forum here.
© 2022 Kodeco Inc.

You're reading for free, with parts of this chapter shown as scrambled text. Unlock this book, and our entire catalogue of books and videos, with a Professional subscription.

Unlock Now