-
Notifications
You must be signed in to change notification settings - Fork 1
Redirections
It is a common use case when some parts of your app should be hidden until some condition. For example, you would like to not allow a user to visit some pages until he/she is signed in.
This is supported in Theseus Navigator by using Redirections.
You can define a list of Redirections for the destination that you want to guard. Redirections are applied in the provided order.
Destination(
// ...
redirections: [
// Your redirections here
],
)In Redirection you provide a validator function and a destination to redirect.
If the validator function returns true, the user is allowed to navigate the original destination. Otherwise, the user is redirected to provided destination.
Destination(
// ...
redirections: [
Redirection(
validator: (destination) async => isLoggedIn,
destination: Destinations.login,
),
],
)The original destination is available as a parameter of the validator function, so you can use it in the validation logic.
It is assumed that the validator function is asynchronous. If your certain validation could be done synchronously, consider using return SynchronousFuture with the result.
When the asynchronous validator function takes a long time, the waiting view is displayed until the validator returns the result. Please see [this section] to learn how to customize that view.
Let's take a simple example app with three screens - Home, Settings and Login. Here are destinations and the navigation scheme:
class Destinations {
static final home = Destination(
path: '/home',
isHome: true,
builder: (context, parameters) => const HomeScreen(),
);
static final settings = Destination(
path: '/settings',
builder: (context, parameters) => const SettingsScreen(),
);
static final login = Destination(
path: '/login',
builder: (context, parameters) => const LoginScreen(),
);
}
final navigationScheme = NavigationScheme(
destinations: [
Destinations.home,
Destinations.settings,
Destinations.login,
],
);To restrict navigation to the Settings screen for not logged in user, we need to do the following:
- Add Redirection to settings destination
static final settings = Destination(
path: '/settings',
builder: (context, parameters) => const SettingsScreen(),
redirections: [
Redirection(
validator: (destination) async {
return isLoggedIn;
},
destination: login,
),
],
);The validator function returns isLoggedIn value, which contains the current state of the user.
- Implement Login screen
We need to implement the Login screen in the way, so user wouldn't be able to return back until logged in.
class LoginScreen extends StatelessWidget {
const LoginScreen({
Key? key,
}) : super(key: key);
@override
Widget build(BuildContext context) {
return Scaffold(
body: Center(
child: ElevatedButton(
onPressed: () {
isLoggedIn = !isLoggedIn;
navigationScheme.goBack();
},
child: Text(isLoggedIn ? 'Log Out' : 'Log In'),
),
),
);
}
}On the button click the login state is changed and we navigate back, so the Settings screen became visible.
- Result
Now if the user navigates to Settings screen and he/she is not logged in, the Login screen will be displayed automatically. Once user logged in, the originally requested Settings screen will appear.
localhost_55550_._home.-.Google.Chrome.2022-11-27.16-26-51_Trim.2.mp4
Check full source code of this example here: Redirection example code