학생 참여 유도를 위해 공부 시작/종료 타이머와 학년별(오늘/이번주/전체) 랭킹 화면을 대시보드에 추가. 로그인 응답에 학년 정보를 포함시켜 세션 저장/복원 전체 경로에 전달되도록 함. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
71 lines
2.1 KiB
Dart
71 lines
2.1 KiB
Dart
// 🔐 "로그인 유지" 기능. 로그인 성공 시 계정 정보를 기기에 저장해두고,
|
|
// 다음 실행 때 로그인 화면을 건너뛰고 바로 대시보드로 들어가게 한다.
|
|
// (서버에 별도 세션/토큰 개념이 없어서, 비밀번호는 저장하지 않고 신원 정보만 저장한다.)
|
|
import 'dart:convert';
|
|
import 'package:shared_preferences/shared_preferences.dart';
|
|
|
|
class SavedSession {
|
|
final String userId;
|
|
final String userName;
|
|
final String role;
|
|
final bool isDeviceMatched;
|
|
final int? grade; // 🎓 공부 타이머 학년별 랭킹에서 본인 학년을 기본값으로 쓰기 위함.
|
|
|
|
const SavedSession({
|
|
required this.userId,
|
|
required this.userName,
|
|
required this.role,
|
|
required this.isDeviceMatched,
|
|
this.grade,
|
|
});
|
|
|
|
Map<String, dynamic> toJson() => {
|
|
'userId': userId,
|
|
'userName': userName,
|
|
'role': role,
|
|
'isDeviceMatched': isDeviceMatched,
|
|
'grade': grade,
|
|
};
|
|
|
|
factory SavedSession.fromJson(Map<String, dynamic> json) => SavedSession(
|
|
userId: json['userId'] as String,
|
|
userName: json['userName'] as String,
|
|
role: json['role'] as String,
|
|
isDeviceMatched: json['isDeviceMatched'] as bool? ?? true,
|
|
grade: json['grade'] as int?,
|
|
);
|
|
}
|
|
|
|
class SessionStore {
|
|
static const _key = 'saved_session_v1';
|
|
|
|
static Future<void> save(SavedSession session) async {
|
|
try {
|
|
final prefs = await SharedPreferences.getInstance();
|
|
await prefs.setString(_key, jsonEncode(session.toJson()));
|
|
} catch (_) {
|
|
// 저장 실패해도 로그인 자체는 계속 진행 (로그인 유지만 안 될 뿐).
|
|
}
|
|
}
|
|
|
|
static Future<SavedSession?> load() async {
|
|
try {
|
|
final prefs = await SharedPreferences.getInstance();
|
|
final raw = prefs.getString(_key);
|
|
if (raw == null) return null;
|
|
return SavedSession.fromJson(jsonDecode(raw));
|
|
} catch (_) {
|
|
return null;
|
|
}
|
|
}
|
|
|
|
static Future<void> clear() async {
|
|
try {
|
|
final prefs = await SharedPreferences.getInstance();
|
|
await prefs.remove(_key);
|
|
} catch (_) {
|
|
// 무시 - 어차피 로그아웃 화면으로는 이동한다.
|
|
}
|
|
}
|
|
}
|