Files

71 lines
2.3 KiB
Dart
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import 'package:flutter_riverpod/flutter_riverpod.dart';
import '../core/storage/local_storage.dart';
import '../models/auth_response.dart';
import '../utils/jwt_util.dart';
class AuthState {
final String? token;
final UserInfo? user;
const AuthState({this.token, this.user});
bool get isLoggedIn => token != null && token!.isNotEmpty;
const AuthState.initial() : this._();
const AuthState._({this.token, this.user});
}
class AuthNotifier extends Notifier<AuthState> {
@override
AuthState build() => const AuthState.initial();
/// App 启动时从本地存储恢复登录态。
/// 若 token 已在本地可判定过期,直接清理,避免带着废 token 进入主界面。
Future<void> load() async {
final token = LocalStorage.instance.getToken();
if (token == null || token.isEmpty) return;
if (isJwtExpired(token)) {
await LocalStorage.instance.clearAuth();
return;
}
final userInfo = LocalStorage.instance.getUserInfo();
state = AuthState(token: token, user: userInfo == null ? null : UserInfo.fromJson(userInfo));
}
/// 登录/注册成功后调用:持久化并更新状态
Future<void> loginSuccess(AuthResponse response) async {
final user = UserInfo(
username: response.username ?? '',
nickname: response.nickname ?? response.username ?? '',
avatar: response.avatar,
);
await LocalStorage.instance.setAuth(token: response.token, userInfo: user.toJson());
state = AuthState(token: response.token, user: user);
}
/// 改完资料后刷新本地缓存的用户信息。
///
/// 不发新 token —— 后端返回的 [AuthResponse.token] 是 null,
/// 所以这里保留原来的 token,只换 user。
Future<void> updateUserFromResponse(AuthResponse response) async {
final user = UserInfo(
username: response.username ?? state.user?.username ?? '',
nickname: response.nickname ?? state.user?.nickname ?? '',
avatar: response.avatar,
);
await LocalStorage.instance.setUserInfo(user.toJson());
state = AuthState(token: state.token, user: user);
}
Future<void> logout() async {
await LocalStorage.instance.clearAuth();
state = const AuthState.initial();
}
}
final authProvider = NotifierProvider<AuthNotifier, AuthState>(AuthNotifier.new);