最近开始使用graphQL和Apollo – apollo-client.
我在graphQL之上构建了一个Web服务,它运行得很好.我面临的唯一问题是项目的客户端.例如(请参阅下面的代码),在运行createVideo()后,我的组件的数据属性是一个可观察的,它正在观察查询不会自动刷新并且在回调上手动调用apollo.query似乎不需要任何影响,因为查询返回缓存的结果,而不是服务器的结果.
我错过了什么吗?
app.component.ts import {Component,OnInit} from '@angular/core'; import {Apollo,ApolloQueryObservable} from 'apollo-angular'; import 'rxjs/Rx'; import gql from 'graphql-tag'; // http://dev.apollodata.com/angular2/mutations.html const NewVideoQuery = gql` mutation AddVideoQuery($title: String!,$duration: Int!,$watched: Boolean!){ createVideo(video: { title: $title,duration: $duration,watched: $watched } ){ id,title } } `; const VideoQuery = gql` { videos { id,title } } `; @Component({ selector: 'app-root',templateUrl: './app.component.html',styleUrls: ['./app.component.css'] }) export class AppComponent implements OnInit { data: ApolloQueryObservable<any>; video: any = {}; constructor(private apollo: Apollo) { } ngOnInit() { this.data = this.apollo.watchQuery({query: VideoQuery}); } createVideo() { /** * This will send a mutate query to the server. */ // @todo After running the mutate,the watch query doesn't refresh this.apollo.mutate({ mutation: NewVideoQuery,variables: { 'title': this.video.title || 'Some Video' + Math.floor(Math.random() * 10),'duration': 123213,'watched': true } }).subscribe((afterMutation) => { console.log(afterMutation); // This fires but query doesn't hit the server since it's coming from cache. // @todo Not even by re-running it here this.apollo.query({query: VideoQuery}) .subscribe((data) => { console.log(data); }); },(err) => alert(err)); } }
//app.component.html <div *ngFor="let x of data | async | select: 'videos'"> <div><b>{{x.id}}</b>{{x.title}}</div> </div> <label> Title <input type="text" [(ngModel)]="video.title"> </label> <button (click)="createVideo()">{{title}}</button>
解决方法
我想到了.
Apollo-client默认缓存我们的查询并重新运行相同的查询当然会从缓存中返回结果,而不是从服务器返回.
Apollo-client默认缓存我们的查询并重新运行相同的查询当然会从缓存中返回结果,而不是从服务器返回.
当然,因为我做了一个突变来创建一个新记录,我希望服务器自动刷新数据集,但事实并非如此.
为了解决这个问题,我提出了从createVideo变异的成功回调中重新运行查询的想法,但这次我添加了一个名为fetchPolicy的特殊选项,它支持以下值:
'cache-first' | 'cache-and-network' | 'network-only' | 'cache-only' | 'standby'
最后我的fetch查询如下所示:
this.apollo.query({query: VideoQuery,fetchPolicy: 'network-only'}) .subscribe(()=>{ console.log('refresh done,our watchQuery will update') })
奖金提示:
关于Apollo的另一个有趣的功能是你可以设置一个像这样的池间隔,这样你的数据总是与服务器同步
this.data = this.apollo.watchQuery({query: VideoQuery,pollInterval: 10000});