API providers aiming for great developer adoption provide SDKs. These SDKs translate the API specification into client code. But that code is not enough to guarantee good developer experience. Why? Because an API specification is not built to stand failures in production. Eventually, manual effort is required to add layers on top of the SDK to ensure developer experience.
This blog outlines these extra layers that ensure an SDK won’t fail in production.
Success criteria of an API
As an API provider, what’s your end goal with the API you have built? It’s to get developers to quickly use your API in production, right? To understand this point best, let’s put our consumer’s shoes on and see what an API consumer goes through while trying to use an API.
A while back, I was trying to use an API to create a meeting when I found the request sample code for an HTTP client.
This was a huge time-saver for me so I instantly copied it into my application. And that’s when things went downhill.
On the first look, I noticed the following red flags:
- Bad HTTP practice: This code sample initializes a new HTTP client for every endpoint call which means X initializations for X endpoints.
- Security vulnerability: The code was sending sensitive authorization information inside the header. I would never recommend this practice to anyone and would never do it myself.
By this time, I was already doubting my decision of using this API but as I skimmed through the code further, I noticed the following:
- Hardcoded JSON: This was a shocker for me because even if you aren’t a pro, you know that the right way is creating objects of classes and sending data through those serialized objects.
Apart from these, I found many major refactoring issues which clearly stated that this code was not production-ready so I gave up on using this API. As a developer myself, I love copy-ready code samples that I can use in my application and build my logic on top of it. But this was not the case here.
The API integration we need
Since I critically analyzed this code sample, it’s only fair to show what sort of API integration I prefer. Upon further research, I came across this API:
What caught my attention was how they advise you to use their SDKs to call endpoints. I was so excited about it because a solution that extracts all duplicate information from code and handles it in a separate library is exactly what leads to quicker API integration. Working with this API was much easier as all I had to do was initialize a client of their SDK and use that client to make API calls.
After experiencing this, there can be no doubt that client SDKs are the road to faster, smoother API integration.
SDKs that are more than just an API wrapper
A client SDK contains wrapper classes that you can use to call the API from your application. APIMatic client SDKs are built to be more than just a wrapper around your API specification. These SDKs are layered with intricate settings to enhance the developer experience. Let’s look at these layers in detail.
API specification wrapping layer
The base layer of every APIMatic-generated SDK is the API specification wrapping layer. It’s exactly like the name suggests; the translation of your API specification into generated code. From this layer, you get data models, endpoints, authentication, HTTP request building, and call to endpoints.
But if you ask me whether this SDK is ready to be used in a production environment, I would say no. This SDK covers the basic working of the API but is not yet equipped to handle failures and other performance issues. To handle these, you need to add more elements on top of the API wrapper. Which leads us to our next layer.
API Consumer DX layer
APIMatic CodeGen handles the shortcomings of an API wrapper by adding a Consumer developer experience layer on top of the wrapper. This layer provides the following enhancements:
- Failed calls are retried with exponential backoff
- Client is configurable
- There are configurable loggers to diagnose and debug issues in the API calls
- Extendable interfaces for controller classes
- Optimized error messages that define custom errors to HTTP response codes
- Concurrent thread-safe API calls
- My personal favorite, how-to guides with code samples
- And much more.
Now that we have catered to the needs of API consumers, do you think this much is enough? At APIMatic, we think we can do more.
API Provider DX Layer
The API provider layer encapsulates the consumer layer with special DX components tailored for API providers. These components help with code styling, code branding, continuous integration, and the overall look and feel of the code.
- Run unit tests on code
- Monitor the generated code regularly through SDK monitoring
- Maintain rapidly going out API versions
- Use CI/CD pipelines for automation
- Monitor performance through telemetry
Apart from these features, APIMatic SDKs come packed with CodeGen settings that let the API providers take full control over the generated libraries. These settings provide code customizations that enhance the overall developer experience.
The last layer, the language-idiomatic layer, envelops this developer experience journey with multiple language support. APIMatic generates SDKs in the following languages:
- Go (coming soon)
- Swift (coming soon)
Each language has its own conventions and semantics, and so should the SDK. Therefore, it is crucial to provide SDKs that can benefit developers regardless of the language they prefer. This is where multi-language support comes in handy. The language-idiomatic layer allows developers to use the SDK in the language of their preference, advocating what the great Nelson Mandela said:
“If you talk to a man in a language he understands, that goes to his head. If you talk to him in his language, that goes to his heart.”
To get a clearer idea, listen to this talk on Taking Generated Code Beyond Hello World.
Simply providing haphazard code samples along with APIs is not good enough. You need to ensure those samples are copy-ready, precise, and that all repetition is handled separately in a library. On top of being a mere translation of the API, this library needs to cater to both API providers' and consumers' needs alike in their language. That’s what makes great SDKs.