Back

[AppwriteException: User (role: guests) missing scope (account)]

  • 0
  • React Native
  • Cloud
  • Auth
Ñìkhíl
22 Jun, 2024, 18:29

As i am sign in, basically the function is setup to create a session using account.createEmailPasswordSession(email, password);

TypeScript
export const Signin = async (email: string, password: string): Promise<Models.Session> => {
    try {
        const session: Models.Session = await account.createEmailPasswordSession(email, password);
        return session;
    } catch (error: unknown) {
        console.error(error);
        if (error instanceof Error) {
            throw new Error(error.message);
        } else {
            throw new Error('An Unknown error occurred');
        }
    }
}

And now we have a session connected with the email and password for the user which can be seen in the appwrite dashboard also. Now we can call the methods realted to the account like account.get and account.getsession('current') and all those methods will work fine. Using these methods on account object we need to check on the app that if the user is logged in or not, we can not use the global state that we had set because refresing the app will clear those states.

TL;DR
Developers are discussing handling a specific exception related to user role in a project. The getCurrentUser function retrieves user data, but there are issues with checking if a user is logged in. The GlobalProvider component manages user authentication state. The code snippet for sign-in shows how to create a session. The solution suggests using the account object to verify user login status.
Ñìkhíl
22 Jun, 2024, 18:29

This is how we are checking the current user in the useeffect.

TypeScript
import { createContext, useContext, useState, useEffect, ReactNode, } from "react";
import { User, getCurrentUser } from "../lib/appwrite";

interface GlobalContextType {
    isLoggedIn: boolean;
    setIsLoggedIn: (isLoggedIn: boolean) => void;
    user: User | null;
    setUser: (user: User | null) => void;
    isLoading: boolean;
}

const GlobalContext = createContext<GlobalContextType | undefined>(undefined);
export const useGlobalContext = () => {
    const context = useContext(GlobalContext);
    if (!context) {
        throw new Error('useGlobalContext must be used within a GlobalProvider');
    }
    return context;
};

export const GlobalProvider = ({ children }: { children: ReactNode }) => {
    const [isLoggedIn, setIsLoggedIn] = useState(false);
    const [user, setUser] = useState<User | null>(null);
    const [isLoading, setIsLoading] = useState(true);

    useEffect(() => {
        getCurrentUser().then(
            (currentUser) => {
                if (currentUser) {
                    setUser(currentUser);
                    setIsLoggedIn(true);
                } else {
                    setIsLoggedIn(false);
                    setUser(null);
                }
            }
        ).catch(
            (error: unknown) => {
                if (error instanceof Error) {
                    console.error("from context", error.message);
                } else {
                    console.error('An Unknown error occurred');
                }
            }
        ).finally(
            () => {
                setIsLoading(false);
            }
        );
    }, []);

    return (
        <GlobalContext.Provider value={{
            isLoggedIn,
            setIsLoggedIn,
            user,
            setUser,
            isLoading,
        }}>
            {children}
        </GlobalContext.Provider>
    )
}
Ñìkhíl
22 Jun, 2024, 18:29

And the getCurrentUser() function is given below:

TypeScript
export const getCurrentUser = async (): Promise<User | null> => {
    try {
        const currentAccount = await account.get<{}>();
        if (!currentAccount) throw Error;

        const currentUser = await database.listDocuments(
            config.databaseID,
            config.userCollectionID,
            [Query.equal('accountId', currentAccount.$id)]
        )
        if (!currentUser) throw Error;
        return currentUser.documents[0] as User;

    } catch (error: unknown) {
        console.error("from appwrite",error);
        if (error instanceof Error) {
            throw new Error(error.message);
        } else {
            throw new Error('An Unknown error occurred');
        }
        
    }
}

Since there is no session so no account methods are allowed to be called.

Ñìkhíl
22 Jun, 2024, 18:33

But then the question is that how to get that information that there is no session present and we need to return null here in the getCurrentUser function.

Steven
22 Jun, 2024, 18:36

If account.get() returns the role: guests error, they aren't logged in. That's how you check

Ñìkhíl
22 Jun, 2024, 18:44

Thank you for the response. yes we can, but instead of checking that in the catch block explicitly where other errors can also occur, It would be great if that would be handled by the account.get() or account.getsession('current') . Just my opinion. But yes As of now i will be trying to implementing the same, checking the status code in the catch block.

Reply

Reply to this thread by joining our Discord

Reply on Discord

Need support?

Join our Discord

Get community support by joining our Discord server.

Join Discord

Get premium support

Join Appwrite Pro and get email support from our team.

Learn more