Kinh nghiệm React-Native – Chọn lựa module Phần 1: Có nên sử dụng Expo hay không?

Thế giới opensource rộng lớn cực kỳ thú vị, nó giúp chúng ta xây dựng phần mềm nhanh hơn từ những đóng góp của cộng đồng, khi gặp một bài toán, thay vì phải mất nhiều thời gian để tìm cách giải quyết, ta lên github, google search và BÙM có ai đó giải quyết thay cho ta rồi, thật tuyệt vời, tiết kiệm hàng đống thời gian. Khó có thể đánh giá được sự quan trọng của modules, plugins, extensions, components, packages… đã đóng góp phát triển cho phần mềm lớn như thế nào.

Tuy nhiên đổi lại với một số bạn newbie lại gặp một trở ngại, đó là giữa một rừng những modules, biết nên chọn cái nào đây? Một vấn đề lại có nhiều cách giải quyết, hoặc nhiều người thích tự làm riêng cho mình, có cái tốt có cái tệ, không phải developer nào cũng làm có tâm cả, không phải module nào cũng ngon, nhiều khi rước hại vào thân, vậy thì dùng gì?

Mình thì có cách đơn giản lắm, cứ tìm trên Github, cái nào nhiều sao nhất và có commit mới nhất thì thử, đừng ngại những repo có nhiều issues, miễn là vẫn thấy contributors vẫn commit đều đều và update liên tục là được. Có cộng đồng là còn phát triển, còn có người sửa cho mình, những repo nào mà > 2 năm rồi không thấy update gì thì hạn chế, xem tham khảo họ làm gì rồi cải tiến thôi, vì sau 1–2 năm mọi thứ đã thay đổi rất nhiều, đặc biệt là với React-Native. Lâu dần khi có kinh nghiệm bạn sẽ tự biết nên sử dụng cái nào.

Số lượng sao và last commit

Đấy là cách thông thường cho các module mới, trong bài này mình muốn chia sẻ với các bạn về các module sau khi mình đã nghiên cứu và sử dụng một thời gian, dựa trên kinh nghiệm của chính bản thân. À không sẽ là serial các bài viết về các module mình chọn để chơi với React-Native, hy vọng có ích cho các bạn mới bắt đầu.

Tất cả hoàn toàn là ý kiến riêng của cá nhân mình, có thể sẽ có những bạn quan điểm, mục đích khác mình thì cứ chia sẻ thoải mái, mình không áp đặt hay cổ suý một công nghệ nào cả, mình viết dành cho các bạn newbie có thể chọn lựa nhanh hơn, tránh khỏi các thread drama cãi nhau chửi bới nhau làm gì mất thời gian.

Bài đầu tiên mình xin được chia sẻ về Vanilla React-Native vs Expo, sửa lại câu hỏi mà mình cũng hay được hỏi là:

Có nên sử dụng Expo hay không?

Vâng khi bắt đầu xây dựng một ứng dụng bằng react-native, và bạn sẽ hào hứng với Getting-Started từ official document của Facebook. Bạn sẽ dễ dàng nhìn thấy có đến 2 cách để tạo mới một project, ví dụ tên là MeoApp đi:

  1. Expo CLI Quickstart ($create-react-native-app MeoApp)
  2. React Native CLI Quickstart ($react-native init MeoApp)

Và thường là bạn sẽ bỏ qua đoạn giới thiệu thế này:

  1. Nếu bạn đang có kinh nghiệm làm web, thì dùng Expo CLI sẽ đơn giản, ngon ăn hơn nhiều, bạn có thể làm app ngay mà méo cần đến config Xcode, Android Studio làm gì, chỉ mất có vài phút
  2. Nếu bạn đã từng làm mobile app với native, thì có thể bạn sẽ muốn dùng React Native CLI. Bạn cần phải cài Xcode hoặc Android Studio, nếu chưa cài thì chắc là cần cả tiếng đồng hồ đấy.

Đọc đã thấy prefer phương án 1 rõ ràng rồi, tuy nhiên thì cũng thông cảm, document nó phải chọn cách dễ dàng nhất cho newbie.

