You (probably) don’t want a hybrid app

We are regularly approached by potential clients who want to help us build or maintain mobile apps. Many are interested in hybrid apps : HTML5 web apps that run in an embedded browser, with common code across iOS and Android. Typically, this use a framework as Cordova (aka PhoneGap) which wraps a web app for distribution and provides access to some device-specific APIs.

The apparent cost savings of these apps are obvious, especially if your organization already has the skills to develop web sites. And as developers, we’re all about saving effort and not writing everything twice.

Our experience, however, is that hybrid apps carry hidden costs that are not immediately obvious. At Zuhlke Engineering Limited in the UK, we now advise our clients that, in virtually all cases, it’s better to build native versions of the app for each platform you want to target.

This is not all hybrid apps are bad, or that’s impossible to build a good one. For some use cases, hybrid apps are a good fit, but this is the exception rather than the rule.

First impressions count

For a mobile app, user experience is everything. Make it convenient to try things out. If someone tries your app and it takes more than a few seconds to start, or has an unpleasant or sluggish user interface, they might leave a bad review, or (worse still) just try something else.

iOS has extensive Human Interface Guidelines , and Google has similar guidelines for how to use Android app should look and work. Users expect the apps on their phone to use their standard UI patterns, like the rest of the apps on their phone. For example, to go “up” in an information hierarchy on iOS, you swipe from the left edge; on Android, there’s the physical ‘back’ button, but no swipe gesture. If you’re building a web app from scratch using Cordova, you may have to consider this as yourself, for both platforms.

You can save yourself some work with a framework such as Ionic, which bundles Cordova with Angular, some stylesheet, extra build tools, and some components that render the expected behavior on each platform. But these may be more difficult to control.

Alternatively, you could do the same on every platform. But this might only be acceptable in a few circumstances. In most cases, if you’re deploying your app to the public, you can expect something’s off, or get confused by unfamiliar UI patterns.

When it comes to performance, Apple recommends it’s a good launch time target for iOS app is 400ms on the slowest supported device. If your web app uses Angular (which is bundled with Ionic) your users will have to wait for that to load, and this can take a long time. IPhones, and even worse performance on Android.

Animations and interactions are so slower implemented as CSS inside a web browser than when implemented natively. Pages might flash when loading. Even scrolling behavior is different, and usually more sluggish. You may decide that this is an acceptable trade-off.

The situation is worse when it comes to supporting phones’ built-in accessibility features. Native components are accessible by default, and VoiceOver and Talkback behave predictably around them. Web components, especially custom modals, menus, and alerts, do not. You may well have to re-implement the logic to trap modalities, move the screen reader to the correct element, etc. yourself. You may decide this is an edge case did you do not care about, but accessibility is usability, and if your app is being released to the public, it’s not unreasonable for disabled people to expect your app to support the features They rely on .

The shared-effort fallacy

A common motivation for hybrid apps is to use the business logic and user interface once without iOS.

This is usually true until you find the feature on the device, as the camera or fingerprint reader. Cordova’s plugin architecture allows JavaScript to invoke native code on iOS and Android, and there are ready-made plug-ins available for basic functionality, as well as taking a single picture from the camera or verifying a single fingerprint. But for everything else, you’ll have to write the code yourself. In practice, it’s almost impossible to avoid writing some native code.

Sometimes a feature wants to exist on one platform, but not another. The result is often a codebase that is full of per-platform code: “iOS, run this long, intractable code block;” if it’s Android, run this other, subtly different code block. “It looks like two separate code bases merged into one, because it is.

80% of the time, it certainly saves 80% of the time, and reduces costs by 80%? This only works if you ignore the costs of testing . Unit tests are worthwhile, but it comes to mobile apps, it’s even more important to test on real devices-especially on Android, where different phones have wildly diverse performance and feature sets.

It’s worth noting that the iOS and Android web browsers have subtle quirks and differences. Internet Explorer know this is a chimera. The quirks in the different platforms’ browser implementations can lead to platform-specific bugs which you may not know about … until your users report them.

An annual barber’s appointment for Mr. Yak

