通过Vue Apollo 在你的 Vue.js 应用中快速集成 GraphQL
1:安装Vue Apollo

npm install --save vue-apollo graphql apollo-client apollo-link apollo-link-http apollo-cache-inmemory graphql-tag

2:在Vue项目中注册Vue Apollo
新建ApolloClient.js,添加如下代码:

import { ApolloClient } from 'apollo-client'
import { createHttpLink } from 'apollo-link-http'
import { InMemoryCache } from 'apollo-cache-inmemory'
// 与 API 的 HTTP 连接
const httpLink = createHttpLink({
  // 你需要在这里使用绝对路径
  uri: 'http://localhost:3020/graphql',
})
// 缓存实现
const cache = new InMemoryCache()
// 创建 apollo 客户端
const apolloClient = new ApolloClient({
  link: httpLink,
  cache,
})

在app.js中添加如下代码:

import VueApollo from 'vue-apollo'
import ApolloClient from './ApolloClient'

Vue.use(VueApollo)
const apolloProvider = new VueApollo({
  defaultClient: ApolloClient,
})
/* eslint no-new:off */
new Vue({
  el: '#app',
  router,
// 像 vue-router 或 vuex 一样注入 apolloProvider
  apolloProvider,
  ...App,
})

到此,已经完整全局配置 Vue Apollo.

3:简单的应用示例
查询
为每个你需要通过 Apollo 的查询结果提供数据的 Vue 属性,在 apollo 对象中添加一个对应属性

<template>
  <div>{{ hello }}</div>
</template>
<script>
import gql from 'graphql-tag'
export default {
  apollo: {
    // 简单的查询,将更新 'hello' 这个 vue 属性
    hello: gql`query {
      hello
    }`,
  },
}
</script>

变更
使用 this.$apollo.mutate 发送变更语句:

methods: {
  async addTag() {
    // 调用 graphql 变更
    const result = await this.$apollo.mutate({
      // 查询语句
      mutation: gql`mutation ($label: String!) {
        addTag(label: $label) {
          id
          label
        }
      }`,
      // 参数
      variables: {
        label: this.newTag,
      },
    })
  }
}

4:碰到的问题:
1、因为前端采用vue-apollo客户端发送fetch方式的graphql的请求,而fetch请求也有的缺点:fetch只对网络请求报错,对400,500都当做成功的请求,需要封装去处理,所以说对于vue-axios的try,catch是获取不到错误的,Apollo请求超时的问题无法解决,httpLink没有提供timeout的接口,导致无法中断或重连当前请求
2、通过Apollo查询返回的数据是freeze状态,无法修改,可以通过对象浅拷贝或者序列化的方式解冻。因为我要做一个对于某一个模板增加适用模板区域的功能,那么要求是先调用模板详情接口,如果有区域就显示出来,对已有的区域可以做增删改的功能,获取到数据后存在vuex中,当我添加完成后更改vuex的数据报错,意思是不允许更改,解决办法就是在初始化vuex的数据时先深拷贝一份数据存入到vuex中,而不是直接存入,另外建议可以使用lodash.js,因为这个js库集成了很多方法,不用写那么多繁琐的代码
3、再说一下query和mutaionl两种方式解释,按照官方的意思是
query:仅获取数据(fetch)的只读请求
mutaion:获取数据后还有写操作的请求
基本上可以理解为,vue-apollo中的query方式就类似于Ajax中的get请求,而mutaion就类似于post请求