Auth-Context在类型方面存在一些问题



我的代码不起作用,尽管它是使用本教程制作的(使用AuthContext链接到确切的文件(。这个片段尤其是Auth-Context的一部分。唯一的区别是我用typescript而不是JS进行编码。告诉我你是否需要其他东西来帮助我解决问题。

useEffect(() => {
const user = supabase.auth.getUser().user;
setCurrentUser(user)
const auth = supabase.auth.onAuthStateChange((event, session) => {
if (event === 'SIGNED_IN') {
setCurrentUser(session.user)
}
if (event === 'SIGNED_OUT') {
setCurrentUser(null)
}
})
return () => auth.data.unsubscribe()
}, [])

错误:

ERROR in src/contexts/AuthContext.tsx:76:46
TS2339: Property 'user' does not exist on type 'Promise<UserResponse>'.
74 |
75 |     useEffect(() => {
> 76 |         const user = supabase.auth.getUser().user;
|                                              ^^^^
77 |         setCurrentUser(user)
78 |
79 |         const auth = supabase.auth.onAuthStateChange((event, session) => {
ERROR in src/contexts/AuthContext.tsx:81:32
TS2531: Object is possibly 'null'.
79 |         const auth = supabase.auth.onAuthStateChange((event, session) => {
80 |             if (event === 'SIGNED_IN') {
> 81 |                 setCurrentUser(session.user)
|                                ^^^^^^^
82 |             }
83 |
84 |             if (event === 'SIGNED_OUT') {
ERROR in src/contexts/AuthContext.tsx:81:32
TS2345: Argument of type 'User' is not assignable to parameter of type 'SetStateAction<undefined>'.
Type 'User' provides no match for the signature '(prevState: undefined): undefined'.
79 |         const auth = supabase.auth.onAuthStateChange((event, session) => {
80 |             if (event === 'SIGNED_IN') {
> 81 |                 setCurrentUser(session.user)
|                                ^^^^^^^^^^^^
82 |             }
83 |
84 |             if (event === 'SIGNED_OUT') {
ERROR in src/contexts/AuthContext.tsx:85:32
TS2345: Argument of type 'null' is not assignable to parameter of type 'SetStateAction<undefined>'.
83 |
84 |             if (event === 'SIGNED_OUT') {
> 85 |                 setCurrentUser(null)
|                                ^^^^
86 |             }
87 |         })
88 |
ERROR in src/contexts/AuthContext.tsx:89:32
TS2339: Property 'unsubscribe' does not exist on type '{ subscription: Subscription; }'.
87 |         })
88 |
> 89 |         return () => auth.data.unsubscribe()
|                                ^^^^^^^^^^^
90 |
91 |     }, [])
92 |

提前感谢的帮助

Suabase v@2.0.0+

可用的auth函数及其返回类型略有变化。它们不再提供supabase.auth.user()函数,而只提供可承诺的supabase.auth.getUser()。getUser的返回类型为

export type UserResponse =
| {
data: {
user: User
}
error: null
}
| {
data: {
user: null
}
error: AuthError
}

我相信对象解构也更可读,所以

const { data: { user } = await supabase.auth.getUser()

将是优选的。

这也解决了的返回类型onAuthStateChange()的返回问题

{
data: { subscription: Subscription }
}

所以你的代码会变成

const { data: { subscription }} = supabase.auth.onAuthStateChange(callback);

Suabase v@1.0.0+Supbase提供了两个检索用户的功能,.user()..getUser().user()从localStorage获取用户,这意味着它是一个非Promise函数。.getUser()使用jwt从服务器获取用户,因此是Promise。在教程中,他们使用.user()函数,这就是为什么没有等待的原因。在代码中使用.getUser()函数。要继续使用useEffect中的.getUser()函数,您必须在异步函数中调用它

useEffect(() => {
const fetchUser = async() => {
const { user } = await supabase.auth.getUser();
setCurrentUser(user);
}
fetchUser();
},[])

useState类型若要解决useState错误,当状态类型与传递给它的defaultValue类型不同时,必须将类型传递给useState((函数。const [str, setStr] = useState('');推断变量为字符串,而const [idk, setIdk] = useState(null)仅推断变量为未定义变量,这就是为什么当您尝试将currentUser设置为User或null类型的变量时,它会引发错误。

解决此问题的方法是将用户类型传递给useState

import { User } from '@supabase/supabase-js';
const [currentUser, setCurrentUser] = useState<User | null>(null);

无效检查要解决"Object could be null"的错误,您所要做的就是添加一个无效检查,可以是if/else语句的形式

if(user) or if(user !== null) {
setCurrentUser(user)
}

或添加无效变量检查,`

const user = session?.user;

两者之间有细微差别!用户或用户!==null,后者的包容性较小。参见此处

supabase和typescript的文档都是很棒的资源

如果您没有特别需要为supabase创建自己的身份验证系统,我建议您使用supabase身份验证助手。

最新更新