Dạng thức sản xuất kiểu mô đun là gì năm 2024
Không có một chiến lược mô-đun hoá nào phù hợp với mọi dự án. Nhờ sự linh hoạt vốn có của Gradle nên bạn sẽ gặp rất ít hạn chế khi thực hiện việc tổ chức dự án. Trang này cung cấp thông tin tổng quan về một số quy tắc chung cũng như các mẫu phổ biến mà bạn có thể tận dụng khi phát triển ứng dụng Android đa mô-đun. Show
Nguyên tắc gắn kết chặt chẽ và ít ràng buộcMột cách để mô tả đặc điểm cơ sở mã mô-đun là sử dụng các khái niệm ràng buộc và gắn kết. Khái niệm "ràng buộc" đo lường mức độ phụ thuộc lẫn nhau của các mô-đun. Trong ngữ cảnh này, khái niệm "gắn kết" đo lường sự liên kết về chức năng giữa các thành phần của một mô-đun. Nguyên tắc chung là chương trình của bạn nên có mức độ gắn kết cao và ràng buộc thấp:
Các loại mô-đunTuỳ thuộc vào cấu trúc ứng dụng mà bạn có thể sắp xếp các mô-đun của mình. Dưới đây là một số loại mô-đun phổ biến mà bạn có thể ra mắt trong ứng dụng của mình khi thực hiện theo cấu trúc ứng dụng đề xuất của chúng tôi. Mô-đun dữ liệuMô-đun dữ liệu thường chứa kho lưu trữ, nguồn dữ liệu và các lớp của mô hình. Một mô-đun dữ liệu có 3 trách nhiệm chính là:
Mô-đun tính năngTính năng là một phần riêng biệt trong chức năng của ứng dụng, thường tương ứng với một màn hình hoặc một loạt màn hình có liên quan chặt chẽ, chẳng hạn như quy trình đăng ký hoặc thanh toán. Nếu ứng dụng của bạn có thanh điều hướng ở dưới cùng, thì có khả năng mỗi đích đến là một tính năng. Hình 2. Mỗi thẻ của ứng dụng này có thể được xác định là một tính năng.Các tính năng liên kết với màn hình hoặc đích đến trong ứng dụng của bạn. Do đó, có thể chúng sẽ có một giao diện người dùng liên kết và Mô-đun ứng dụngMô-đun ứng dụng là điểm truy cập đến ứng dụng. Các mô-đun này phụ thuộc vào các mô-đun tính năng và thường cung cấp tính năng điều hướng gốc. Một mô-đun ứng dụng đơn lẻ có thể được biên dịch thành một số tệp nhị phân nhờ các biến thể bản dựng. Hình 4. Biểu đồ phần phụ thuộc mô-đun của các phiên bản sản phẩm: “Bản minh hoạ” và “Bản đầy đủ”.Nếu ứng dụng của bạn nhắm đến nhiều loại thiết bị (chẳng hạn như ô tô, thiết bị đeo thông minh hay TV), hãy xác định một mô-đun ứng dụng cho mỗi loại thiết bị. Điều này giúp tách biệt các phần phụ thuộc dành riêng cho từng nền tảng. Hình 5. Biểu đồ phần phụ thuộc của ứng dụng Wear.Các mô-đun phổ biếnCác mô-đun phổ biến, còn gọi là mô-đun cốt lõi, chứa mã mà các mô-đun khác thường sử dụng. Các mô-đun này giúp giảm tình trạng thừa mã và không đại diện cho lớp cụ thể nào trong cấu trúc của một ứng dụng. Sau đây là ví dụ về các mô-đun phổ biến:
Mô-đun kiểm thửMô-đun kiểm thử là các mô-đun Android chỉ dùng cho mục đích kiểm thử. Các mô-đun này chứa mã kiểm thử, tài nguyên kiểm thử và các phần phụ thuộc kiểm thử chỉ cần thiết để chạy hoạt động kiểm thử chứ không cần thiết trong thời gian chạy của ứng dụng. Các mô-đun kiểm thử được tạo để tách mã dành riêng cho kiểm thử khỏi ứng dụng chính, giúp quản lý và duy trì mã mô-đun dễ dàng hơn. Các trường hợp sử dụng mô-đun kiểm thửCác ví dụ sau đây cho thấy những trường hợp triển khai mô-đun kiểm thử có thể đặc biệt có lợi:
Giao tiếp giữa mô-đun với mô-đunCác mô-đun hiếm khi tồn tại một cách hoàn toàn tách biệt và thường dựa vào, cũng như giao tiếp với các mô-đun khác. Việc giữ mức độ ràng buộc thấp là rất quan trọng, ngay cả khi các mô-đun hoạt động cùng nhau và trao đổi thông tin thường xuyên. Đôi khi, bạn không nên cho hai mô-đun giao tiếp trực tiếp với nhau, như trong trường hợp ràng buộc về mặt cấu trúc. Thậm chí cũng có khả năng không thực hiện được việc này, chẳng hạn như với các phần phụ thuộc tuần hoàn. Hình 7. Không thể giao tiếp trực tiếp, hai chiều giữa các mô-đun do các phần phụ thuộc tuần hoàn. Cần có mô-đun dàn xếp để điều phối luồng dữ liệu giữa 2 mô-đun độc lập khác.Để khắc phục vấn đề này, bạn có thể tạo một mô-đun thứ ba để dàn xếp giữa hai mô-đun khác. Mô-đun dàn xếp có thể theo dõi thông báo từ cả hai mô-đun và chuyển tiếp các thông báo này khi cần. Trong ứng dụng mẫu của chúng ta, màn hình thanh toán cần biết cuốn sách nào cần mua mặc dù sự kiện bắt nguồn từ một màn hình khác, thuộc về một tính năng khác. Trong trường hợp này, mô-đun dàn xếp là mô-đun sở hữu biểu đồ điều hướng (thường là mô-đun ứng dụng). Trong ví dụ này, chúng ta sử dụng tính năng điều hướng để truyền dữ liệu từ tính năng trang chủ đến tính năng thanh toán bằng thành phần Điều hướng.
Đích đến thanh toán sẽ nhận được mã nhận dạng của sách để làm đối số, cụ thể là để tìm nạp thông tin về sách. Bạn có thể sử dụng Ô điều khiển trạng thái đã lưu để truy xuất các đối số điều hướng bên trong
Bạn không nên truyền các đối tượng dưới dạng đối số điều hướng. Thay vào đó, hãy sử dụng mã nhận dạng đơn giản mà các tính năng có thể sử dụng để truy cập và tải tài nguyên mong muốn từ lớp dữ liệu. Bằng cách này, bạn sẽ duy trì được ràng buộc thấp và không vi phạm nguyên tắc nguồn đáng tin cậy duy nhất. Trong ví dụ bên dưới, cả hai mô-đun tính năng đều phụ thuộc vào cùng một mô-đun dữ liệu. Điều này giúp bạn giảm thiểu lượng dữ liệu mà mô-đun dàn xếp cần chuyển tiếp và duy trì ràng buộc giữa các mô-đun ở mức thấp. Thay vì truyền đối tượng, các mô-đun phải trao đổi mã nhận dạng gốc và tải tài nguyên từ một mô-đun dữ liệu dùng chung. Hình 8. Hai mô-đun tính năng dựa vào một mô-đun dữ liệu dùng chung.Đảo ngược phần phụ thuộcĐảo ngược phần phụ thuộc là khi bạn sắp xếp mã sao cho mô-đun trừu tượng tách biệt với mô-đun triển khai cụ thể.
Các mô-đun dựa vào hành vi được xác định trong mô-đun trừu tượng chỉ nên phụ thuộc vào mô-đun trừu tượng, thay vì các mô-đun triển khai cụ thể. Hình 9. Thay vì mô-đun cấp cao phụ thuộc trực tiếp vào mô-đun cấp thấp, thì mô-đun cấp cao và mô-đun triển khai sẽ phụ thuộc vào mô-đun trừu tượng.Ví dụHãy tưởng tượng một mô-đun tính năng cần có một cơ sở dữ liệu để hoạt động. Mô-đun tính năng không liên quan đến cách triển khai cơ sở dữ liệu, mà cần có một cơ sở dữ liệu Room cục bộ hoặc bản sao Firestore từ xa. Mô-đun này chỉ cần lưu trữ và đọc dữ liệu ứng dụng. Để đạt được điều này, mô-đun tính năng phụ thuộc vào mô-đun trừu tượng thay vì một phương thức triển khai cụ thể cho cơ sở dữ liệu. Mô-đun trừu tượng này xác định API Cơ sở dữ liệu của ứng dụng. Nói cách khác, mô-đun này đặt ra các quy tắc về cách tương tác với cơ sở dữ liệu. Nhờ đó, mô-đun tính năng có thể dùng bất kỳ cơ sở dữ liệu nào mà không cần biết thông tin triển khai cơ bản của cơ sở dữ liệu đó. Mô-đun triển khai cụ thể cung cấp phương thức triển khai thực tế của các API được xác định trong mô-đun trừu tượng. Để làm được điều đó, mô-đun triển khai cũng phụ thuộc vào mô-đun trừu tượng. Chèn phần phụ thuộcHiện tại, bạn có thể thắc mắc về cách kết nối mô-đun tính năng với mô-đun triển khai. Câu trả lời là Chèn phần phụ thuộc. Mô-đun tính năng không trực tiếp tạo thực thể cơ sở dữ liệu bắt buộc. Thay vào đó, mô-đun này chỉ định những phần phụ thuộc cần thiết. Sau đó, các phần phụ thuộc này được cung cấp bên ngoài, thường là trong .
Lợi íchSau đây là lợi ích của việc phân tách giữa API và mô-đun triển khai các API này:
Thời điểm phân táchBạn nên phân tách API khỏi các mô-đun triển khai trong các trường hợp sau đây:
Cách thức triển khai?Để triển khai tính năng đảo ngược phần phụ thuộc, hãy làm theo các bước sau đây:
Các phương pháp chung hay nhấtNhư đã đề cập từ đầu, có nhiều cách phù hợp để phát triển một ứng dụng nhiều mô-đun. Tương tự với việc có đa dạng cấu trúc phần mềm, có nhiều cách để mô-đun hoá ứng dụng. Tuy nhiên, các đề xuất chung sau đây có thể giúp mã của bạn dễ đọc, dễ bảo trì và dễ kiểm thử hơn. Duy trì tính nhất quán của cấu hìnhMỗi mô-đun đều có mức hao tổn cấu hình riêng. Nếu số lượng mô-đun của bạn đạt đến một ngưỡng nhất định, thì việc quản lý tính nhất quán của cấu hình sẽ trở nên rất khó khăn. Chẳng hạn, điều quan trọng là các mô-đun phải sử dụng cùng một phiên bản của các phần phụ thuộc. Nếu bạn chỉ cần cập nhật một phiên bản phần phụ thuộc nhưng lại phải cập nhật số lượng lớn mô-đun thì đó không chỉ là sự hao công tốn sức mà còn là kẽ hở có thể phát sinh ra lỗi. Để giải quyết vấn đề này, bạn có thể sử dụng một trong các công cụ của Gradle để tập trung vào cấu hình của mình:
Hiển thị càng ít càng tốtGiao diện công khai của một mô-đun phải ở mức tối thiểu và chỉ hiển thị các mục thiết yếu. Điều này sẽ không làm rò rỉ chi tiết triển khai nào ra bên ngoài. Giới hạn mọi thứ trong phạm vi nhỏ nhất có thể. Dùng phạm vi hiển thị
1 hơn
2. Phần sau hiển thị các phần phụ thuộc bắc cầu cho người dùng mô-đun của bạn. Việc sử dụng phương thức triển khai có thể cải thiện thời gian xây dựng vì sẽ làm giảm số lượng mô-đun cần xây dựng lại. Ưu tiên các mô-đun Kotlin và JavaCó 3 kiểu mô-đun thiết yếu mà Android Studio hỗ trợ:
Vì các mô-đun Android đi kèm với mức hao tổn, tốt nhất bạn nên sử dụng loại Kotlin hoặc Java nhiều nhất có thể. |