Mobile platforms move almost. iOS now receives a major update every single year in mid-September. Major Android releases happen every year too, although hardware releases are significantly slower. With these releases come new features, which may be supported ‘for free’ by the platform; new releases thus bringing deprecations, and breaking changes to the APIs.

Your users would like to have their device updated. This is why in advance of the new OS’s general availability.

In mid-July 2015, a bug Which raised against Ionic and Angular on iOS 9 beta 3. A regression in UIWebView‘s window.locationimplementation Caused Angular apps to end up in a infinite loop digest, Effectively breaking navigation. A workaround for this bug given by the Angular team on 11th of September, two days after the iOS 9 Golden Master was released UIWebView. In the Ionic team’s blog post on 12th September, they wrote :

there’s time to make the ASAP […] unfortunately, we assumed that would be fixed in time but they were not.

Given that the App Store could not be fixed to push, it could not be fixed in time. Caused by Angular or Ionic, but in iOS itself. But from a user’s perspective, it made no difference. The apps were broken on iOS 9.

With Cordova, there are three places from which regressions or breaking API changes can propagate upwards and present as defects to the user: they could be in the iOS and Android APIs, or in Cordova itself. Ionic adds two extra layers (Angular and Ionic itself) on top of this thesis. That’s five huge, complex dependencies for your app you need to keep abreast of. The rat’s nest of NPM dependencies many Javascript apps.

Cordova wants to generate 11 deprecation warnings when opened in Xcode. Plugins can add dozens to this figure. And Cordova still does not support the iPhone X’s edge-to-edge display out of the box, over six weeks after it was released.

In a world where hardware and software moves so close, is it sustainable to rely on a complex web of dependencies to make your app look nice-or even work at all-on the newest platforms and devices? The dependencies that matter the most are the operating systems and their APIs.

Thirteen amps and three square pins

Most of us want to travel to a menagerie of power adapters at home. My own electronics scrapyard has at least three UK-to-mainland Europe adapters (only one of which fits hexagonal Swiss sockets) along with a pair of American adapters.

A lot of the cheaper adapters on the market are awkward to squeeze into the UK because of small violations of the BS 1363 standard. Some are loose, which is even worse because of the risk of exposed contacts. At best, this can lead to a tenuous power supply; at worst, it can lead to damaged equipment, fire, and electrocution.

This may be acceptable if you need to charge your phone in a hotel room for a few nights. But it’s a hack. If you were the manager of a New York and Amsterdam office, you would not be happy with the kit in the UK,

This is the problem with hybrid apps. They are a hack. A hybrid app wants to work normally, just about. But they typically provide a sub-par user experience compared to native apps, and less flexibility than comes with just building a website. If you want to associate your brand with a mediocre user experience.

And then there’s the problem behind the scenes: your complex web app is encased in a hybrid app framework, which is itself encased in a complex scaffolding of native code. The whole stack appears like one of the contraptions in the Wallace and Gromit films, supremely intricate and impossible to understand or maintain. At this point, your team needs more than generic web skills to progress. You might as well have written a native app.

The temptation of familiarity and reduced effort is obvious. But for anything remotely complex, development can be out of control into yak-shaving or painstakingly trying to reproduce weird rendering bugs. I’ve been that too many times to recommend hybrid apps as a good mobile strategy.

Comments (3)


19 January 2018 at 20:12

So true. Saw a lot of hybrid apps with motivation to save budget. All did not match expectations and were more expensive then true native apps. Same with Xamarin.


21 January 2018 at 10:59

Very true. That said, part of the motivation is also expertise and skills gap.

    Jonathan Rothwell

    Jonathan Rothwell

    22 January 2018 at 13:30

    Of course. This is a classic anti-pattern in our industry. People tend to try and do the easiest stuff first, when all the risk is in the difficult stuff.

    It’s almost impossible to avoid doing at least some native development with a mobile app. The more you kick that unknown stuff into the long grass, the harder, riskier, and more expensive it will be to learn the native skills you need to fix that one weird rendering bug or that crash with some exotic custom Android launcher.


Sign up for our Updates

Sign up now for our updates.

This field is required
This field is required
This field is required

I'm interested in:

Select at least one category
You were signed up successfully.