WhoBuilt

Media Rich App Best Practices

Oct 9, 2019· 23 min· 815 views·Watch on YouTube

Speaker

React Native core contributor Dulmandakh Sukhbaatar of a Mongolia-based music streaming service explains at React Native EU 2019 how his team used React Native with native modules to build media playback and offline features.

Why the team chose React Native

The team could not find a ready-made licensed music platform, so it began building its own service, with a React web app and React Native apps for Android and iOS. Sukhbaatar chose React Native partly because hiring native developers was difficult and sharing code could help the team move faster. The team built more than 50 screens and shared UI and business logic in JavaScript.

Making playback work in the background

Music apps need to support playback from lock screens, Control Center, Android notifications, headsets, cars, and Bluetooth devices. They also need to handle calls, other media, headset removal, network failures, DRM licenses, and offline playback. Because Android cannot run JavaScript while the app is in the background, the team made the native player the source of truth for playback state.

Keeping frequent updates off the bridge

The player manager lets React Native set a queue and play a track, read player state, and subscribe to progress, queue, track, and state changes. The team built six custom native UI components, including a progress bar and slider, to avoid sending frequent events across the bridge for JavaScript to process. Native components handled behavior such as showing an indicator, while React Native controlled styling such as size and shape.

Handling downloads and large libraries

Offline support required downloading images, audio, and DRM licenses, storing metadata, and checking that each part was ready before confirming a download. Keeping download state synchronized across native and JavaScript code became difficult, so a native download button handled its own status display while React Native controlled its appearance. The team also added native pagination after a library with thousands of tracks caused the list to load everything at once.

Lessons for native integration

Sukhbaatar recommends starting with React Native and adding native code when a feature requires it, while keeping bridge payloads small. He advises using dedicated threads or dispatch queues and React Native tools such as Fresco, OkHttp, and YogaKit. He also stresses understanding platform rendering and concurrency, including Kotlin or Swift and platform-specific queues or threads.

Takeaways

  • Make the native player the source of truth when playback must continue without JavaScript running.
  • Keep high-frequency playback updates in native UI components to reduce bridge traffic.
  • Separate component behavior from presentation: native code can manage state while React Native controls styling.
  • Plan offline downloads as a coordinated process for media, licenses, and metadata.
  • Use native pagination for large libraries so lists load only what users need to see.

Mentioned in this talk

Search inside this talk

What was claimed 14

Show all 14 facts

Related talks