How Does Mobile Engineering Work at Clearcover?
Doing things the “easy” way doesn’t always mean it’s the right way. And in some cases, it ends up making things needlessly complicated. At Clearcover, we look to strike the ideal balance of fast but sustainable development. We can’t take months to develop features, but we also want to avoid coding our way into future problems.
My name is Tom Targosz and I’m a senior software engineer at Clearcover, one of the two Mobile engineers at the company. We develop our app using React Native, a Javascript framework based on React that allows us to rapidly build features and deploy to both Android and iOS from one codebase. React Native has been a phenomenal technology for us, allowing us to build an award-winning app while remaining incredibly agile as a small team of 5 including developers, Product, and QA. Most companies need to have two teams for their mobile apps, one Android and one iOS. All technologies have their caveats though and React Native is no different.
We recently came across a challenge while implementing a new SDK for handling sensitive data. Our previous solution in the app was barebones and didn’t allow us to implement all our desired features. We met with the Product Owner of the pod that needed the SDK implementation for his team and he demoed how “simple” it was to add the SDK into our apps. The product has a drop-in component that you simply plug into your app, add a few configurations and the SDK handles all the encryption work. While ideal from a Product perspective - minimal effort to implement is always a good thing - we foresaw two engineering challenges:
Off-brand visuals - Using these drop-in components meant we had to use their styling and aesthetic when we already had a flow developed and running in our app where we were doing this encryption work ourselves. The components allowed for some styling options, but they were pretty limited. We’d have to restructure our UI to accommodate the ‘look and feel’ of the new forms and buttons.
Lost efficiency - The company didn’t offer a React Native SDK, so we’d have to bridge all of the UI pieces for both Android and iOS to leverage this drop-in capability. Bridging to the native layer in React Native is a common practice, especially when dealing with mobile SDKs. But doing it with multiple UI pieces that all need to communicate in their own ways? It’d be a massive undertaking, effectively canceling out any efficiency gained from the drop-in solution.
With these reasons in mind, we voiced our concerns about the complexity of having to architect a custom solution to be able to use these drop-in components. And what was our Product Owner’s response? He said to choose whatever solution we preferred.
This was a huge breath of fresh air for me.
At previous companies, Product Owners’ decisions were usually the law (even if the engineering team had concerns or potentially better solutions.) At Clearcover, it’s a collaborative team effort. The Product Owner outlines the goal, and we implement it the way that’s most effective and sustainable.
Being given the green light to implement the solution of our choosing created the freedom to do some pretty cool work. Beneath the allure of the drop-in components was really just the SDK passing the data to the encryption logic, along with some client-side validation happening. The vendors’ Android and iOS SDKs were open-source so digging into them wasn’t an issue. This allowed me to examine the logic occurring within those drop-in components and extract/replicate it. We now collect all the form data on the Javascript layer like we do throughout the rest of the app and only pass it to the native bridge when we’re ready to encrypt. We also brought the same validation checks that would have been happening through the drop-in components to the Javascript layer. This led to the following wins:
We’re able to pass the necessary fields to the SDKs without having to use their components. This allows us to use our own UI while still getting the same encryption results if we were using the drop-in components. We already had the UI developed so this created huge time savings that would have been allocated to redesigning and rebuilding the flow, and it allowed us to maintain the branding style existing throughout the entire app.
We’re able to replicate the validation logic to keep it in the Javascript layer (instead of on the native layer) and make it platform agnostic. Bridging to the native layer through React Native is an extremely powerful toolkit, but it should only be used when necessary. Having to constantly call to the bridge and wait for the operation to finish just to perform simple validations would have hurt our performance. Furthermore, the validations were not consistent across Android and iOS. For example, on Android the validations happening would take all fields into account, meaning if some fields weren’t yet filled out, the checks would fail. On the iOS side, however, the validations were only concerned with individual pieces of data. This meant that our QA would need to design different tests for different systems, which is something we avidly try to avoid. Building the validation logic ourselves allowed us to avoid both of these issues. We’re running the validations on the JS layer which barely costs anything, and we standardized the validation logic/error messages.
We reduced the size added to our app by only taking parts of the SDK needed. A top reason that users delete apps is due to limited phone capacity. With this in mind, we keep our apps as small as possible. The size of our app once installed is 33.4 MB and 10.1 MB on Android and iOS, respectively. Keep in mind that our industry peers’ apps average around 106 MB on Android and 87 MB on iOS - so we’re doing pretty good.
Due to the function of our app to store a customers’ insurance ID card, provide a place to file claims and make payments, we are sensitive to the idea of a customer uninstalling our app due and then being without it in a time of need. We were able to import just the encryption logic since we didn’t need the UI portions of the SDK and in turn, save a great deal of space.
Our eventual solution wasn’t the obvious one, but it ended up being a massive win across the board. If we had implemented the vendor’s recommendation, we would have lost out on all the benefits listed above. Plus, our app would have been more prone to bugs due to the complexity of the UI native bridging.
Having our Product team trust our judgment was a critical asset. Engineering teams might not always have the correct answer right away, but being given the freedom to explore unique solutions fosters an environment where thinking outside the box is encouraged and leads to some awesome discoveries.
This kind of problem-solving occurs every day at Clearcover.
Interested in being a part of it? See our open jobs.