and right now it's throwing, and I have no way of knowing when it's set other than after login but the authRepository handles all of the methods around the user and that ref.watch is supposed to update the data (it's a reactive caching framework so the extra network calls don't matter)
thats why i recommend doing something like this where you have methods for login and/or init that can be called to make an api call and then set the state
what's the new code? and where are you calling currentUser?
I'm currently doing this
@Riverpod(keepAlive: true)
Future<User?> authState(AuthStateRef ref) async {
final User? user =ref.watch(authRepositoryProvider).currentUser;
return user;
}
@Riverpod(keepAlive: true)
AuthRepository authRepository(AuthRepositoryRef ref) {
final account = ref.watch(appwriteAccountProvider);
return AuthRepository(account: account);
}
class AuthRepository {
AuthRepository({required this.account});
final Account account;
User? user;
User? get currentUser {
if (user != null) {
return user;
} else {
return null;
}
}
Future<User?> _checkCurrentUser() async {
try {
final maybeUser = await account.get();
user = maybeUser;
} catch (e) {
return Future.value(null);
}
}
which is obviously disconnected
I could do on login ref.read(authRepositoryProvider).checkCurrentUser() after login
but I really don't think it makes sense the way it gets translated to flutter
because if it was just Future<User?> instead of a User than it would be null until it's not and the provider would work correctly
It just seems like an implementation where error handling is on the developer even though the thing I'm asking is "is the user logged in?"
calling checkCurrentUser() won't trigger any state updates
so what exception is being thrown now?
It isn't working ATM. Working on it.
okay so if checkCurrentUser won't trigger any state updates what am I supposed to do?
that's my issue I'm having here
if I could call account.get() and it would return User? then I could just watch that value, because I can't do that I have to develop a roundabout way of creating a simple authentication system
i already told you
you can try this
okay. It technically shouldn't be a repository but I'll do that
I ended up doing this in case it happens again
import 'package:appwrite/models.dart';
import 'package:bealbot_ai/core/core.dart';
import 'package:riverpod_annotation/riverpod_annotation.dart';
part 'appwrite_auth_state.g.dart';
@Riverpod(keepAlive: true)
class AppwriteAuthState extends _$AppwriteAuthState {
User? user;
@override
Future<User?> build() async {
return await checkCurrentUser();
}
Future<User?> checkCurrentUser() async {
if (user != null) {
return user;
} else {
try {
final account = ref.watch(appwriteAccountProvider);
final maybeUser = await account.get();
user = maybeUser;
return user;
} catch (e) {
return Future.value(null);
}
}
}
}
still testing to make sure it works
Please, can you publish the code of the "appwriteAccountProvider" to take the account, thanks
import 'package:appwrite/models.dart';
import 'package:bealbot_ai/core/core.dart';
import 'package:riverpod_annotation/riverpod_annotation.dart';
part 'appwrite_auth_state.g.dart';
@Riverpod(keepAlive: true)
class AppwriteAuthState extends _$AppwriteAuthState {
User? user;
@override
Future<User?> build() async {
return await checkCurrentUser();
}
Future<User?> checkCurrentUser() async {
if (user != null) {
return user;
} else {
try {
final account = ref.watch(appwriteAccountProvider);
final maybeUser = await account.get();
user = maybeUser;
return user;
} catch (e) {
return Future.value(null);
}
}
}
}
import 'package:appwrite/appwrite.dart';
import 'package:appwrite/models.dart';
import 'package:bealbot_ai/core/core.dart';
import 'package:bealbot_ai/features/auth/data/appwrite_auth_state.dart';
import 'package:bealbot_ai/features/auth/domain/app_user.dart';
import 'package:flutter/foundation.dart';
import 'package:riverpod_annotation/riverpod_annotation.dart';
// Want to sign up or get user account -> Account (from appwrite)
// Want to access user related data -> model.User (from models.dart)
part 'auth_repository.g.dart';
@Riverpod(keepAlive: true)
Future<User?> authState(AuthStateRef ref) async {
return ref.watch(appwriteAuthStateProvider).value;
}
@Riverpod(keepAlive: true)
AuthRepository authRepository(AuthRepositoryRef ref) {
final account = ref.watch(appwriteAccountProvider);
return AuthRepository(account: account);
}
class AuthRepository {
AuthRepository({required this.account});
final Account account;
User? user;
User? get currentUser {
if (user != null) {
return user;
} else {
return null;
}
}
Future<User?> checkCurrentUser() async {
try {
final maybeUser = await account.get();
user = maybeUser;
} catch (e) {
return Future.value(null);
}
return null;
}
Future<AppUser> signUp({
required String email,
required String password,
}) async {
try {
final userId = ID.unique();
await account.create(
userId: userId,
email: email,
password: password,
);
final AppUser appUser = AppUser(
$id: userId,
email: email,
name: getNameFromEmail(email),
profilePic: '',
);
return appUser;
} on AppwriteException catch (e, st) {
//TODO: Implement Error Handling
debugPrint("Appwrite Exception: ${e.message}\n${st.toString()}");
} catch (e, st) {
//TODO: Implement Error Handling
debugPrint("Appwrite Exception: ${e.toString()}\n${st.toString()}");
}
throw Exception("Failed to sign up user, we should never reach here");
}
Future<void> login({
required String email,
required String password,
}) async {
try {
final result = await account.createEmailSession(
email: email,
password: password,
);
debugPrint(result.toString());
} on AppwriteException catch (e, st) {
//TODO: Implement Error Handling
debugPrint("Appwrite Exception: ${e.message}\n${st.toString()}");
} catch (e, st) {
//TODO: Implement Error Handling
debugPrint("Appwrite Exception: ${e.toString()}\n${st.toString()}");
}
}
}
I did this in the end
One question, when it make "final account = ref.watch(appwriteAccountProvider);" that provieder where is it?
wherever you need it
oh
the appwrite account
that's in its own providers file but that's just literally doing the basic Appwrite Flutter setup as a provider
Recommended threads
- CORS error only on tables db api After u...
I've recently updated my self hosted appwrite instance to the 1.8.0 and updated my frontend with the tables db apis but strangely, even if I'm able to log in, g...
- [SOLVED] Access ExecutionStatus of a fun...
I am calling a cloud function from the newest Flutter SDK 20.2.1with the `xasync: false` flag and get the result, but the `execution.status` is not a String and...
- Appwrite isn't accepting the api from se...
Error creating user: AppwriteException: Server Error type: 'general_unknown', response: '{"message":"Server Error","code":500,"type":"general_unknown","versi...