Search the site
GETTING STARTED
Add Dartvel to the Flutter app you already have, one screen at a time.
dartvel init changes two things in pubspec.yaml and moves no files.
ON THIS PAGE
Keep your router
go_router
auto_route
Navigator 1.0
Navigator 2.0
MaterialApp.router and CupertinoApp.router
See what Dartvel manages
Adoption errors
Existing native hosts
Status
dartvel init --dry-run # the report and the changes, nothing written
dartvel initCopy code to clipboard
It adds dartvel_core, plus dartvel_flutter for a Flutter app, and a dartvel: block. Every other line and comment stays.
It reports first: your SDK constraint against Dart 3.13, and each package you share with Dartvel against its constraint.
When lib/pages or lib/backend already hold your files, it picks other directories so nothing of yours is claimed.
Add the CLI yourself
init adds the runtime only. Run the generator from the dartvel binary you installed, or add dartvel_cli as a dev dependency and use dart run dartvel_cli:dartvel.
Dartvel works with five kinds of routing: go_router, auto_route, Navigator 1.0, Navigator 2.0, and MaterialApp.router or CupertinoApp.router with a RouterConfig. dartvel init says which one your app uses.
Each one works the same way. You pass your existing routes or handler as existing:, in its own type. Dartvel answers its own paths under the mount, such as /app. Every other path goes to your handler, as it did before.
On a path both declare, Dartvel's page wins. dartvel routes also stops with DV-ADOPT-002 when a GoRoute of yours has the path of a generated page.
Dartvel's routes stay typed: open one with dvHostedPath(DVRoutes.users(id: '7').path, at: '/app') or DV.Navigation.navigate(DVRoutes.about). Your routes keep their own argument types.
Dartvel's guards and redirects run on Dartvel's paths. Back goes through Dartvel's stack first, then yours.
final GoRouter router = dartvelGoRouter(
at: '/app',
existing: myRoutes, // List<RouteBase>
redirect: myRedirect, // GoRouterRedirect
);
MaterialApp.router(routerConfig: router);Copy code to clipboard
One GoRouter holds Dartvel's routes and yours. DV.Navigation is attached to it.
Your redirect runs only on your paths. Dartvel's paths keep Dartvel's guards.
Building the GoRouter yourself still works: GoRouter(routes: [...myRoutes, ...dartvelRoutes(at: '/app')]), then DVNavigation.attach(router).
class AppRouter extends RootStackRouter {
@override
List<AutoRoute> get routes => dartvelAutoRoutes(
at: '/app',
existing: <AutoRoute>[
AutoRoute(page: HomeRoute.page, path: '/', initial: true),
AutoRoute(page: ProfileRoute.page, path: '/profile'),
],
);
}Copy code to clipboard
dartvelAutoRoutes is generated when your project depends on auto_route. It adds one route for each Dartvel path under /app, before yours.
Your pages keep their generated route classes and typed arguments.
auto_route and go_router both define RouteData and RouteMatch. Import the Dartvel client with hide RouteData, RouteMatch in files that use auto_route.
MaterialApp(
onGenerateRoute: dartvelRouteFactory(
at: '/app',
existing: myOnGenerateRoute, // RouteFactory
),
);
Navigator.pushNamed(context, dvHostedPath(DVRoutes.about.path, at: '/app'));Copy code to clipboard
A route name that is a Dartvel path gets the Dartvel page. Any other name goes to your onGenerateRoute, with its arguments.
A name that neither handles goes to onUnknownRoute, as before.
If you wrote your own RouterDelegate, keep your routes in one table and spread Dartvel's into it. dartvelNavigator2_0Routes returns all of Dartvel's routes as a list:
late final List<DVNavigatorRoute> table = <DVNavigatorRoute>[
DVNavigatorRoute('/settings', (uri) => const MaterialPage(child: SettingsScreen())),
...dartvelNavigator2_0Routes(at: '/app', onLocationChanged: go),
];
@override
Widget build(BuildContext context) => Navigator(
key: navigatorKey,
pages: <Page<Object?>>[
const MaterialPage(child: HomeScreen()),
...dvNavigatorPages(location, table),
],
onDidRemovePage: (_) {},
);Copy code to clipboard
Your delegate stays in charge: it keeps the location and the stack, and asks the table which page a location is. The first entry that matches answers.
Every Dartvel route is an entry, under the prefix. Guards, parameters, the query and back work as in a Dartvel app.
Under a prefix there is one more entry, /app/**, so an unknown path under /app gets Dartvel's not-found page.
All of Dartvel's entries build the same page, so moving between two Dartvel paths keeps that page and its state.
When someone navigates inside Dartvel, onLocationChanged gets the new location, such as /app/users/7. Store it, so your currentConfiguration and the address bar stay correct.
You can also keep your delegate and parser unchanged, and pass them to dartvelRouterConfig (next section).
MaterialApp.router(
routerConfig: dartvelRouterConfig(at: '/app', existing: myConfig),
);
// A delegate and a parser of your own:
dartvelRouterConfig(
at: '/app',
existing: RouterConfig<MyConfiguration>(
routerDelegate: myDelegate,
routeInformationParser: myParser,
),
);Copy code to clipboard
Your RouterConfig can come from go_router, auto_route or your own delegate and parser. Its configuration type stays its own.
A Dartvel path is handled by Dartvel. Every other location goes to your parser and delegate.
Your screens stay loaded while a Dartvel page shows. Back from the first Dartvel page returns to them.
With no existing config, dartvelRouterConfig() is the app's own Dartvel router.
dartvel inspect adoption
dartvel inspect adoption --json
dartvel db pull --localCopy code to clipboard
inspect adoption counts routes, models, screens and functions as managed or not, and says how it counted each.
db pull --local prints @DVModel suggestions from drift tables, isar collections and sqflite CREATE TABLE strings. It writes nothing.
It never marks a field sensitive for you. Decide that yourself.
DV-ADOPT-001
Means: Stated once by init: multi-tenancy scopes only the models Dartvel manages
DV-ADOPT-002
Means: A route of yours has the same path as a generated page
DV-ADOPT-003
Means: A @DVModel class also uses freezed, json_serializable or dart_mappable
DV-ADOPT-005
Means: dartvel create was pointed at a pubspec it did not write. Use dartvel init
dartvel explain DV-ADOPT-003Copy code to clipboard
init adopts Flutter projects. Dartvel module mounts and backend generation are built; they do not create a Kotlin, Swift or desktop host integration.
Planned
Not yet implemented: native add-to-app artifact and host scaffold generation. See Existing native apps for the draft design.
Partial
Spec section: Adoption
Planned work and implementation limits
No bridges between signals and Riverpod providers or streams.
No auth adapters for Firebase Auth or Supabase Auth.
Routing packages other than go_router and auto_route are not tested. They can only join through dartvelRouterConfig.
FSL-1.1-MIT licensed. Built with Dartvel.
Dartvel is made by
To the bottom