Choosing modules
An app is made of the modules you ask for and the modules they need. You name modules with -m or pick them in the questions of smf create, and SMF adds the rest.
Roles and the modules that provide them
Most modules provide a role, a part of the app that other modules count on without knowing which module provides it. An app has at most one provider of most roles, while crash reporting and analytics can have several.
| Role | -m | What the module does | In an app |
|---|---|---|---|
| App entry | flutter_core | The Flutter project: main(), start-up, root widget, native projects | always, added by SMF |
| Router | go_router | Routes of the features, typed navigation | none or one |
| Layout | bottom_tabs | Tabs at the bottom for the features' destinations | none or one |
| State management | bloc | BLoC with flutter_bloc | none or one |
riverpod | Riverpod with flutter_riverpod | ||
| Dependency injection | get_it | Service locator with get_it | none or one |
| Events | event_bus | A service that delivers events between parts of the app | none or one |
| Crash reporting | firebase_crashlytics | Reports errors to Firebase Crashlytics | any number |
| Analytics | firebase_analytics | Records events and screen views in Firebase Analytics | any number |
Two modules provide no role:
| Kind | -m | What the module does |
|---|---|---|
| Feature | home | A start screen with the name of the app, at /home |
| Infrastructure | firebase_core | Sets up Firebase, for the other Firebase modules |
Each module has a page of its own.
What SMF adds for you
flutter_coregoes into every app.- A module brings the modules it depends on:
firebase_crashlyticsandfirebase_analyticsbringfirebase_core. - A module that requires a role brings its provider when only one module provides it. Features need a router, and so does the layout, so
homeorbottom_tabsbringsgo_router. A module that needs dependency injection bringsget_it.
When several modules provide a required role, a run in a terminal asks which one to use. A run without a terminal stops and asks you to add one of them to -m. Before it generates the app, SMF prints each module it added and why.
How the modules combine
Screens need a router
A feature declares its routes for whatever router the app has. An app without a router shows a fallback start screen with the name of the app, and so does an app with a router but no screen to start on.
The layout shows the destinations of the features
A feature can mark a route as a destination of the main navigation, as home does. With bottom_tabs, every destination becomes a tab, in the order the features were chosen. With one destination the tab bar is hidden, and without any the app has no main navigation. The bar holds at most five tabs. A feature whose destination does not fit is left out with a warning, and with --strict the run stops instead.
State management is per feature
bloc and riverpod add their package, and riverpod also puts its ProviderScope around the app. A feature that keeps state brings its Cubits or providers in a variant for each state manager. home has no state, so it works with either of them or with none.
Services work with or without a container
The events, analytics and crash reporting roles each generate a service interface and a function that returns the app's service. With get_it, the roles register their services in the container, and features take them from there. Without a container, the app calls the function. See Services and state.
Analytics follows the router
With a router, firebase_analytics logs a screen view for each screen the user sees. Without a router, it records only the events that the app logs itself.
Reporting modules add up
With more than one module for crash reporting or analytics, the app's CrashReporter or AnalyticsService forwards every call to all of them.
Some useful sets
| Command | What you get |
|---|---|
smf create my_app | Every question, in a terminal. |
smf create my_app --no-input | Only what every app needs: a Flutter app with a fallback start screen. |
smf create my_app -m home,bottom_tabs | A start screen, the router and tabs for the screens that features add. |
smf create my_app -m home,bottom_tabs,get_it,event_bus,bloc | The same, with a service container, events between parts of the app, and BLoC. |
smf create my_app -m home,bottom_tabs,get_it,firebase_crashlytics,firebase_analytics | Crash reports and analytics in Firebase, with screen views. |
To see what a set of modules gives before anything is generated, add --explain. It prints the modules, the roles, the dependencies and what the machine is missing, and then stops. See the smf create reference.
Conflicts
Asking for two providers of a role that an app has at most one of, such as -m bloc,riverpod, stops smf create with a usage error that names both. Keep one of them.