iOS for Javascript Developers

Diego Watanabe
Broadlume Product Development
6 min readJun 21, 2017

You are a Javascript developer working at a startup with only two other devs. You build your web app and back-end together using React and Node but your sales team keeps promising people an iOS app that doesn’t exist. The circumstances don’t really matter, but you have a few months to deliver an iOS application.

What do you do? Depending on your team’s experience, you may hear a few options, such as building a PhoneGap application, using React Native, good old Objective-C, or modern, flexible Swift. You could spend more time arguing for or against any of these methodologies than writing code, but at the end of the day, there is no silver bullet that will automatically create an iOS app for you. This is a long process that requires careful consideration regardless of which way you decide to go.

Why Not Javascript?

If your team is predominantly web devs with Javascript experience, it is likely that they’ll want to try using React Native or PhoneGap as they both use technologies and workflows familiar to web devs. This opinion is valid and, if your team really lacks the resources and the time, it could be your best bet.

I have nothing against PhoneGap, but each application that I’ve tried to build with it has poor performance and an experience that is not quite as polished as a native iOS or Android app. The real positive here is that PhoneGap truly does deploy to both platforms while React Native requires some platform-specific code. However, this advantage is costly because PhoneGap apps in the end require much more effort and tinkering with to get them to match the native experience while React Native does not.

React Native applications feel almost the same as native ones, but they lose the ability to deploy on Android and iOS using the same code. If your team really wants to stick to Javascript, React Native is the choice I would go with. It’s written in Javascript and you can build iOS apps with just your JS skills after reading a few short pages of documentation. You could even share some of the non-ui code between your iOS app and your web app which can potentially save you a lot of time.

XCode vs Modern Web Development

I’m a big fan of React Native and admire the way Facebook was able to bring Javascript to the iOS platform in a simple way, but that approach itself is also the problem I have with it. By using React Native on iOS you are bringing the dependency hell that is modern web development into a platform that should be simple to use and get started on. The beauty of using Xcode and Swift/Objective-C is that everything comes in a nice little package.

All of your files, build scripts, settings, and more are contained within Xcode. Apple doesn’t want you to deal with any issues with deploying, debugging, compiling, building, or archiving. With Swift, you even get a modern language that has everything you could possibly want out of the box! Libraries such as UIKit and NSURLSession also provide everything you need to build beautiful UIs and integrate with your favorite backends or third-party services. The only setup iOS requires is using CocoaPods or Carthage to manage your dependencies. This also makes it simple to onboard people onto the iOS project and hire new developers because you don’t have to spend as much time on setup.

Getting Started with Xcode

Within a few minutes you can have an environment set up with everything you need for iOS development out of the box. Including a modern, strongly-typed, flexible language in Swift or a mess of weird brackets and syntax (that still works well) with Objective-C. In order to accomplish the same thing on a React webapp, this requires quite a bit of work.

If we want to use classes, arrow functions and other modern JS features, we need to use ES6. In order to use ES6 we need to compile our project using a tool such as Babel. To add support for a type system, we need Typescript or Flow. This might involve creating typing files for packages that did not have them already. Everything we did seemed to require another dependency and if you want to have a similar experience on iOS with React Native, you will inevitably follow a similar process.

Brief Introduction to Swift

If you have been using ES6 and Typescript, Swift will feel very familiar. Swift is strongly typed and has an object-oriented model similar to Java. It is not prototype-based, like JS. Swift also has many of the nice functional programming features and higher-order functions Javascript developers use such as map, reduce, filter, etc. I believe Swift will also feel familiar to anyone coming from writing C# or Java also because the OOP concepts remain the same, only the syntax will be slightly different.

Swift will also surprise you with a lot of useful features and patterns that the language supports such as computed variables, extensible protocols(interfaces), and functions as first-class objects. Your code doesn’t necessarily need to take advantage of all of the new features but once you adopt some of these, it is hard to go back.

Structural vs. Nominal Typing

Swift and Typescript are both strongly typed but Swift is nominal and Typescript is structural.

Swift

In Swift, every instance of a class must be instantiated from the named class definition. As a result, it will have all the properties that the named class defines. If an object is not instantiated from the same named class definition, then the types are incompatible. This is slightly different from Typescript because Typescript uses a structural typing system. This allows you to create an anonymous object that has the same properties that a class defines, and the type system will see this object as a member of that class.

Typescript, this taken from the Typescript handbook section on interfaces.

As mentioned in the TypeScript handbook, say for instance we have an interface called Namedin TypeScript, and a Namedobject has a property name of type sting. Then we declare a variable named X and define it to be of type Named. If we were to then create an anonymous object named Ythat contains the properties name and location each of type string, then because of the structural typing system, Typescript will accept assigning Yto Xeven though it is not explicitly of the type Named because name: string is a subset of the properties available on the y object.

Optionals

Swift has optionals which can seem a bit pointless at first but you will quickly learn to love them. Optionals are values that may be something or may be nil. This allows you to be very explicit about which variables must always be there and which could be nil. This also removes the need for nil-checking variables in Swift because the language handles the nils using optional bindings or guard statements that will fall through if nil is found.

Typescript also allows you to define both optional variables and function parameters (even though I’ve met many that choose not to use these). Typescript uses control-flow based type analysis to determine whether a given variable is nullable. For example:

Conclusion

In conclusion if you wanna build an iOS application, I really think you have two viable options: to use React Native with ES6 and Typescript, or native Swift iOS development using XCode. While I definitely have a bit of a bias towards using Swift, I will say that it doesn’t come without faults. Apple retains tight control over the ecosystem which makes it hard to extend and customize your development environment. The Swift project is still rather new and has growing pains that are then pushed to developers through language updates that will inevitably break your previous code once you update to the latest version of the language. Even still if you are a Javascript developer with some time and resources, I implore you to give Swift a chance since, for the most part, it does provide a fully-fleged, modern development environment and toolchain right out of the box.

--

--