赞
踩
在以flutter为底的app项目中,用户登录,退出等认证必须做在flutter项目里,那么采用何种状态管理,来全局管理用户认证呢?
今天我就借助flutter_bloc这个库来搭建一套可以复用的成熟用户认证系统
1、启动app,判断有无token,有token则跳转首页获取数据,无token则跳转需要授权页面如登录页
2、登录页登录,登陆后保存token,跳转首页
3、退出登录,删除token跳转需要授权页
那么总结起来就有三种事件
1、启动事件
2、登录事件
3、退出登录事件
1、在app启动后,需要初始化用户状态,那么用户当前是一个身份需要初始化的状态
2、如果有token,或者用户登录后那么用户就是一个已认证的状态
3、如果用户退出登录,那么用户当前是未认证的状态
1、是否有token,token是决定app是否认证的关键
2、删除token,退出登录需要删除
3、保存token,登录需要保存
4、跳转授权页面
5、跳转非授权页面
1、先编写认证事件:
part of 'authentication_bloc.dart'; //App认证事件,一般来说有三种,启动认证,登录认证,退出认证 abstract class AuthenticationEvent extends Equatable { const AuthenticationEvent(); @override List<Object?> get props => []; } //App启动事件 class AppStart extends AuthenticationEvent{} //App登录事件 class LogIn extends AuthenticationEvent{ final String token; LogIn(this.token); @override List<Object?> get props => [token]; @override String toString() =>"LoggedIn { token: $token }"; } //App退出事件 class LogOut extends AuthenticationEvent{}
2、编写认证状态
part of 'authentication_bloc.dart'; /// 认证状态 abstract class AuthenticationState extends Equatable { const AuthenticationState(); @override List<Object> get props => []; } /// - uninitialized - 身份验证未初始化 class AuthenticationUninitialized extends AuthenticationState {} /// - authenticated - 认证成功 class AuthenticationAuthenticated extends AuthenticationState {} /// - unauthenticated - 未认证 class AuthenticationUnauthenticated extends AuthenticationState {}
3、编写外部接口
abstract class IUserAuthentication{
bool hasToken();
void saveToken(String token);
void deleteToken();
void authPage();
void unAuthPage();
}
4、有了如上的内容咱们就可以编写核心逻辑bloc了
import 'dart:async'; import 'package:bloc/bloc.dart'; import 'package:equatable/equatable.dart'; import 'i_user_authentication.dart'; part 'authentication_event.dart'; part 'authentication_state.dart'; class AuthenticationBloc extends Bloc<AuthenticationEvent, AuthenticationState> { final IUserAuthentication iUserAuthentication; /// 初始化认证是未认证状态 AuthenticationBloc(this.iUserAuthentication) : super(AuthenticationUninitialized()); @override Stream<AuthenticationState> mapEventToState( AuthenticationEvent event, ) async* { if(event is AppStart){ // 判断是否有Token if(iUserAuthentication.hasToken()){ yield AuthenticationAuthenticated(); } else { yield AuthenticationUnauthenticated(); } }else if(event is LogIn){ iUserAuthentication.saveToken(event.token); yield AuthenticationAuthenticated(); }else if(event is LogOut){ iUserAuthentication.deleteToken(); yield AuthenticationUnauthenticated(); } } }
import 'package:flutter/widgets.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'authentication_bloc.dart'; class Authentication{ static TransitionBuilder init({ TransitionBuilder? builder, }) { return (BuildContext context, Widget? child) { var widget = BlocListener<AuthenticationBloc, AuthenticationState>( listener: (context, state) { var bloc = BlocProvider.of<AuthenticationBloc>(context); if (state is AuthenticationAuthenticated) { bloc.iUserAuthentication.authPage(); } else if (state is AuthenticationUnauthenticated) { bloc.iUserAuthentication.unAuthPage(); } }, child: child, ); if (builder != null) { return builder(context, widget ); } else { return widget; } }; } }
在项目中如何使用呢??
1、接口事件类
2、bloc初始化
3、监听初始化
代码如下:
接口实现类
class Auth implements IUserAuthentication{ static final String userTokenN = 'userToken'; Auth(){ _userMMKV = MMKVStore.appMMKV(name: "123"); } @override void authPage() { RouterName.navigateTo(LibRouteNavigatorObserver.instance.navigator!.context, RouterName.home,clearStack: true); } late MMKV _userMMKV; @override void deleteToken() { _userMMKV.removeValue(userTokenN); } @override bool hasToken() { return _userMMKV.decodeString(userTokenN)!=null; } @override void saveToken(String token) { _userMMKV.encodeString(userTokenN, token); } @override void unAuthPage() { RouterName.navigateTo(LibRouteNavigatorObserver.instance.navigator!.context, RouterName.login,replace: true); } }
2、初始化
MultiBlocProvider(
providers: [
//AuthenticationBloc bloc初始化
BlocProvider(create: (_) => AuthenticationBloc(Auth())),
],
child: MaterialApp(
...
builder: Authentication.init() //监听初始化
),
);
3、事件调用
1、退出按钮调用,BlocProvider.of(context).add(LogOut())
2、登录页面调用,BlocProvider.of(context).add(LogIn(“123”))
3、SplashPage页面调用 BlocProvider.of(context).add(AppStart())
如上搭建的一个用户认证系统,可以抽离项目做成package,再下次开发其他项目时候,就可以直接使用。方便快捷。
更多flutter教程请关注我的IMGeek:https://www.imgeek.org/people/33692
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。