Debugging Chronicles: Debugging with Proxy Tools

İrem Tosun
adessoTurkey
Published in
5 min readJun 12, 2024

Debugging is a vital skill for any developer navigating the ever-evolving landscape of software development. In this article, I will demonstrate how to debug network requests and responses while developing mobile applications. Using Proxyman as our primary tool, I’ll provide examples across various scenarios to illustrate its capabilities. By the end, you’ll gain a comprehensive understanding of when and why proxy tools like Proxyman are indispensable.

What are Proxy Servers?

Proxy server operates as a “man-in-the-middle”. This means that it intercepts communication between a client (such as a mobile device or computer) and a server. By sitting between the client and the server, it can capture and analyze the traffic passing through it, allowing developers to inspect, modify, and simulate network requests and responses. This capability is particularly useful for debugging and testing purposes in mobile and web development, as it provides visibility into the data being exchanged and enables developers to identify and address issues more effectively.

Recommended proxy tools that are paid.
Recommended proxy tools that are free.

Debugging Network Responses with Proxyman

With the power to monitor, analyze, and manipulate HTTP/HTTPS requests, Proxyman is a robust and easy-to-use proxy tool that can greatly improve your debugging skills.

Scenario 1: Debug How to Handle an Irreproducible Case

The backend changed the implementation and decided not to send episodes anymore. We do not have such a record in the real environment and are unable to debug it with any of the records. This is when Proxyman’s Map Local tool comes into play.

In order to start mocking with Proxyman, you first need to install Proxyman’s certificate onto the device you are going to use for debugging.

First step is to make sure proxyman certificate is installed on device/simulator.

Check if it’s working as expected: I can inspect the web responses like that.

I am able to inspect the responses after running the app in debug mode.
Original display of the record that I am going to mock.
Original display of the corresponding record before mocking.

Now let’s modify the response of the record with id 20.

Configuring the endpoint that I want to mock.
I removed the episodes information completely.
Make sure you select enable Map Local Tool and the configuration you want to activate below.

Let’s re-run and see how it responds. I am expecting to encounter a bug since I haven’t taken any actions for that case before.

I see the expected error when I try to open the related record now.

Time to Fix:

Now let’s figure out how to fix the bug for this case. In my current implementation, I never expect episode field to be absent, so my decoder expects to decode each coding key. Now that the episodes has become optional, it is time to make it optional.

import Network

struct Figure: HTTPResponseProtocol {
typealias HTTPEntityType = Figure.Type

let id: Int
var name: String
let status: CharacterStatus
let species, type: String
let gender: CharacterGender
let origin, location: Location
let image: String
let episode: [String]?
let url: String
let created: String

enum CodingKeys: String, CodingKey {
case id
case name
case status
case species
case type
case gender
case origin
case location
case image
case episode
case url
case created
}
}
let episode: [String]

By making this variable optional, the app will be able to handle this edge case without any crashes or unexpected behavior.

let episode: [String]?
Fixed the bug when episodes list is not received at all from the web api.

Scenario 2: When a New Feature Added

Suppose the product owner has added a new feature. All of its details have been determined; however, the backend has not published the change yet. You can save time by using Map Local to debug the new feature.

In my example, I am going to add a new variable to Figure called hobbylist.

enum Hobby: String, Codable, CaseIterable {
case sports
case music
case dance
case baseball
case picnic
case movies
case art
case travelling
case gardening
}
import Network

struct Figure: HTTPResponseProtocol {
typealias HTTPEntityType = Figure.Type

let id: Int
var name: String
let status: CharacterStatus
let species, type: String
let gender: CharacterGender
let origin, location: Location
let image: String
let episode: [String]
let url: String
let created: String
let hobbyList: [Hobby]?
}

I need to make this field optional, since it won’t be implemented for real in my example.

let hobbyList: [Hobby]?
Added the new feature hobbyList to mock response.

Then, when I run the project and set a breakpoint inside my getCharacter function, I can see the hobbyList as expected.

HobbyList is decoded successfully with the mock response.

Time to Use HttpClients

In scenarios where you don’t have a server to intercept, you can indeed use HTTP clients to simulate server responses. By using HTTP clients, you can create mock responses and simulate various server behaviors without needing an actual backend server. This approach is particularly useful during early stages of development or when backend services are unavailable.

Debug When Production API is not ready

Mock servers are essential for ensuring seamless development, testing, and prototyping processes when the backend is not yet ready or available. Tools like Postman Mock Server, JSON Server, Mockoon, WireMock, and Mountebank provide various options to create and manage mock APIs efficiently. By using these HttpClient tools, you can work independently of backend constraints, leading to faster and more reliable project delivery.

If you are interested in using Postman Mock Server, you can take a look at this article where I provide detailed instructions on how to configure a mock server in Postman.

Summary

If you are interested in debugging in terms of all aspects, please take a look at my previous articles as well.

Postman for Network Debugging

A Journey into View Layer Debugging Mastery

Exploring Breakpoints, Conditions, LLDP Commands, and Watchpoints

--

--