Closed akayrak-adesso closed 4 years ago
Network stubbing (generally speaking) is made with various way;
All of these methods have their own pros and cons against each other.
Common sides
Nearly all libraries for these methods provide responses via file, JSON data, or with hardcoded strings. All cover various response status codes. All provides delay for requests, but some libraries make the delay endpoint base, some make it run instance base. Nearly all covers dynamic responses, which means for different request query, the same endpoint responses differently.
Info & Maintaining
External one means one more application and project, that we need to deal with (-), beside the mobile app. It may or may not be written in swift. Being a distinct project makes it more flexible (+) to do the stuff we may need. However, maintaining it with new endpoints may be neglected because of its being not in eyesight and need of all the time (-).
Discuss: Is it possible to have a swift mac-os server in the same workspace with our app?
In-app in-memory local servers are, as its name applies, in the same project with the mobile application, running locally on the device within the app. Maintaining them would be easier than external ones cause they are on eye-sight an also eligible to write unit tests in the workspace for its existence (+). For the tests, there are two approaches to create it. One is for just initing the necessary endpoint and request for the test. The other is initing all requests from one single point. First approaches maintaining would be higher (-) than second; because may init the same request multiple times for different places. But the second approach maintaining requests' cost is nearly the same for the external server's cost (+).
Interception method is kinda different than the others. With this method, the requests are not going out from the network layer; they are stubbed before. The maintenance cost is the highest (-). Although the stubbing looks very similar to the previous method's initing necessary requests for that test, it has a couple of drawbacks. If you are using a framework other than Alamofire or URLSession, there is no specific solutions/library for that stubbing. You have to stub manually that calls (-).
Usage Areas & Drawbacks
External local server method is both for general usage (+) while developing application when we do not have or have limited access to the backend system, and while making unit and UI tests with mock services (+). The local server's being of completely different process from the mobile application, there will be no memory, thread, or any other app-wide related problems.
In-app In-memory local server method is mostly used in UI and Unit testing (+). I think that it is also possible for general use but haven't seen anybody using it in that way. As this method is integrated within the application, it will use the same device resources. So it may have a bit creates performance issues on the edge cases.
The stubbing method is only for testing, not for general usage. Stubbing does not actually simulate whole network connections, so it may have resulted in overlooking some problems.
One other aspect of drawbacks is the approaches' code penetration with the app's non-test code base. The external approach has only the IP/address of the localhost (+) in the app's code, to point the server. In-app server's however, have its complete code (-) base may be resulted in sending it to production release. For the third option, stubbing has nearly no integration (+) with the non-test part of code.
Result
Before proceeding to a deep examination of possible tools/libraries, we need to decide the approach first.
When we examine in-memory servers written in Swift that can run on iOS along with an app, we can find lots of libraries in various sizes. But we will examine 5 of them which are either just popular or backed by corporate companies.
Ambassador by Envoy, Shock by JustEat, SwiftLocalhost, Swifter, and Kitura - by IBM.
Kitura was a very popular and high demanded library until 2019. But IBM pulled its support from it by the end of last year. So we have to eliminate Kitura because it may become idle very soon and community support is uncertain right now.
Let's move to compare the others.
Ambassador is supported by Envoy and be actively used in the company's projects on UI testing. Shock is supported by open-source supporter company JustEat. They have created it from just their need, it is pretty much simpler and smaller than others. SwiftLocalhost is one person supported framework. It is simple and small like Shock, with a couple of different features. Swifter is kinda big brother here with 72 contributors and much bigger community than the others'.
Here below is a comparison chart for these four libraries. | Ambassador | Shock | SwiftLocalhost | Swifter |
---|---|---|---|---|
Same endpoint Different Request Method | No | Yes | Yes | Yes |
Lazy Response JSON File | No | Project Resource Path | No | Computer File Path |
Parameter as Input on File Response | N/A | No | N/A | No |
Parameter as Input on Custom Data Response | Yes | N/A | Yes | Yes - A bit of work |
Delay | Yes | No | Manual - sleep on data | Manual - sleep on data |
Community - Star | 141 | 14 | 54 | 3000+ |
You can find examples of request handling with these libraries in this gist.
https://gist.github.com/akayrak-adesso/577924a9919ad9abc216f0024f756256
@akayrak-adesso Great work!!
We have decided to use Swifter.
Possible networking data mocking frameworks should be analyzed.