Over the last few months, I have been brushing up on API testing, specifically around contract testing.
According to Postman, an API contract is a human- and machine-readable representation of an API’s intended functionality. It establishes a single source of truth for what each request and response should look like—and forms the basis of service-level agreements (SLAs) between producers and consumers. API contract testing helps ensure that new releases don’t violate the contract by checking the content and format of requests and responses.
If you begin to walk down the road of API contrast testing, one question that naturally comes up is, what tools can I use to identify breaking changes? After all, reviewing a large YAML file on a pull request is not necessarily the best way for humans to spot breaking changes to API contracts.
While researching API Contract testing I came across two tools that help identify breaking changes, Akita and Optic. In today’s post, I would like to explore Optic and demonstrate some of its capabilities and how it can be used to identify breaking changes.
According to their documentation, Optic is a version of control tool, just like Git. In fact, it relies on Git in order to find breaking changes, it invokes a git show command to be able to see a diff between OpenAPI spec files across branches, which means you can use Optic in your existing pull request and since Optic is an NPM package you can import it into any CI provider.
To get started, installed the Optic CLI using NPM.
As of April 2023, the command above will install version 0.42.13. With Optic now installed you can use the diff command to compare two OpenAPI specs. Below you will find an OpenAPI specification file that I have created for this demo.
Might be hard to see from the YAML, but basically, the API defined in the YAML is an API with a /users endpoint, an HTTP client can send a GET request to retrieve a specific user. The users resource exposes the following model.
Let’s assume I want to change the API, say I want to rename the field dateOfBirth to dob, breaking the existing contract exposed by the API, I will modify the contract and save my changes in a change.yaml file and the existing contract will be saved to a main.yaml file. To have Optic identify breaking changes on the contract I can use the following command.
The command above results in the following output.
Don’t know if you can tell from the output, but Optic has successfully identified the change, appending a –web to the command we ran will output the results in a web browser for better visual aid as seen in the screenshot below.
You can also run Optic across git branches using the diff command, you simply would change to the branch containing the API changes and then run the command.
Where –base is the name of the main branch, in this case, the main branch is called main. The –check parameter tells Optic to run the default breaking changes. See optic also offers the ability to apply rules, allowing you to create API standards, for example, imagine that you wanted all properties to be written using snake casing. In optic, you would define the properties casing as snake casing then you would run the rules against all pull requests. Let’s see how that would work, you will find a custom rule definition, I want all my properties to follow snake casing because it is easier to read than camel casing.
Now that I have my rule I can apply it to the previous command.
Optic has identified all properties that do not follow the naming convention defined by my rule. This is great, I can now enforce naming conventions across all resources on my users API.
On an upcoming blost I will explore Akita, the second tools I found for API contract testing, till next time.