【问题标题】:Unhandled Rejection (Error): GraphQL error: Not authenticated未处理的拒绝(错误):GraphQL 错误:未经过身份验证
【发布时间】:2020-09-24 02:37:24
【问题描述】:

我正在尝试在带有 apollo 客户端的反应应用程序中在注销时重置商店,以清除当前用户信息。但是用client!.resetStore()重置后会抛出错误Unhandled Rejection (Error): GraphQL error: Not authenticated

import React from 'react';
import { Link } from 'react-router-dom';
import { useMeQuery, useLogoutMutation } from '../../generated/graphql';
import { setAccessToken } from '../../accessToken';

interface Props {}

export const Navigation : React.FC<Props> = () =>{
    const { data, loading } = useMeQuery();
    const [logout, {client}] = useLogoutMutation();
    let body: any = null;

    if (loading) {
        body = null;
    } else if (data && data.me) {
        body = <div>welcome {data.me.email} </div>;
    } else {
        body = <div>Not logged in</div>;
    }

    return (
        <header>
            <div>
                <Link to="/login">Login</Link>
            </div>
            <div>
                {!loading && data && data.me ?
                    <button onClick= {
                        async () => {
                            await logout();
                            setAccessToken('');
                            await client!.resetStore();
                        }}
                    >
                    Logout
                    </button>
                    : null
                }
            </div>
            { body }
        </header>
    )
}

我的apollo客户端配置是:

const cache = new InMemoryCache({});

const authLink = new ApolloLink((operation, forward) =>
  new Observable(observer => {
    let handle : any;
     Promise.resolve(operation)
      .then((operation) => {
        const accessToken = getAccessToken();

        if (!accessToken) return;

        operation.setContext({
            headers: { authorization: `bearer ${accessToken}` }
        });
     })
      .then(() => {
        handle = forward(operation).subscribe({
          next: observer.next.bind(observer),
          error: observer.error.bind(observer),
          complete: observer.complete.bind(observer),
        });
      })
      .catch(() => {observer.error.bind(observer)});
    return () => {
      if (handle) handle.unsubscribe();
    };
  })
);

const requestlink = new HttpLink({
    uri: 'http://localhost:4000/graphql',
    credentials: 'include'
});

const errorLink = onError(({ graphQLErrors, networkError }) => {
    if (graphQLErrors)
    graphQLErrors.forEach(({ message, locations, path }) =>
      console.log(
        `[GraphQL error]: Message: ${message}, Location: ${locations}, Path: ${path}`
      )
    );
  if (networkError) console.log(`[Network error]: ${networkError}`);
});

const refreshTokenLink = new TokenRefreshLink({
    accessTokenField: 'accessToken',
    isTokenValidOrUndefined: () => {
        const token = getAccessToken();

        if (!token) return true;

        try {
            const {exp} = JwtDecode(token);
            if (Date.now() >= exp * 1000) return false;
            return true;
        } catch(error) {
            return false;
        }
    },
    fetchAccessToken: () => {
        return fetch('http://localhost:4000/refresh_token', {
            method: 'POST',
            credentials: 'include'
        });
    },
    handleFetch: accessToken => {
       setAccessToken(accessToken)
    },
    handleError: err => {
        console.warn('Your refresh token is invalid. Try to relogin');
        console.error(err);
    }
});

const client = new ApolloClient({
  link: ApolloLink.from([
    errorLink,
    refreshTokenLink,
    authLink,
    requestlink,
  ]),
  cache
});

有人可以帮我弄清楚如何解决这个问题吗?请

错误堆栈。

【问题讨论】:

  • 可能不是 client.resetstore 抛出错误,应该是 useMeQuery 是我的感觉。尝试处理如下错误场景并更新 const { data,eror, loading } = useMeQuery();
  • 也是ui或console中的错误?
  • 嗨@MeanMan 我已经尝试过你提到的,如果发生错误,我添加了一个条件来采取不同的行动,但错误仍然存​​在。根据您的问题,用户界面中出现错误。
  • 你能分享一下错误堆栈吗?
  • @MeanMan 我已经添加了堆栈的图像,请检查一下吗?

标签: reactjs typescript graphql react-apollo apollo-client


【解决方案1】:

将 try/catch 块添加到您的注销 ;)

<button onClick={
  async () => {
    try {
      await logout();
      setAccessToken('');
      await client!.resetStore();
    } catch (err) {
      console.log(err.message)
    }
  }}
>

【讨论】:

    猜你喜欢
    • 2017-04-04
    • 2022-08-22
    • 2018-05-02
    • 2018-04-25
    • 1970-01-01
    • 2017-06-08
    • 2017-10-22
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多