J2ObjC. Cross platform development - Google way

J2ObjC. Cross platform development - Google way

The presentation was given at: https://devfest.gdg.org.ua

The war between mobile platforms is over. After several years of active competition, we’ve got two operating systems with almost the same quality and feature set.

For mobile developers this means that all further projects should target at least two platforms. In this talk, Vitaliy wants to share results of internal R&D experiments at GetSocial with J2ObjC – Java to Objective-C translation tool developed by Google.

J2ObjC goal is to write an app’s non-UI code (such as application logic and data models) in Java, which is then shared with no editing by Android and iOS apps.

F456ed67b75e58e533d11b301f5f62b5?s=128

Vitaliy Zasadnyy

September 10, 2016
Tweet

Transcript

  1. Cross platform development - Google way J2ObjC Vitaliy Zasadnyy Head

    of Mobile @ GetSocial
  2. In yellow boxes like this one you can find comments

    to the slide. Enjoy the presentation and if you have any questions, feel free to reach me at v@zasadnyy.com
  3. #dfua hard Cross platform development is

  4. #dfua 70% code reuse Source: Gmail Blog

  5. #dfua 25+ projects Google is using J2ObjC for almost all

    office apps. Besides Google, more than 25 projects claimed using J2ObjC.
  6. Now I’m leading mobile department at Dutch startup GetSocial

  7. With help of GetSocial SDK you can add Activity Feed,

    Chat, Notifications or Smart Invites just with a few lines of code
  8. SDK is available for Android, iOS, Unity and Cordova

  9. 30M 50+ 500M APPS & GAMES MONTHLY USERS TOTAL SESSIONS

    With over 50 integrated apps, GetSocial serve 30 million users every month that generated half a billion sessions during 2015.
  10. #dfua GetSocial SDK architecture Android SDK iOS SDK iOS Bridge

    Android Bridge C# API Unity SDK Java Objective C C# We have Android and iOS SDKs built natively using Java and Objective C respectively. Unity SDK is a thin bridge layer that forwards calls from public interface exposed in C# to native implementation
  11. #dfua GetSocial SDK architecture THE GOOD: • Easy to leverage

    all platform features • Doing work twice • Hard to keep in sync API behaviour THE BAD: The biggest advantage of having pure native SDK - being able to use low level platform features. Disadvantage - all features are implemented twice (longer time to market), also it’s hard to keep behaviour in sync, coz each developer has unique way to solve problems.
  12. –Sun Microsystems Write once, run everywhere “ We decided to

    look around on possible solutions, to reach ultimate goal, write code once and run it everywhere.
  13. #dfua Requirements Maintainability Performance Size footprint Licensing Requirements for the

    solution: - performance should be at least the same as on native - code should be easy to maintain (reliable toolchain) - SDK should keep reasonable size - ideally solution should be free and compatible with our distribution model
  14. #dfua J2ObjC Xamarin XmlVM RoboVM We did a research on

    what tools were available on a market. Some were not performant enough, some were not suitable for SDK development.
  15. #dfua J2ObjC All except J2ObjC. Project started and actively developed

    by Google. Inbox built with J2ObjC. We started an internal RnD project to research if J2ObjC can fit with our requirements.
  16. #dfua Dive into J2ObjC Let’s look more close on the

    key features of J2ObjC.
  17. J2ObjC - WTF? Build configuration Development process Project impact The

    grand plan @zasadnyy
  18. #dfua What is J2ObjC? • Source-to-source compiler • Focus on

    shared business logic • Apache 2 Licence
  19. #dfua • NOT cross-platform application tool • NOT platform-independent UI

    toolkit • NOT Java emulator • NOT one time source translation What J2ObjC isn’t
  20. #dfua Is it production ready? v1.0.0 January 21, 2016

  21. #dfua What is supported? • Full Java 7 syntax •

    Inner classes, enums, annotations… • Reflection • JUnit test translation • OCNI code embedding J2ObjC engineers did a great job, they reimplemented Java paradigms like inner classes, enums, annotations and reflection on Objective C, where they are not available.
  22. #dfua OCNI code embedding static native void log(String text) /*-[

    NSLog(@"%@", text); 
 ]-*/; Java code You can embed Objective C code in Java in a special comments.
  23. #dfua OCNI code embedding static native void log(String text) /*-[

    NSLog(@"%@", text); 
 ]-*/; + (void)log: (NSString*)text {
 NSLog(@"%@", text); 
 } Translated code DON’T do that, little bunnies die each time you’re using OCNI.
  24. #dfua Build configuration

  25. #dfua How to use $ j2objc DevFest.java $ ls DevFest.h

    DevFest.m translating DevFest.java Translated 1 file: 0 errors, 0 warnings j2objc is a command line tool, you’re going to work with to perform translation from Java to Objective C. It’s very powerful, but not very convenient to use on a real projects, coz amount of passed parameters will explode.
  26. #dfua Available plugins Make Eclipse Gradle Maven J2ObjC provide a

    plugins for most part of popular build tools. We’re going to focus on Gradle plugin.
  27. #dfua Gradle plugin • Easy integration • State of art

    codebase The good Bruno Bowden Advay Mengle • Rockstar authors
  28. #dfua Gradle plugin • As of July 25 is not

    supported • Last supported J2ObjC version is 0.9.8.2.1 • Last supported Gradle version is 2.8 • Check our fork at https://github.com/getsocial-rnd/j2objc-gradle The bad Main problem with j2objc-gradle plugin - it supports only Gradle up to v2.8. Android on the other hand to support latest features requires 2.9+. Big part of plugin need to be rewritten to support new project model introduced in 2.9.
  29. #dfua Setting up iOS project • Automatically via CocoaPods •

    Manually link binaries THE GOOD: THE BAD: • Impossible debug
  30. #dfua Setting up iOS project Xcode Project Default flow Java

    Source ObjC Source Static Library
  31. #dfua Setting up iOS project Xcode Project Java Source ObjC

    Source Static Library GetSocial solution Python script
  32. #dfua Build time optimisations • Build only debug binaries •

    Include only target processor architectures Default: ios_arm64,ios_armv7,ios_x86_64 • Set up single platform builds
  33. #dfua 6 min <2 min *Android + J2ObjC build GetSocial

    case Build time optimisations
  34. #dfua Development process

  35. #dfua Project structure workspace ├── build.gradle ├── android │ ├──

    android-demo/.. │ └── android-library/.. ├── ios │ ├── ios-demo/.. │ ├── ios-library/.. │ ├── ios-shared │ └── WORKSPACE.xcworkspace ├── lib │ ├── rx-java │ └── gson └── shared ├── src/.. └── build.gradle Shared code GetSocial case
  36. #dfua Libraries sources Project structure workspace ├── build.gradle ├── android

    │ ├── android-demo/.. │ └── android-library/.. ├── ios │ ├── ios-demo/.. │ ├── ios-library/.. │ ├── ios-shared │ └── WORKSPACE.xcworkspace ├── lib │ ├── rx-java │ └── gson └── shared ├── lib/.. └── src/... GetSocial case
  37. #dfua Project structure workspace ├── build.gradle ├── android │ ├──

    android-demo/.. │ └── android-library/.. ├── ios │ ├── ios-demo/.. │ ├── ios-library/.. │ ├── ios-shared │ └── WORKSPACE.xcworkspace ├── lib │ ├── rx-java │ └── gson └── shared ├── lib/.. └── src/... iOS code GetSocial case
  38. #dfua Project structure workspace ├── build.gradle ├── android │ ├──

    android-demo/.. │ └── android-library/.. ├── ios │ ├── ios-demo/.. │ ├── ios-library/.. │ ├── ios-shared │ └── WORKSPACE.xcworkspace ├── lib │ ├── rx-java │ └── gson └── shared ├── lib/.. └── src/... GetSocial case Android code
  39. #dfua

  40. #dfua J2ObjC enforces Clean Architecture THE GOOD

  41. #dfua Presentation Clean architecture Drivers Frameworks Domain Dependency Rule shared

    XXX-library XXX-demo
  42. #dfua Libraries • Sources required • Not all java packages

    implemented • Tests are highly recommended
  43. #dfua dependencies { compile ‘com.google.code.gson:gson:2.6.2’ } j2objcConfig {
 autoConfigureDeps true


    } Libraries shared/build.gradle If OOS library has sources and test published together with a binaries, you can ask j2objc plugin to pull them and cross compile. But we managed to get it working only for Gson.
  44. #dfua workspace ├──... ├── lib │ └── rx-java │ └──

    build.gradle └── shared └── build.gradle GetSocial solution Libraries Set-up J2ObjC translation Include library project More universal way is to create a new project with library, set up j2objc cross compilation for a project and include it as a dependency into shared module.
  45. #dfua Check ported libs at j2objc-common-libs-e2e-test GitHub project Junit, Hamcrest,

    Mockito, Protobuf, Guava, Gson, Joda-time, commons-lang3, sqlighter-4 PORTED: AssertJ, RxJava, http libraries, DI, … MISSING: Libraries
  46. #dfua Unit testing is the DNA of J2ObjC THE GOOD

  47. #dfua High test coverage is the only way to confidence

    THE BAD
  48. #dfua Testing • JUnit 3, 4 • Hamcrest 1.3 •

    Mockito 1.9.5 Toolchain
  49. #dfua • Narrow selection of testing libs/frameworks • Util classes

    in tests are being executed => FAIL • Thread.sleep(0) hangs Testing The bad The easiest way to solve the problem with util classes being run as test is to agree on convention of Test suffix for all text classes + providing exclude pattern for tests in j2objc grade plugin config
  50. #dfua Name mangling package com.zasadnyy.reddit.model; public class RedditDataManager {…} @interface

    ComZasadnyyRedditModelRedditDataManager : NSObject Translates to Class names Check the demo repo for more examples
  51. #dfua Name mangling String foo(int i); - (NSString *)fooWithInt:(jint)i; Translates

    to METHODS
  52. #dfua Name mangling The good j2objcConfig {
 translateArgs '--prefixes', 'packagePrefixes.properties'


    translateArgs '--mapping', 'methodMapping.properties'
 } • @ObjectiveCName(“”) • Method/package mapping configurations Gradle plugin provides configuration closure to setup package and method names mappings
  53. #dfua Name mangling The bad RedditDataManager.init(Ljava/lang/String;)V = VzRedditDataManager initWithAppId:(NSString)appId Method

    mappings are fragile Any refactoring of the method or change in package mappings will break your method mapping configuration
  54. #dfua Name mangling GetSocial solution Package prefixes Set of wrappers

    + We ended up using package mapping + wrapping all generated code on the ObjC side
  55. #dfua Project Impact

  56. #dfua Performance Make simple computations on the array of 600

    GPS coordinates 1,000 times Testing method: Computational Source: Medium post by Harry Cheung
  57. #dfua Computational Average iOS Computational Performance Swift 1.2 J2ObjC J2ObjC

    (ARC) Xamarin RoboVM Time, s 0 0,275 0,55 0,825 1,1 Performance
  58. #dfua Make simple computations on the array of 600 GPS

    coordinates 10,000 times Testing method: Source: Medium post by Harry Cheung Performance Memory
  59. #dfua Peak iOS Memory Performance Swift 1.2 J2ObjC J2ObjC (ARC)

    Xamarin RoboVM Usage, Mb 0 5 10 15 20 Performance Memory
  60. #dfua iOS app size impact 3Mb Extra (1 target platform)

    Reduce size: • Include only required parts of jre_emul.a • Shrink unused Java code with Proguard 3Mb is mainly a size of translated JRE library that should be included with your project.
  61. #dfua Team impact • iOS Developers have way less work

    • Developers should be familiar with both platforms
  62. #dfua At a glance

  63. #dfua At a glance • Unsupported Gradle plugin • Limitations

    on dependencies • Unit tests as the only way to validate logic THE BAD:
  64. #dfua At a glance THE GOOD: • Performance • Maintainability

    • Reasonable size footprint • Apache License • Clean architecture
  65. #dfua 64% code reuse At a glance

  66. Thank you! Questions? Vitaliy Zasadnyy @zasadnyy Slides will be available

    at: v.zasadnyy.com/slides/ Дякую за увагу!
  67. #dfua We are hiring ninjas! • Android (UA/NL) • Golang

    (UA)
  68. #dfua Resources • Official J2ObjC website • J2ObjC on GitHub

    • J2ObjC Gradle Plugin on GitHub • GitHub project with end-to-end test of compatible libraries • Goodow GitHub account with several J2ObjC related repos • Cross platform frameworks performance tests • Demo project