尝试在我的演示应用程序上设置身份验证检查器。目前使用shared_preferences包存储从demo API获取的jwt token。
我已经组合了一个函数,它返回Future bool来验证我们是否存储了一个令牌,以及该令牌是否未过期:
Future<bool> isUserAuthenticated() async {
if (tokenIsStored) {
if (tokenIsNotExpired) {
return true;
}
}
return false;
}
因此,在MyHomePage状态下,我正在考虑使用FutureBuilder来处理验证
class _MyHomePageState extends State<MyHomePage> {
Future<bool> isUserAuthenticated = Future.delayed(const Duration(seconds: 1), () => API().isUserAuthenticated());
@override
Widget build(BuildContext context) {
return FutureBuilder(
future: isUserAuthenticated,
builder: (context, snapshot) {
if (snapshot.hasData) {
if (snapshot.data as bool) {
return Text("Hello");
} else {
return const LoginPage();
}
}
return CircularProgressIndicator();
},
);
}
}
然后通过LoginPage请求jwt token并导航回MyHomePage。
ElevatedButton(
onPressed: () {
setState(() => waitingForAPI = true);
String username = usernameController.text;
String password = passwordController.text;
API().login(username, password).then((credsWereValid) {
if (credsWereValid) {
Navigator.pushNamed(context, '/home');
}
});
}
)
这会创建一个“总是转发”的流,如:
MyHomePage -> LoginPage -> MyHomePage
我不知道为什么,但这看起来不像是一个好的流动。我认为正确的流程应该是从LoginPage返回Navigator.pop调用:
MyHomePage -> LoginPage
MyHomePage <- LoginPage
我相信要做到这一点,我们需要重新修改我的主页如下:
class _MyHomePageState extends State<MyHomePage> {
Future<bool> isUserAuthenticated = Future.delayed(const Duration(seconds: 1), () => API().isUserAuthenticated());
@override
Widget build(BuildContext context) {
return FutureBuilder(
future: isUserAuthenticated,
builder: (context, snapshot) {
if (snapshot.hasData) {
if (snapshot.data as bool) {
return Text("Hello");
} else {
// return const LoginPage();
Navigator.pushNamed(context, '/login');
}
}
return CircularProgressIndicator();
},
);
}
}
LoginPage逻辑如下:
ElevatedButton(
onPressed: () {
setState(() => waitingForAPI = true);
String username = usernameController.text;
String password = passwordController.text;
API().login(username, password).then((credsWereValid) {
if (credsWereValid) {
Navigator.pop(context);
}
});
}
)
我的问题是我应该坚持哪一种设计模式?还是应该追求另一种设计模式?
1条答案
按热度按时间fdx2calv1#
FutureBuilder
和Navigator
是一次性使用的auth方法。有一个简单的方法可以让这个过程顺利地来回进行:在身份验证页面中生成一个
Stream
的身份验证状态数据,然后使用一个Provider
在转换页面中侦听该数据。有关详细说明,您可以参考此video