如何在Apollo Angular中使用带有refetchQueries的optimisticResponse

时间:2019-05-29 03:47:34

标签: angular graphql apollo apollo-client

我正在尝试利用Apollo的Optimistic UI,但无法使其按预期工作。为了对其进行测试,我在服务器上设置了一个断点,以便可以停止响应。我希望看到突变会导致列表中的更改,但是整个过程都在等待服务器的响应。我在做什么错了?

这是Angular 7,Angular的Apollo-angular客户端2.4.0:

"apollo-angular": "^1.5.0",
    "apollo-angular-link-http": "^1.6.0",
    "apollo-cache-inmemory": "^1.3.2",
    "apollo-client": "^2.4.0",
    "apollo-link": "^1.2.11",
    "apollo-link-error": "^1.1.10",

要查看该项目是否在缓存中,我首先调用了此方法,它返回了预期的ID:

let testID = defaultDataIdFromObject(mail); 
console.log('found in cache: ', testID); // outputs the correct ID 
(e.g. found in cache)

控制台输出:

  

电子邮件:Cl4weDliM2QyZjQ1OTU2ZTZlMmZmOTAyMjRkYTkxNmE2MjI1ZDk2NWM3MDcAAAFrAUPhyTB4OWIzZDJmNDU5NTZlNNUUzZYYMYyYRYOT1Y

这是完整的查询:

this.trashEmailGQL.mutate({
      id: mail.id,
      table: Table.ARCHIVE
    },{
      refetchQueries: [{
        query: this.getEmailsGQL.document,
        variables: {table: Table.ARCHIVE}
      },
      {
        query: this.getEmailsGQL.document,
        variables: {table: Table.TRASH}
      }],
      optimisticResponse:{
        __typename:'Mutation',
        trashEmail:{
          __typename:"Email",
          id:mail.id,
          fromEmail:mail.fromEmail,
          fromName:mail.fromName,
          fromAddress:mail.fromAddress,
          cc: mail.cc,
          bcc: [],
          replyTo:mail.replyTo,
          body:mail.body,
          contentType:mail.contentType,
          draftId:"",
          read:mail.read,
          inReplyTo:mail.inReplyTo,
          inReferences:mail.inReferences,
          created:mail.created
        }
      }
    }).subscribe(({data}) => {
      console.log('Trashed email response: ', data);
    }, (err) => {
      this.errorService.handleError(err);
    });

我希望Apollo会从缓存中返回结果,并在服务器返回任何响应之前更新表。

1 个答案:

答案 0 :(得分:0)

最后弄清楚了。 Apollo 2.x不支持开箱即用的删除突变。因此,需要从缓存中手动删除。该解决方案看起来不太好(代码爆炸),但是比将一块石头扔在您的背上更好。

据说3.x版应该可以解决此问题,但是目前,这是我发现可以预期的解决方案。

this.trashEmailGQL.mutate({
      id: mail.id,
      table: Table.ARCHIVE
    },  
    {
        refetchQueries: [{
          query: this.getEmailsGQL.document,
          variables: {table: Table.ARCHIVE}
        },
        {
          query: this.getEmailsGQL.document,
          variables: {table: Table.TRASH}
        }], 
        optimisticResponse:{
          __typename:'Mutation',
          trashEmail:{
            __typename:"Email",
            id:mail.id,
            fromEmail:mail.fromEmail,
            fromName:mail.fromName,
            fromAddress:mail.fromAddress,
            cc: mail.cc,
            bcc: [],
            replyTo:mail.replyTo,
            body:mail.body,
            contentType:mail.contentType,
            draftId:"",
            read:mail.read,
            inReplyTo:mail.inReplyTo,
            inReferences:mail.inReferences,
            created:mail.created
          }
        },
        update: (store, {data :{trashedEmail}}) => {
          const data = store.readQuery({query: this.getEmailsGQL.document, variables: {table: Table.ARCHIVE}});
          if (data && data.hasOwnProperty('getEmails')) {
            let cacheList:Email[] = data['getEmails'];
            let foundItemIndex = cacheList.findIndex(i => i.id === mail.id);
            if (foundItemIndex > -1) {
              cacheList.splice(foundItemIndex,1)
              data['getEmails'] = cacheList
              store.writeQuery({query: this.getEmailsGQL.document, variables: {table: Table.ARCHIVE}, data:data});
            }
          }
        }
      }
     ).subscribe(({data}) => {
      console.log('Trashed email response: ', data);
    }, (err) => {
      this.errorService.handleError(err);
    });