2018-07-23

What is MVI? Model-View-Intent


Thế là gần 2 năm trôi qua từ lần gần đây nhất mình nói về Android architecture từ tháng 11/2016 Android evolution ... the right architecture?

OK lúc đó Hannes Dorfmann chỉ mới đề cập đến ý tưởng MVI (04 Mar 2016) và muốn chuyển ý tưởng này từ Javascript sang Android. Lúc đó Google còn chưa chính thức ra Android Architecture Components.

Bài viết đầu tiên trong series về MVI của Hannes Dorfmann là vào tháng 01/2017, còn bài viết cuối là vào tháng 05/2018. Nói chung cũng vừa mới đây thôi.

Series của Hannes Dorfmann, tất nhiên là bạn nên đọc hết, đọc một cách kỹ càng
Gần đây công ty lại chuẩn bị một số project mới về mobile nên mình lại cảm thấy ngứa nghề developer. Mặc dù focus vào phát triển sản phẩm như tính năng và không đi sâu vào implement nhưng nhiều khi dạo quanh và đọc các thông tin về architecture cũng có cái thú vị của nó. Càng về sau mình thấy cần thiết phải có một triết lý và các giá trị rõ ràng khi xây dựng sản phẩm từ cả thiết kế đến implementation.

Đầu tiên nói về MVI. Nó là viết tắt của Model-View-Intent. Intent ở đây không phải là Intent của Android (đừng mắc bệnh nghề nghiệp). Phải nói mình rất ấn tượng với lập luận đơn giản của MVI, về unidirectional flow. Muốn tìm về cuội nguồn của MVI thì phải đi từ Cycle.js của André Staltz một framework hướng functional và reactive – A functional and reactive JavaScript framework for predictable code. Một lưu ý thêm ở đây là mục đích framework này nhằm tổ chức code một cách predictable.

Quay lại một chút về trending năm 2017 (development thôi nhé). Đầu năm bên cạnh những thứ liên quan nhiều đến thiết kế như Lottie, motion, onboarding ... sẽ có MVP, MVVM, RxJava (từ v1 sang v2), Dagger2. Chốt lại cuối năm 2017 thì vẫn là sử dụng MVP và MVVM (Google recommended), thêm Kotlin, Android Architecture Components và có thể là Flutter.

Như vậy cả năm 2017 architecture vẫn xoay quanh MVP và MVVM. Tuy nhiên, mình cũng như nhiều developer khác nhận xét thì MVP và MVVM vẫn gây một chút cảm giác thiếu khi không giới thiệu một data flow nào như kiểu Redux. Cái này là điểm mấu chốt để tổ chức predictable code. Dĩ nhiên đó là lý do khi dùng reactive với 2 architecture này, reactive sẽ không phát huy hết khả năng của mình.

Bạn có thể chọn MVP hay MVVM như khuyến khích của Google. Tuy nhiên cá nhân mình thích MVI vì triết lý đơn giản của nó hơn. Ý tưởng của MVI là giao tiếp Human-Computer thể hiển như một vòng tròn, một vòng lặp thì chính xác hơn (cycle).


Khi thể hiện dưới dạng chuỗi các function thì như sau:


Đầu tiên hệ thống (computer/app) lấy input có thể từ DB, Restful API để hiển thị theo cách nào đó. Nó là view(model). Sau khi hiển thị xong thì nó là input của người dùng user. User sẽ thao tác trên ứng dụng ví dụ click chẳng hạn. 

Function intent() sẽ nhận các input từ user, chuyển nó sang model và function model() nhận các input này để thay đổi trạng thái. Cuối cùng function view() sẽ nhận tham số từ output của model() để cập nhật lại UI, hoàn tất một cycle.

Tới đây có lẽ khá đủ cho một bài giới thiệu. Việc còn lại là bắt tay vào làm thử cái gì đó. Re-factor lại một project đã làm cũng có thể, đọc thêm trên GitHub hay Medium... À nhớ là Mosby đã có implement MVI rồi.

Mosby library https://github.com/sockeqwe/mosby

G9