javascript 使用graphql和apollo的角SSR,transferState未传输到客户端

k7fdbhmy  于 2023-02-21  发布在  Java
关注(0)|答案(1)|浏览(92)

我有一个Angular 应用程序,它在第一页显示文章。我不希望API调用被执行两次,第一次在服务器端,第二次在客户端,所以我使用传输状态来检查api是否已经被调用。如果我使用REST API,一切都工作正常,api调用只在服务器上执行,但当我用apollo添加graphql时,这似乎不起作用。

async ngOnInit() {
let myTransferStateKey = makeStateKey<any>('myDatas');

if (this.transferState.hasKey(myTransferStateKey)) {
  console.log('HomeComponent ngOnInit hasKey');
  this.transferState.get(myTransferStateKey, [])
  this.transferState.remove(myTransferStateKey);
} else {
  console.log('HomeComponent ngOnInit noKey');
  
  this.posts = (await this.graphql.query(this.home_query)) as {
    capital: string
    currency: string
    languages: []
    name: string
    native: string
  }[] 

  this.transferState.set(myTransferStateKey, this.posts) 
  
}

}

ig9co6j1

ig9co6j11#

如果您使用Apollo,请考虑使用他们的docs中使用的方法。请记住在配置中添加ssrMode和ssrForceFetchDelay以使其正常工作。正确设置API服务器URL也很重要,正如他们在最佳实践中提到的那样。示例:

import { APOLLO_OPTIONS } from 'apollo-angular';
import { HttpLink } from 'apollo-angular/http';
import { HttpClientModule } from '@angular/common/http';
import { InjectionToken, NgModule } from '@angular/core';
import { BrowserModule, makeStateKey, TransferState } from '@angular/platform-browser';
import { InMemoryCache } from '@apollo/client/core';
 
const APOLLO_CACHE = new InjectionToken<InMemoryCache>('apollo-cache');
const STATE_KEY = makeStateKey<any>('apollo.state');
 
@NgModule({
  imports: [
    // ...
    BrowserModule,
    HttpClientModule,
  ],
  providers: [
    {
      provide: APOLLO_CACHE,
      useValue: new InMemoryCache(),
    },
    {
      provide: APOLLO_OPTIONS,
      useFactory(httpLink: HttpLink, cache: InMemoryCache, transferState: TransferState) {
        const isBrowser = transferState.hasKey<any>(STATE_KEY);
 
        if (isBrowser) {
          const state = transferState.get<any>(STATE_KEY, null);
          cache.restore(state);
        } else {
          transferState.onSerialize(STATE_KEY, () => {
            return cache.extract();
          });
          // Reset cache after extraction to avoid sharing between requests
          cache.reset();
        }

        return {
          link: httpLink.create({ '/graphql', withCredentials: true }),
          cache,
          ssrMode: true,
          ssrForceFetchDelay: 100,
        };
      },
      deps: [HttpLink, APOLLO_CACHE, TransferState],
    },
  ],
  // ...
})
class AppModule {}

相关问题