处理客户端上的阿波罗服务器错误

时间:2019-01-15 12:11:34

标签: reactjs apollo-client apollo-server

我在做什么?

我想在apollo服务器上抛出一个错误,并在客户端上对其进行处理。

注意:我在apollo客户端上使用apollo-link-error中间件。

服务器:

import { UserInputError } from "apollo-server";

 Mutation: {     
    someMutation : { 
     try {
       // here is some code which failed
      } catch (error) { 
// base Error class has message property by default 
// response just hold some additional informations 
       throw new UserInputError(error.message, { response });
      }
    }
  }

客户

简化了我在客户端的突变实施

    <Mutation
       mutation={CREATE_ORDER}
     >
        {(createOrder, { loading, error }) => (
        ....
         try {
           await createOrder({  variables: {...}});
         } catch (createOrderError) {
          //  here I get Cannot read property 'data' of undefined
            console.log(createOrderError);

          }

         )}
   </Mutation>

我在客户端上收到以下错误(在上面的代码中的 catch子句中):

TypeError: Cannot read property 'data' of undefined
    at Mutation._this.onMutationCompleted (react-apollo.browser.umd.js:631)
    at react-apollo.browser.umd.js:586

此错误类似于 httpLink 的问题。

响应 :(来自chrome开发工具中的“网络”标签)

enter image description here

根据graphql规范:

  

如果在执行过程中遇到错误,导致无法执行   有效的响应,响应中的数据条目应为空。

因此,我假设服务器发出的响应是有效的。数据对象应为null。

我期望发生什么?

我想访问来自apollo服务器的响应如何实现?

感谢帮助!

1 个答案:

答案 0 :(得分:0)

访问查询或变异返回的数据之前要检查的东西

  1. 如果正在加载->返回一些加载器组件
  2. 如果存在错误->显示一些错误组件

如果以上两个条件中的任何一个都不匹配,那么请确保您具有数据。

除此之外,您还需要

1。在Apollo客户端"errorPolicy"

 const client = new ApolloClient({
    defaultOptions: {
      watchQuery: {
        errorPolicy: 'all'
      },
      query: {
        errorPolicy: 'all'
      },
      mutate: {
        errorPolicy: 'all'
      }
    },
    link,
    cache,
    connectToDevTools: true,
  })

2。用于自定义从服务器发送的错误-

您可以使用formatError

const server = new ApolloServer({
  ...root,
  resolverValidationOptions: {
    requireResolversForResolveType: false,
  },
  formatError, <---------- send custom error
  formatResponse: (response, query) => formatResponse({ response, query }),
  dataSources,
  context: async ({ req, res }) => {
    const user = req.user;
    return { user, req, res };
  }
});

例如

const formatError = (error) => {
  const { extensions } = error;
  logger.error(error);

  const exception = extensions.exception ? extensions.exception : {};
  logger.error('\nStackTrace');
  logger.error(exception.stacktrace);
  exception.stacktrace = null;
  const extractedError = extractErrorFromExtention(extensions);

  return extractedError || { message: error.message, code: extensions.code, exception };
};