feat: replace mail protocol with smolmail and rebuild the UI
This commit is contained in:
parent
cb24b68069
commit
e94e4158cc
93 changed files with 6387 additions and 3479 deletions
|
|
@ -1,18 +0,0 @@
|
|||
import "package:auto_route/auto_route.dart";
|
||||
import "package:flash_mail/data/providers/providers.dart";
|
||||
import "package:flutter_riverpod/flutter_riverpod.dart";
|
||||
|
||||
class AccountGuard extends AutoRouteGuard {
|
||||
final WidgetRef ref;
|
||||
|
||||
AccountGuard(this.ref);
|
||||
|
||||
@override
|
||||
void onNavigation(NavigationResolver resolver, StackRouter router) {
|
||||
if (!ref.read(accountProvider).isAuthenticated()) {
|
||||
router.replaceNamed("/");
|
||||
} else {
|
||||
resolver.next(true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -1,13 +1,12 @@
|
|||
import "package:auto_route/auto_route.dart";
|
||||
import "package:flash_mail/presentation/routes/account_guard.dart";
|
||||
import "package:flutter_riverpod/flutter_riverpod.dart";
|
||||
|
||||
import "package:flash_mail/presentation/routes/auth_guard.dart";
|
||||
|
||||
import "package:smol_mail/presentation/routes/home_guard.dart";
|
||||
import "package:smol_mail/presentation/routes/identity_guard.dart";
|
||||
import "app_router.gr.dart";
|
||||
|
||||
@AutoRouterConfig(replaceInRouteName: "Screen,Route")
|
||||
class AppRouter extends $AppRouter {
|
||||
class AppRouter extends RootStackRouter {
|
||||
final WidgetRef ref;
|
||||
|
||||
AppRouter(this.ref);
|
||||
|
|
@ -15,23 +14,40 @@ class AppRouter extends $AppRouter {
|
|||
@override
|
||||
List<AutoRoute> get routes => [
|
||||
AutoRoute(
|
||||
page: AccountRoute.page,
|
||||
page: OnboardingRoute.page,
|
||||
path: "/",
|
||||
initial: true,
|
||||
guards: [AuthGuard(ref)],
|
||||
),
|
||||
AutoRoute(
|
||||
page: LoginRoute.page,
|
||||
path: "/login",
|
||||
guards: [HomeGuard(ref)],
|
||||
),
|
||||
AutoRoute(
|
||||
page: InboxRoute.page,
|
||||
path: "/inbox",
|
||||
guards: [AccountGuard(ref)],
|
||||
guards: [IdentityGuard(ref)],
|
||||
),
|
||||
AutoRoute(
|
||||
page: MessageDetailRoute.page,
|
||||
path: "/message",
|
||||
)
|
||||
guards: [IdentityGuard(ref)],
|
||||
),
|
||||
AutoRoute(
|
||||
page: ComposeRoute.page,
|
||||
path: "/compose",
|
||||
guards: [IdentityGuard(ref)],
|
||||
),
|
||||
AutoRoute(
|
||||
page: ContactsRoute.page,
|
||||
path: "/contacts",
|
||||
guards: [IdentityGuard(ref)],
|
||||
),
|
||||
AutoRoute(
|
||||
page: ContactDetailRoute.page,
|
||||
path: "/contact",
|
||||
guards: [IdentityGuard(ref)],
|
||||
),
|
||||
AutoRoute(
|
||||
page: SettingsRoute.page,
|
||||
path: "/settings",
|
||||
guards: [IdentityGuard(ref)],
|
||||
),
|
||||
];
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,3 +1,4 @@
|
|||
// dart format width=80
|
||||
// GENERATED CODE - DO NOT MODIFY BY HAND
|
||||
|
||||
// **************************************************************************
|
||||
|
|
@ -8,132 +9,240 @@
|
|||
// coverage:ignore-file
|
||||
|
||||
// ignore_for_file: no_leading_underscores_for_library_prefixes
|
||||
import 'package:auto_route/auto_route.dart' as _i5;
|
||||
import 'package:flash_mail/presentation/screens/account_screen.dart' as _i1;
|
||||
import 'package:flash_mail/presentation/screens/inbox_screen.dart' as _i2;
|
||||
import 'package:flash_mail/presentation/screens/login_screen.dart' as _i3;
|
||||
import 'package:flash_mail/presentation/screens/message_detail_screen.dart'
|
||||
as _i4;
|
||||
import 'package:flutter/material.dart' as _i6;
|
||||
|
||||
abstract class $AppRouter extends _i5.RootStackRouter {
|
||||
$AppRouter({super.navigatorKey});
|
||||
import 'package:auto_route/auto_route.dart' as _i8;
|
||||
import 'package:flutter/material.dart' as _i9;
|
||||
import 'package:smol_mail/presentation/screens/compose_screen.dart' as _i1;
|
||||
import 'package:smol_mail/presentation/screens/contact_detail_screen.dart'
|
||||
as _i2;
|
||||
import 'package:smol_mail/presentation/screens/contacts_screen.dart' as _i3;
|
||||
import 'package:smol_mail/presentation/screens/inbox_screen.dart' as _i4;
|
||||
import 'package:smol_mail/presentation/screens/message_detail_screen.dart'
|
||||
as _i5;
|
||||
import 'package:smol_mail/presentation/screens/onboarding_screen.dart' as _i6;
|
||||
import 'package:smol_mail/presentation/screens/settings_screen.dart' as _i7;
|
||||
|
||||
/// generated route for
|
||||
/// [_i1.ComposeScreen]
|
||||
class ComposeRoute extends _i8.PageRouteInfo<ComposeRouteArgs> {
|
||||
ComposeRoute({
|
||||
_i9.Key? key,
|
||||
String? to,
|
||||
String? subject,
|
||||
List<_i8.PageRouteInfo>? children,
|
||||
}) : super(
|
||||
ComposeRoute.name,
|
||||
args: ComposeRouteArgs(key: key, to: to, subject: subject),
|
||||
initialChildren: children,
|
||||
);
|
||||
|
||||
static const String name = 'ComposeRoute';
|
||||
|
||||
static _i8.PageInfo page = _i8.PageInfo(
|
||||
name,
|
||||
builder: (data) {
|
||||
final args = data.argsAs<ComposeRouteArgs>(
|
||||
orElse: () => const ComposeRouteArgs(),
|
||||
);
|
||||
return _i1.ComposeScreen(
|
||||
key: args.key,
|
||||
to: args.to,
|
||||
subject: args.subject,
|
||||
);
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
class ComposeRouteArgs {
|
||||
const ComposeRouteArgs({this.key, this.to, this.subject});
|
||||
|
||||
final _i9.Key? key;
|
||||
|
||||
final String? to;
|
||||
|
||||
final String? subject;
|
||||
|
||||
@override
|
||||
final Map<String, _i5.PageFactory> pagesMap = {
|
||||
AccountRoute.name: (routeData) {
|
||||
return _i5.AutoRoutePage<dynamic>(
|
||||
routeData: routeData,
|
||||
child: const _i1.AccountScreen(),
|
||||
);
|
||||
},
|
||||
InboxRoute.name: (routeData) {
|
||||
return _i5.AutoRoutePage<dynamic>(
|
||||
routeData: routeData,
|
||||
child: const _i2.InboxScreen(),
|
||||
);
|
||||
},
|
||||
LoginRoute.name: (routeData) {
|
||||
return _i5.AutoRoutePage<dynamic>(
|
||||
routeData: routeData,
|
||||
child: const _i3.LoginScreen(),
|
||||
);
|
||||
},
|
||||
MessageDetailRoute.name: (routeData) {
|
||||
final args = routeData.argsAs<MessageDetailRouteArgs>();
|
||||
return _i5.AutoRoutePage<dynamic>(
|
||||
routeData: routeData,
|
||||
child: _i4.MessageDetailScreen(
|
||||
key: args.key,
|
||||
id: args.id,
|
||||
subject: args.subject,
|
||||
),
|
||||
);
|
||||
},
|
||||
};
|
||||
String toString() {
|
||||
return 'ComposeRouteArgs{key: $key, to: $to, subject: $subject}';
|
||||
}
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
if (identical(this, other)) return true;
|
||||
if (other is! ComposeRouteArgs) return false;
|
||||
return key == other.key && to == other.to && subject == other.subject;
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => key.hashCode ^ to.hashCode ^ subject.hashCode;
|
||||
}
|
||||
|
||||
/// generated route for
|
||||
/// [_i1.AccountScreen]
|
||||
class AccountRoute extends _i5.PageRouteInfo<void> {
|
||||
const AccountRoute({List<_i5.PageRouteInfo>? children})
|
||||
: super(
|
||||
AccountRoute.name,
|
||||
initialChildren: children,
|
||||
);
|
||||
/// [_i2.ContactDetailScreen]
|
||||
class ContactDetailRoute extends _i8.PageRouteInfo<ContactDetailRouteArgs> {
|
||||
ContactDetailRoute({
|
||||
_i9.Key? key,
|
||||
required String address,
|
||||
List<_i8.PageRouteInfo>? children,
|
||||
}) : super(
|
||||
ContactDetailRoute.name,
|
||||
args: ContactDetailRouteArgs(key: key, address: address),
|
||||
initialChildren: children,
|
||||
);
|
||||
|
||||
static const String name = 'AccountRoute';
|
||||
static const String name = 'ContactDetailRoute';
|
||||
|
||||
static const _i5.PageInfo<void> page = _i5.PageInfo<void>(name);
|
||||
static _i8.PageInfo page = _i8.PageInfo(
|
||||
name,
|
||||
builder: (data) {
|
||||
final args = data.argsAs<ContactDetailRouteArgs>();
|
||||
return _i2.ContactDetailScreen(key: args.key, address: args.address);
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
class ContactDetailRouteArgs {
|
||||
const ContactDetailRouteArgs({this.key, required this.address});
|
||||
|
||||
final _i9.Key? key;
|
||||
|
||||
final String address;
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return 'ContactDetailRouteArgs{key: $key, address: $address}';
|
||||
}
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
if (identical(this, other)) return true;
|
||||
if (other is! ContactDetailRouteArgs) return false;
|
||||
return key == other.key && address == other.address;
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => key.hashCode ^ address.hashCode;
|
||||
}
|
||||
|
||||
/// generated route for
|
||||
/// [_i2.InboxScreen]
|
||||
class InboxRoute extends _i5.PageRouteInfo<void> {
|
||||
const InboxRoute({List<_i5.PageRouteInfo>? children})
|
||||
: super(
|
||||
InboxRoute.name,
|
||||
initialChildren: children,
|
||||
);
|
||||
/// [_i3.ContactsScreen]
|
||||
class ContactsRoute extends _i8.PageRouteInfo<void> {
|
||||
const ContactsRoute({List<_i8.PageRouteInfo>? children})
|
||||
: super(ContactsRoute.name, initialChildren: children);
|
||||
|
||||
static const String name = 'ContactsRoute';
|
||||
|
||||
static _i8.PageInfo page = _i8.PageInfo(
|
||||
name,
|
||||
builder: (data) {
|
||||
return const _i3.ContactsScreen();
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
/// generated route for
|
||||
/// [_i4.InboxScreen]
|
||||
class InboxRoute extends _i8.PageRouteInfo<void> {
|
||||
const InboxRoute({List<_i8.PageRouteInfo>? children})
|
||||
: super(InboxRoute.name, initialChildren: children);
|
||||
|
||||
static const String name = 'InboxRoute';
|
||||
|
||||
static const _i5.PageInfo<void> page = _i5.PageInfo<void>(name);
|
||||
static _i8.PageInfo page = _i8.PageInfo(
|
||||
name,
|
||||
builder: (data) {
|
||||
return const _i4.InboxScreen();
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
/// generated route for
|
||||
/// [_i3.LoginScreen]
|
||||
class LoginRoute extends _i5.PageRouteInfo<void> {
|
||||
const LoginRoute({List<_i5.PageRouteInfo>? children})
|
||||
: super(
|
||||
LoginRoute.name,
|
||||
initialChildren: children,
|
||||
);
|
||||
|
||||
static const String name = 'LoginRoute';
|
||||
|
||||
static const _i5.PageInfo<void> page = _i5.PageInfo<void>(name);
|
||||
}
|
||||
|
||||
/// generated route for
|
||||
/// [_i4.MessageDetailScreen]
|
||||
class MessageDetailRoute extends _i5.PageRouteInfo<MessageDetailRouteArgs> {
|
||||
/// [_i5.MessageDetailScreen]
|
||||
class MessageDetailRoute extends _i8.PageRouteInfo<MessageDetailRouteArgs> {
|
||||
MessageDetailRoute({
|
||||
_i6.Key? key,
|
||||
_i9.Key? key,
|
||||
required String folder,
|
||||
required String id,
|
||||
required String subject,
|
||||
List<_i5.PageRouteInfo>? children,
|
||||
List<_i8.PageRouteInfo>? children,
|
||||
}) : super(
|
||||
MessageDetailRoute.name,
|
||||
args: MessageDetailRouteArgs(
|
||||
key: key,
|
||||
id: id,
|
||||
subject: subject,
|
||||
),
|
||||
initialChildren: children,
|
||||
);
|
||||
MessageDetailRoute.name,
|
||||
args: MessageDetailRouteArgs(key: key, folder: folder, id: id),
|
||||
initialChildren: children,
|
||||
);
|
||||
|
||||
static const String name = 'MessageDetailRoute';
|
||||
|
||||
static const _i5.PageInfo<MessageDetailRouteArgs> page =
|
||||
_i5.PageInfo<MessageDetailRouteArgs>(name);
|
||||
static _i8.PageInfo page = _i8.PageInfo(
|
||||
name,
|
||||
builder: (data) {
|
||||
final args = data.argsAs<MessageDetailRouteArgs>();
|
||||
return _i5.MessageDetailScreen(
|
||||
key: args.key,
|
||||
folder: args.folder,
|
||||
id: args.id,
|
||||
);
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
class MessageDetailRouteArgs {
|
||||
const MessageDetailRouteArgs({
|
||||
this.key,
|
||||
required this.folder,
|
||||
required this.id,
|
||||
required this.subject,
|
||||
});
|
||||
|
||||
final _i6.Key? key;
|
||||
final _i9.Key? key;
|
||||
|
||||
final String folder;
|
||||
|
||||
final String id;
|
||||
|
||||
final String subject;
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return 'MessageDetailRouteArgs{key: $key, id: $id, subject: $subject}';
|
||||
return 'MessageDetailRouteArgs{key: $key, folder: $folder, id: $id}';
|
||||
}
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
if (identical(this, other)) return true;
|
||||
if (other is! MessageDetailRouteArgs) return false;
|
||||
return key == other.key && folder == other.folder && id == other.id;
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => key.hashCode ^ folder.hashCode ^ id.hashCode;
|
||||
}
|
||||
|
||||
/// generated route for
|
||||
/// [_i6.OnboardingScreen]
|
||||
class OnboardingRoute extends _i8.PageRouteInfo<void> {
|
||||
const OnboardingRoute({List<_i8.PageRouteInfo>? children})
|
||||
: super(OnboardingRoute.name, initialChildren: children);
|
||||
|
||||
static const String name = 'OnboardingRoute';
|
||||
|
||||
static _i8.PageInfo page = _i8.PageInfo(
|
||||
name,
|
||||
builder: (data) {
|
||||
return const _i6.OnboardingScreen();
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
/// generated route for
|
||||
/// [_i7.SettingsScreen]
|
||||
class SettingsRoute extends _i8.PageRouteInfo<void> {
|
||||
const SettingsRoute({List<_i8.PageRouteInfo>? children})
|
||||
: super(SettingsRoute.name, initialChildren: children);
|
||||
|
||||
static const String name = 'SettingsRoute';
|
||||
|
||||
static _i8.PageInfo page = _i8.PageInfo(
|
||||
name,
|
||||
builder: (data) {
|
||||
return const _i7.SettingsScreen();
|
||||
},
|
||||
);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,18 +0,0 @@
|
|||
import "package:auto_route/auto_route.dart";
|
||||
import "package:flash_mail/data/providers/providers.dart";
|
||||
import "package:flutter_riverpod/flutter_riverpod.dart";
|
||||
|
||||
class AuthGuard extends AutoRouteGuard {
|
||||
final WidgetRef ref;
|
||||
|
||||
AuthGuard(this.ref);
|
||||
|
||||
@override
|
||||
void onNavigation(NavigationResolver resolver, StackRouter router) {
|
||||
if (ref.read(accountProvider).isAuthenticated()) {
|
||||
router.replaceNamed("/inbox");
|
||||
} else {
|
||||
resolver.next(true);
|
||||
}
|
||||
}
|
||||
}
|
||||
23
lib/presentation/routes/home_guard.dart
Normal file
23
lib/presentation/routes/home_guard.dart
Normal file
|
|
@ -0,0 +1,23 @@
|
|||
import "package:auto_route/auto_route.dart";
|
||||
import "package:flutter_riverpod/flutter_riverpod.dart";
|
||||
|
||||
import "package:smol_mail/data/providers/providers.dart";
|
||||
import "package:smol_mail/presentation/routes/app_router.gr.dart";
|
||||
|
||||
/// The landing screen is only for users who cannot use the app yet: no
|
||||
/// identity, or no registered account.
|
||||
class HomeGuard extends AutoRouteGuard {
|
||||
final WidgetRef ref;
|
||||
|
||||
HomeGuard(this.ref);
|
||||
|
||||
@override
|
||||
void onNavigation(NavigationResolver resolver, StackRouter router) {
|
||||
if (ref.read(identityProvider) != null &&
|
||||
ref.read(accountProvider) != null) {
|
||||
router.replace(InboxRoute());
|
||||
} else {
|
||||
resolver.next(true);
|
||||
}
|
||||
}
|
||||
}
|
||||
22
lib/presentation/routes/identity_guard.dart
Normal file
22
lib/presentation/routes/identity_guard.dart
Normal file
|
|
@ -0,0 +1,22 @@
|
|||
import "package:auto_route/auto_route.dart";
|
||||
import "package:flutter_riverpod/flutter_riverpod.dart";
|
||||
|
||||
import "package:smol_mail/data/providers/providers.dart";
|
||||
import "package:smol_mail/presentation/routes/app_router.gr.dart";
|
||||
|
||||
/// Everything past onboarding needs an identity; the account can still be
|
||||
/// registered from settings.
|
||||
class IdentityGuard extends AutoRouteGuard {
|
||||
final WidgetRef ref;
|
||||
|
||||
IdentityGuard(this.ref);
|
||||
|
||||
@override
|
||||
void onNavigation(NavigationResolver resolver, StackRouter router) {
|
||||
if (ref.read(identityProvider) == null) {
|
||||
router.replace(OnboardingRoute());
|
||||
} else {
|
||||
resolver.next(true);
|
||||
}
|
||||
}
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue