login: Restore saved url and email if available

This commit is contained in:
2025-09-29 22:38:37 +02:00
parent bde317e159
commit b7d2580488
3 changed files with 21 additions and 25 deletions

View File

@@ -30,7 +30,7 @@ class _MyHomePageState extends State<MyHomePage> {
Future<List<Sheet>> acquireSheets() async { Future<List<Sheet>> acquireSheets() async {
final url = await _storageHelper.readSecure(SecureStorageKey.url); final url = await _storageHelper.readSecure(SecureStorageKey.url);
final jwt = await _storageHelper.readSecure(SecureStorageKey.jwt); final jwt = await _storageHelper.readSecure(SecureStorageKey.jwt);
apiClient = ApiClient(baseUrl: url!, token: jwt); apiClient = ApiClient(baseUrl: "${url!}/api", token: jwt);
// TODO: check if really logged in // TODO: check if really logged in
final sheets = await apiClient!.fetchSheets(); final sheets = await apiClient!.fetchSheets();
log.info("${sheets.length} sheets fetched"); log.info("${sheets.length} sheets fetched");

View File

@@ -1,5 +1,6 @@
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:jwt_decoder/jwt_decoder.dart'; import 'package:jwt_decoder/jwt_decoder.dart';
import 'package:logging/logging.dart';
import 'package:sheetless/api.dart'; import 'package:sheetless/api.dart';
import 'package:sheetless/home_page.dart'; import 'package:sheetless/home_page.dart';
import 'package:sheetless/storage_helper.dart'; import 'package:sheetless/storage_helper.dart';
@@ -12,6 +13,8 @@ class LoginPage extends StatefulWidget {
} }
class _LoginPageState extends State<LoginPage> { class _LoginPageState extends State<LoginPage> {
final log = Logger("_LoginPageState");
final TextEditingController _urlController = TextEditingController( final TextEditingController _urlController = TextEditingController(
text: "https://sheetable.julian-mutter.de", text: "https://sheetable.julian-mutter.de",
); );
@@ -27,30 +30,26 @@ class _LoginPageState extends State<LoginPage> {
@override @override
void initState() { void initState() {
super.initState(); super.initState();
_checkJwtValidity(); _restoreStoredValues();
} }
Future<void> _checkJwtValidity() async { Future<void> _restoreStoredValues() async {
final jwt = await _storageHelper.readSecure(SecureStorageKey.jwt); final jwt = await _storageHelper.readSecure(SecureStorageKey.jwt);
if (jwt != null) { if (jwt != null && await _isJwtValid(jwt)) {
final isValid = await _validateJwt(jwt); await _navigateToMainPage();
if (isValid) { return;
_navigateToMainPage(); }
return; final url = await _storageHelper.readSecure(SecureStorageKey.url);
} else { final email = await _storageHelper.readSecure(SecureStorageKey.email);
final url = await _storageHelper.readSecure(SecureStorageKey.url); if (url != null) {
final email = await _storageHelper.readSecure(SecureStorageKey.email); _urlController.text = url;
final password = await _storageHelper.readSecure( }
SecureStorageKey.password, if (email != null) {
); _emailController.text = email;
if (url != null && email != null && password != null) {
_login(url, email, password);
}
}
} }
} }
Future<bool> _validateJwt(String jwt) async { Future<bool> _isJwtValid(String jwt) async {
try { try {
bool expired = JwtDecoder.isExpired(jwt); bool expired = JwtDecoder.isExpired(jwt);
return !expired; return !expired;
@@ -63,15 +62,13 @@ class _LoginPageState extends State<LoginPage> {
setState(() { setState(() {
_error = null; _error = null;
}); });
serverUrl = "$serverUrl/api"; final apiClient = ApiClient(baseUrl: "$serverUrl/api");
final apiClient = ApiClient(baseUrl: serverUrl);
final loginResult = await apiClient.login(email, password); final loginResult = await apiClient.login(email, password);
if (loginResult.isOk()) { if (loginResult.isOk()) {
await _storageHelper.writeSecure(SecureStorageKey.url, serverUrl); await _storageHelper.writeSecure(SecureStorageKey.url, serverUrl);
await _storageHelper.writeSecure(SecureStorageKey.jwt, apiClient.token!); await _storageHelper.writeSecure(SecureStorageKey.jwt, apiClient.token!);
await _storageHelper.writeSecure(SecureStorageKey.email, email); await _storageHelper.writeSecure(SecureStorageKey.email, email);
await _storageHelper.writeSecure(SecureStorageKey.password, password); await _navigateToMainPage();
_navigateToMainPage();
} else { } else {
setState(() { setState(() {
_error = "Login failed.\n${loginResult.error()}"; _error = "Login failed.\n${loginResult.error()}";
@@ -127,7 +124,6 @@ class _LoginPageState extends State<LoginPage> {
TextFormField( TextFormField(
controller: _emailController, controller: _emailController,
validator: validateNotEmpty, validator: validateNotEmpty,
autofocus: true,
decoration: InputDecoration(labelText: 'Email'), decoration: InputDecoration(labelText: 'Email'),
textInputAction: TextInputAction.next, textInputAction: TextInputAction.next,
), ),

View File

@@ -1,7 +1,7 @@
import 'package:flutter_secure_storage/flutter_secure_storage.dart'; import 'package:flutter_secure_storage/flutter_secure_storage.dart';
import 'package:hive/hive.dart'; import 'package:hive/hive.dart';
enum SecureStorageKey { url, jwt, email, password } enum SecureStorageKey { url, jwt, email }
enum ConfigKey { twoPageMode } enum ConfigKey { twoPageMode }