Is that your experience too, that a good bit of native code is required (with RN serving as glue and handling simple screens), or have you avoided that somehow?
Check out the code examples: https://facebook.github.io/react-native/docs/native-modules-...
In practice, most of it is wrapping "RCT_EXPORT_METHOD" around native code and importing it into JS.
Even if you had to write half the app in native code (which you won't), you're still far ahead of having to write it all in native code on both platforms.
The bridge creates an interface between an embedded webserver to react native.
Things to note:
1. Always dispatch bridging methods to their own threads. On IOS you can do this via. dispatch_async. On Android, you can utilise native threads or some kind of task management library. I like Bolts [2].
2. Always create bridging methods that resolve promises. This makes it easy to utilise async / await paradigm on the JS side.
[0] Android: https://github.com/hemantasapkota/react-native-web-server/tr...
[1] IOS: https://github.com/hemantasapkota/react-native-web-server/tr...