Để mình nói kỹ hơn về Expo, thì nó giống như một bộ thư viện, (lib hoặc sdk) đã đóng gói sẵn react-native kèm theo rất nhiều api phổ biến để bạn sử dụng các tính năng từ native. Công việc của bạn chỉ là viết code JS (giống như làm web bằng JS vậy), phần còn lại Expo sẽ lo hết (như là hiển thị bản đồ, quét barcode, update tự động từ cloud, upgrade phiên bản… những cái này mặc định react-native không có, bạn phải cài cắm, sửa hoặc viết thêm rất nhiều). Bạn không cần biết và cũng không cần động đến native một chút nào cũng được, cũng chẳng có file project iOS hay android cho bạn mở.

Hình dung thế này, nếu ứng dụng của bạn làm từ Expo sẽ giống như một trình duyệt, mỗi lần mở app ra nó sẽ gửi yêu cầu đến server của Expo (AWS nếu là bản release, hoặc server local nếu là bản bạn đang dev) để lấy code JS mới nhất của bạn về, đoạn code đó sẽ quy định xem app cần hiển thị gì màn hình nào, popup gì, chạy ra sao … (hiển thị bằng native view chứ không phải web DOM nhé, khác biệt so với Ionic).

Thêm thông tin nữa, Expo là mã nguồn mở của công ty Expo, có đăng ký pháp nhân, có đầu tư có nhân viên phát triển đàng hoàng, không giống những module cá nhân khác trên Github. Sau này khi đủ người dùng mình nghĩ họ sẽ thu tiền bằng cách bán các dịch vụ kèm theo, như là auto testing hay auto deploy, quảng cáo gì đó…

Tuy nhiên các bạn cũng yên tâm là Expo phát hành dạng BSD-licensed, nghĩa là bạn làm cái méo gì với cái thư viện đó cũng được, sửa nó, hack nó, thêm bớt tính năng, … Các tính năng trả phí sau này sẽ chỉ có khi nào bạn cần sử dụng đến thôi.

Ok giờ đến danh sách các điểm tốt của Expo là gì nào:

Pros:

  • Miễn phí, dễ cài đặt, dễ bắt đầu và phát triển ứng dụng, tất cả việc bạn cần làm là viết code JS.
  • Tiết kiệm thời gian, không phải tốn nhiều giờ, thậm chí nhiều ngày để sửa các lỗi rất “ảo” từ native
  • Test trên thiết bị thật rất nhanh không cần build (thông qua app Expo có sẵn trên store, Expo đã đóng gói và build sẵn tất cả phần native cài vào máy mình rồi, phần đó không thay đổi trừ khi bạn upgrade version mới), build để release thì cũng build trên cloud của Expo không phải trên máy mình, máy ai yếu chắc thích lắm.
  • Port sang các phiên bản Window/MacOS/Web cũng dễ dàng (họ cũng đang thử nghiệm Expo web để port phiên bản native sang web)
  • Có nhiều đồ chơi khác có sẵn như analytics, push notification, auto testing, auto deploy, cloud update, tích hợp siêu dễ dàng.
  • Tài liệu cũng rõ, đẹp đẽ hơn cả của Facebook, team phát triển rất thân thiện, tài giỏi, chăm chỉ quảng cáo, demo các kiểu (có tiền đầu tư mà, mình có nói chuyện qua với ku Evan Bacon ở đó, trẻ vãi, đẹp trai, giỏi, chắc các bạn nữ sẽ thích)

Nói tóm lại tất cả bản chất, lợi thế thì loanh quanh quanh việc Expo sẽ lo hết phần native cho bạn, bạn chỉ cần lo phần giao diện, flow bằng JS thôi, nhưng bản release cuối cùng app ra lò thì vẫn là native ngon nhé, điểm yếu cũng từ đó mà ra:

