Zadbaj o dobrą organizację dzięki kolekcji
Zapisuj i kategoryzuj treści zgodnie ze swoimi preferencjami.
Projekt z wieloma modułami Gradle jest nazywany projektem wielomodułowym. Ten przewodnik zawiera sprawdzone metody i zalecane wzorce tworzenia aplikacji na Androida składających się z wielu modułów.
Problem z rosnącą bazą kodu
W stale rosnącej bazie kodu skalowalność, czytelność i ogólna jakość kodu często z czasem maleją. Wynika to ze zwiększenia rozmiaru bazy kodu bez podejmowania przez osoby odpowiedzialne za jej utrzymanie aktywnych działań w celu wymuszenia struktury, którą można łatwo utrzymywać. Modularyzacja to sposób strukturyzacji bazy kodu, który zwiększa łatwość utrzymania i pomaga uniknąć tych problemów.
Co to jest modularność?
Modularyzacja to praktyka organizowania bazy kodu w luźno powiązane i samodzielne części. Każda część jest modułem. Każdy moduł jest niezależny i służy do określonego celu. Dzieląc problem na mniejsze i łatwiejsze do rozwiązania podproblemy, zmniejszasz złożoność projektowania i utrzymywania dużego systemu.
Ilustracja 1. Graf zależności przykładowej bazy kodu z wieloma modułami
Korzyści z modularyzacji
Modularyzacja przynosi wiele korzyści, ale wszystkie sprowadzają się do poprawy łatwości utrzymania i ogólnej jakości bazy kodu. W tabeli poniżej znajdziesz podsumowanie najważniejszych korzyści.
Korzyści
Podsumowanie
Możliwość ponownego wykorzystania
Modularyzacja umożliwia udostępnianie kodu i tworzenie wielu aplikacji na tej samej podstawie. Moduły to w zasadzie elementy składowe. Aplikacje powinny być sumą funkcji, które są zorganizowane jako osobne moduły. Funkcje, które zapewnia dany moduł, mogą być włączone lub wyłączone w określonej aplikacji. Na przykład :feature:news może być częścią pełnej wersji aplikacji na zegarek, ale nie wersji demonstracyjnej.
Ścisła kontrola widoczności
Moduły umożliwiają łatwe kontrolowanie, co udostępniasz innym częściom bazy kodu. Wszystko poza interfejsem publicznym możesz oznaczyć jako internal lub private, aby uniemożliwić używanie tego poza modułem.
Dostawa z możliwością dostosowania
Play Feature Delivery korzysta z zaawansowanych funkcji pakietów aplikacji, dzięki czemu możesz dostarczać określone funkcje aplikacji warunkowo lub na żądanie.
Korzyści z modularyzacji można osiągnąć tylko w przypadku modułowej bazy kodu.
Poniższe korzyści można osiągnąć za pomocą innych technik, ale modularyzacja może pomóc w ich jeszcze większym wzmocnieniu.
Korzyści
Podsumowanie
Skalowalność
W przypadku ściśle powiązanego kodu pojedyncza zmiana może wywołać kaskadę zmian w pozornie niezwiązanych częściach kodu. Prawidłowo podzielony na moduły projekt będzie zgodny z zasadą rozdzielenia odpowiedzialności, a tym samym ograniczy powiązania. Zwiększa to autonomię współtwórców.
Własność
Oprócz umożliwienia autonomii moduły mogą też służyć do egzekwowania odpowiedzialności. Moduł może mieć dedykowanego właściciela, który jest odpowiedzialny za utrzymywanie kodu, naprawianie błędów, dodawanie testów i sprawdzanie zmian.
Hermetyzacja
Enkapsulacja oznacza, że każda część kodu powinna mieć jak najmniejszą wiedzę o innych częściach. Wyodrębniony kod jest łatwiejszy do odczytania i zrozumienia.
Możliwość testowania
Testowalność określa, jak łatwo jest testować kod. Testowalna baza kodu to taka, w której komponenty można łatwo testować osobno.
Czas kompilacji
Niektóre funkcje Gradle, takie jak przyrostowe kompilowanie, pamięć podręczna kompilacji czy kompilowanie równoległe, mogą wykorzystywać modułowość do zwiększania wydajności kompilacji.
Typowe problemy
Granularność bazy kodu to stopień, w jakim składa się ona z modułów. Bardziej szczegółowa baza kodu ma więcej mniejszych modułów. Podczas projektowania modułowej bazy kodu musisz określić poziom szczegółowości. Aby to zrobić, weź pod uwagę rozmiar bazy kodu i jej względną złożoność. Zbyt szczegółowe podziały zwiększą obciążenie, a zbyt ogólne zmniejszą korzyści z modularyzacji.
Oto kilka typowych pułapek:
Zbyt szczegółowe: każdy moduł wiąże się z pewnym narzutem w postaci zwiększonej złożoności kompilacji i powtarzalnego kodu. Złożona konfiguracja kompilacji utrudnia zachowanie spójności konfiguracji w różnych modułach. Zbyt duża ilość kodu szablonowego
powoduje, że baza kodu jest nieporęczna i trudna w utrzymaniu. Jeśli narzut niweluje ulepszenia dotyczące skalowalności, rozważ scalenie niektórych modułów.
Zbyt ogólne: jeśli moduły stają się zbyt duże, możesz skończyć z kolejnym monolitem i stracić korzyści, jakie daje modułowość. Na przykład w małym projekcie można umieścić warstwę danych w jednym module. Jednak w miarę rozwoju aplikacji może być konieczne rozdzielenie repozytoriów i źródeł danych na osobne moduły.
Zbyt skomplikowane: nie zawsze warto dzielić projekt na moduły. Dominującym czynnikiem jest rozmiar bazy kodu. Jeśli nie spodziewasz się, że Twój projekt przekroczy określony próg, korzyści związane ze skalowalnością i czasem kompilacji nie będą miały zastosowania.
Czy modularyzacja jest odpowiednią techniką dla mnie?
Jeśli potrzebujesz możliwości ponownego użycia, ścisłej kontroli widoczności lub chcesz korzystać z Play Feature Delivery, modułowość jest dla Ciebie koniecznością. Jeśli nie, ale nadal chcesz korzystać z większej skalowalności, własności, hermetyzacji lub krótszego czasu kompilacji, warto rozważyć modułowość.
Próbki
Now in Android – w pełni funkcjonalna aplikacja na Androida z modułową architekturą.
Treść strony i umieszczone na niej fragmenty kodu podlegają licencjom opisanym w Licencji na treści. Java i OpenJDK są znakami towarowymi lub zastrzeżonymi znakami towarowymi należącymi do firmy Oracle lub jej podmiotów stowarzyszonych.
Ostatnia aktualizacja: 2025-08-17 UTC.
[[["Łatwo zrozumieć","easyToUnderstand","thumb-up"],["Rozwiązało to mój problem","solvedMyProblem","thumb-up"],["Inne","otherUp","thumb-up"]],[["Brak potrzebnych mi informacji","missingTheInformationINeed","thumb-down"],["Zbyt skomplikowane / zbyt wiele czynności do wykonania","tooComplicatedTooManySteps","thumb-down"],["Nieaktualne treści","outOfDate","thumb-down"],["Problem z tłumaczeniem","translationIssue","thumb-down"],["Problem z przykładami/kodem","samplesCodeIssue","thumb-down"],["Inne","otherDown","thumb-down"]],["Ostatnia aktualizacja: 2025-08-17 UTC."],[],[],null,["# Guide to Android app modularization\n\nA project with multiple Gradle modules is known as a multi-module project. This\nguide encompasses best practices and recommended patterns for developing\nmulti-module Android apps.\n| **Note:** This page assumes a basic familiarity with the [recommended app\n| architecture](/topic/architecture).\n\nThe growing codebase problem\n----------------------------\n\nIn an ever-growing codebase, scalability, readability, and overall code quality\noften decrease through time. This comes as a result of the codebase increasing\nin size without its maintainers taking active measures to enforce a structure\nthat is easily maintainable. Modularization is a means of structuring your\ncodebase in a way that improves maintainability and helps avoid these problems.\n\nWhat is modularization?\n-----------------------\n\nModularization is a practice of organizing a codebase into loosely coupled and\nself contained parts. Each part is a module. Each module is independent and\nserves a clear purpose. By dividing a problem into smaller and easier to solve\nsubproblems, you reduce the complexity of designing and maintaining a large\nsystem.\n**Figure 1**: Dependency graph of a sample multi-module codebase\n\nBenefits of modularization\n--------------------------\n\nThe benefits of modularization are many, though they each center upon improving\nthe maintainability and overall quality of a codebase. The following table\nsummarizes the key benefits.\n\n| Benefit | Summary |\n|---------------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|\n| Reusability | Modularization enables opportunities for code sharing and building multiple apps from the same foundation. Modules are effectively building blocks. Apps should be a sum of their features where the features are organized as separate modules. The functionality that a certain module provides may or may not be enabled in a particular app. For example, a `:feature:news` can be a part of the full version flavor and wear app but not part of the demo version flavor. |\n| Strict visibility control | Modules enable you to easily control what you expose to other parts of your codebase. You can mark everything but your public interface as `internal` or `private` to prevent it from being used outside the module. |\n| Customizable delivery | [Play Feature Delivery](/guide/playcore/feature-delivery) uses the advanced capabilities of app bundles, allowing you to deliver certain features of your app conditionally or on demand. |\n\nThe benefits of modularization are only achievable with a modularized codebase.\nThe following benefits might be achieved with other techniques but\nmodularization can help you enforce them even more.\n\n| Benefit | Summary |\n|---------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|\n| Scalability | In a tightly coupled codebase a single change can trigger a cascade of alterations in seemingly unrelated parts of code. A properly modularized project will embrace the [separation of concerns](https://en.wikipedia.org/wiki/Separation_of_concerns) principle and therefore limit the coupling. This empowers the contributors through greater autonomy. |\n| Ownership | In addition to enabling autonomy, modules can also be used to enforce accountability. A module can have a dedicated owner who is responsible for maintaining the code, fixing bugs, adding tests, and reviewing changes. |\n| Encapsulation | Encapsulation means that each part of your code should have the smallest possible amount of knowledge about other parts. Isolated code is easier to read and understand. |\n| Testability | Testability characterizes how easy it is to [test](/training/testing) your code. A testable codebase is one where components can be easily tested in isolation. |\n| Build time | Some Gradle functionalities such as incremental build, build cache or parallel build, can leverage modularity to [improve build performance](/studio/build/optimize-your-build). |\n\nCommon pitfalls\n---------------\n\nThe granularity of your codebase is the extent to which it is composed of\nmodules. A more granular codebase has more, smaller modules. When designing a\nmodularized codebase, you should decide on a level of granularity. To do so,\ntake into account the size of your codebase and its relative complexity. Going\ntoo fine-grained will make the overhead a burden, and going too coarse will\nlessen the benefits of modularization.\n\nSome common pitfalls are as follows:\n\n- **Too fine-grained** : Every module brings a certain amount of overhead in the form of increased build complexity and [boilerplate code](https://en.wikipedia.org/wiki/Boilerplate_code). A complex build configuration makes it difficult to [keep configurations consistent](/topic/modularization/patterns#consistent-configuration) across modules. Too much boilerplate code results in a cumbersome codebase that is difficult to maintain. If overhead counteracts scalability improvements, you should consider consolidating some modules.\n- **Too coarse-grained**: Conversely, if your modules are growing too large you might end up with yet another monolith and miss the benefits that modularity has to offer. For example, in a small project it's ok to put the data layer inside a single module. But as it grows, it might be necessary to separate repositories and data sources into standalone modules.\n- **Too complex**: It doesn't always make sense to modularize your project. A dominating factor is the size of the codebase. If you don't expect your project to grow beyond a certain threshold, the scalability and build time gains won't apply.\n\nIs modularization the right technique for me?\n---------------------------------------------\n\nIf you need the benefits of reusability, strict visibility control or to use the\n[Play Feature Delivery](/guide/playcore/feature-delivery), then modularization is a necessity for you. If you\ndon't, but still want to benefit from improved scalability, ownership,\nencapsulation, or build times, then modularization is something worth\nconsidering.\n\nSamples\n-------\n\n- [Now in Android](https://github.com/android/nowinandroid) - fully functional Android app featuring modularization.\n- [Multi module architecture sample](https://github.com/android/architecture-samples/tree/multimodule)"]]