If you don’t still get what it is, there are many articles out there online and you can go through a couple of them. However, in short, the goal of using clean architecture is to have a codebase:
In other words, dependencies can exist only from outer to inner layers. We put more general stuff in inner layers and are more likely to change stuff in outer layers. As a result, we can easily replace whatever in outer layers easily when we need and without affecting our core logic. And this core logic always stays testable as it’s independent of external factors.
OK, that’s enough for the explanation part! I know these words don’t mean much without showing a real-world example. Therefore, it’s time to get into how I use clean architecture in a Flutter app.
First of all, our app’s overall architecture is as follows:
Overall architecture of the app
The main/root project has three modules (Flutter packages) in it: presentation, data, and domain. Presentation and data modules are the outer layers of clean architecture, whereas the domain module corresponds to inner layers. That’s why the first two depend on the third one. In the overall picture, our root project depends only on these three packages, nothing else.
In terms of code, the main project has just main.dart
file under lib
folder. Here, basically what we do is to initialize these three modules and run the app. By initializing, I mean we perform whatever necessary for a module before starting the app; and there might be nothing necessary for some. So, our main
function looks something like the following:
void main() {
//INIT MODULES
Data.init();
Domain.init();
Presentation.init();
//RUN APP
runApp(MyApp());
}
class MyApp extends StatelessWidget {
//...
}
Our first module to talk about is the presentation module. This module directly depends on the domain module in our architecture. It’s not allowed to communicate with the data module. Its package structure is as follows:
Package structure of presentation module
Almost all our code resides in src
package. So, presentation.dart
, the file which contains Presentation
class, decides what to “export”, meaning that it allows what will be visible to the root project.
In src
folder, we have the following packages:
feature
package contains the packages related to all presentational features of the app. As an example, let’s say we have profile
feature in our app. So, this package would contain at least the following: ProfilePage
, ProfileController
, ProfilePresenter
, and a widget
package which contains the related widgets used in ProfilePage
. I will explain what these classes are responsible for while I’m going through an example. So, please keep reading :)widget
package contains the reusable widgets that are not specific to one feature but used by multiple features.core
package contains the “brain” of our app, so to speak. It includes all the classes regarding localization, styling, resource/asset handling, page navigation management, constants, etc.entity
package contains all simple data classes only related to the presentation layer.util
package contains all utility classes only related to the presentation layer.#flutter #clean-architecture #mobile-app-development