Cons:

  • Bạn không được sửa file native (tức là rất khó tối ưu, sử dụng bản patch sửa lỗi nhanh) tất nhiên vẫn có cách là detaching khỏi ExpoKit để sửa native, nhưng mà làm vậy thì chả còn mẹo gì hay nữa.
  • Bị hạn chế bởi những api Expo cung cấp, bạn không được cài module native mới, không được thay thế những module thú vị hơn mà phải bó buộc vào giải pháp của Expo (ví dụ push notification). Bạn nên nghiên cứu kỹ các api mà ứng dụng của bạn yêu cầu, sau đó xem Expo có hỗ trợ đủ không trước khi quyết định sử dụng.
  • Bạn không chủ động được việc upgrade, Expo luôn phải chờ và upgrade phụ thuộc sau khi react-native phát hành phiên bản mới.
  • Các mã nguồn JS sẽ bị lưu lại trên cloud của Expo, tất nhiên là họ sẽ bảo vệ private cho mình, nhưng đây là điểm cực kỳ hạn chế.
  • App của bạn sẽ bao gồm cả những thứ mà bạn sẽ không hay không bao giờ dùng đến, dẫn đến việc dung lượng app sẽ năng hơn, ít nhất là 30MB trên iOS và 20MB trên Android.

Vậy thì mình có sử dụng Expo hay không? Có và Không.

Mình dùng Expo để test nhanh các trường hợp xem đoạn code này, plugin này sẽ chạy như thế nào, thậm chí là không cần cài cắm hay build gì cả mà có thể xem trực tiếp trên trình duyệt hoặc qua app có sẵn của Expo nên cực tiện, cực nhanh. Hoặc khi mình cần share một đoạn code nào đó, thì Expo cũng rất tiện cho người khác xem.

Mặc dù mình cũng thích Expo, nhưng ở thời điểm hiện tại, mình sẽ không dùng Expo cho các sản phẩm production nào, vì các điểm yếu nêu ở trên là những thứ mình không chấp nhận được cho 1 sản phẩm production:

  • Với các ứng dụng lớn, mình biết chắc chắn sẽ phải detach khỏi Expo, từ việc không thể cài đặt các module mình thích, đặc biệt là module react-native-navigation mình sẽ viết trong bài sau, ngoài ra có run background, in-app purchase, audio player…, tương lai có thể Expo sẽ hỗ trợ thêm, nhưng không bao giờ là đủ.
  • Mình không thể áp dụng các hacky, patch core file trong react-native để tối ưu performance hay behaviour theo ý mình được. Mình cũng không thể bỏ đi những thứ thừa thãi mà không dùng đến, có những phải pháp module tốt hơn mình cũng không thể sử dụng
  • Với các ứng dụng nhỏ, ví dụ như Barcode scanner đi, việc một ứng dụng nhỏ mà lại nặng hơn 20MB là hoàn toàn không hợp lý với mình.

Quan điểm của mình, Expo phù hợp với sinh viên làm đồ án, các bạn resource hạn chế muốn xây dựng prototype, MVP nhanh để giới thiệu, làm ứng dụng cho nội bộ, hoặc các bạn không có kinh nghiệm native chỉ có kinh nghiệm JS và lười học thêm thứ mới, hoặc chấp nhận được các điểm yếu mình nêu ở trên.

Với các bạn đi làm, mình khuyên thành thật nên dùng Vanilla React-Native, để các bạn hiểu được native nó chạy như thế nào, sự khác nhau trong cách xử lý giữa các nền tảng ra sao, khi gặp vấn đề này kia có thể chủ động sửa thay vì ngồi đợi Expo xử lý giùm mình, điều này rất quan trọng để có app tối ưu chất lượng hơn. blah blah…

Thôi dài quá mình xin dừng bài viết, có gì không hiểu các bạn cứ thoải mái hỏi thêm.

Bonus có mấy thứ đang diễn ra và sẽ update trong tương lai gần như thế này:

  1. React-Native đang phát triển CLI cực ngon để link các module ngoài vào react-native siêu đơn giản và dễ dàng, nghĩa là bạn cũng không cần thiết phải biết nhiều hay mất nhiều thời gian để cài đặt module, config native nữa, công việc hầu như chỉ còn import vào và sử dụng.
  2. Expo cũng đang phát triển để tách Expo-kit thành một thư viện độc lập để có thể sử dụng với các project Vanilla React-Native, tức là lúc này nó sẽ giống như một module có chứa nhiều tính năng, và cài đặt như bao module khác, họ cũng đang tiến hành hỗ trợ typescript ngon hơn.