2024 Public Training Schedule
November 18 – 21, 2024 – Agile Analysis and Design Patterns
Half-Day Sessions
December 9 – 12, 2024 – Agile Analysis and Design Patterns
Half-Day Sessions
(c) 2024 To Be Agile
As software developers, many of us have been trained to dive right into implementation. As soon as we learn about a problem, we think about how to code a solution.
But this is not always the right approach. Sometimes, it makes more sense to step back and look at the big picture, to try to see how the piece we’re working on will fit into the whole system. Many integration and incompatibility issues can be solved if we take a moment to consider them up front. The expression is “ready, aim, fire” not “fire, aim, ready.”
So then what do we need to know before we dive into implementation?
Start by taking your caller’s perspective. In other words, when writing an API, don’t think about what you want to get as parameters but rather think about what your client wants to give you. This advice is echoed in the sixth SOLID principle in software development, which we refer to as the Dependency Inversion Principle.
We normally think about implementing an API without giving much consideration to how our clients want to call our API. But that can make it awkward for our callers so instead, we take their perspective and build a method signature for our API that corresponds to what our callers want to give us.
Of course, sometimes what our callers want to give us is not what we want to receive, and it’s part of our job to reconcile this. For example, if our caller wants us to parse a document on a server then they may want to give us the URL of that document on a server. In this case, they’re asking us, the API provider, to do two things. First, they’re asking us to locate and retrieve the document from the server then they’re asking us to parse the document. This may make perfect sense from the caller’s perspective but these two activities, when combined together, make our API very difficult to test. What we should do instead is break them up internally using a simple technique called peeling.
Peeling can be useful in situations where the first things we need to do is retrieve some data we’ll then act on. The first few lines of our API are involved in locating and accessing the data. If we use peeling to extract these lines out into its own method, our API can call this method then call the main method with the document to parse. This breaks the dependency on needing a web server to retrieve a document because we can test the code that parses the document by passing a document to the internal method rather than spinning up a web server. If we don’t create a peel then in order to test our API we would have to bring up a web server.
Most of the time, by taking our caller’s perspective, we can forge method signatures that are more convenient to our callers so they’re easier to use. This can greatly simplify the software we build.
Taking our caller’s perspective can also help us create better encapsulation because it reinforces information on an object having an inside and an outside. This allows us to hide implementation details inside of an object so that those outside are unaware of those details, and when they change, callers are not affected.
Taking our caller’s perspective helps us build out observable behaviors in a system, which can provide a great deal of overarching cohesion to our software.
{1 Comments }
Previous Post: « Slow Down to Go Faster
Next Post: Barely Sufficient Documentation »
As well as taking the caller’s perspective, I find reaching out to the consumers of an API I’m building to be the best approach to designing it. As much as I try to put myself in their shoes, it’s not always obvious what the right solution is for them.