在开始学习GraphQL之前,我们需要先理解的事情

我是佐佐木,前几天第一次在LT上做演讲!?

在非常温暖的氛围中,我有幸发表演讲,自那之后,我逐渐开始参加其他的演讲活动。
一旦参加就会上瘾!强烈推荐!✨

现在如您所料,第一次的LT是关于“GraphQL入门”的内容。

在进行LT演讲之前,我对GraphQL的理解很浅,并且尝试使用GraphQL时也不能完全把握其整体情况,心里总是感到困惑。

我希望大家通过这篇文章能够了解”GraphQL是什么?””它的配置结构是怎样的?”并顺利入门GraphQL。

此外,什么是GraphQL呢?我从来没听过!但是我认为这篇文章非常易懂,所以请务必阅读!

GraphQL是什么?

这是API的一种「方式」。

Facebook在2015年推出的是一种相对较新的API方法。

作为特征,有以下几点。

    1. 只有一个终结点

 

    1. 可以对交互数据进行类型检查

 

    实时通信

我希望我能够详细地谈论这些事情。

(顺便说一句)为什么API需要“方式”呢?

假设不使用”通用化的方式”,在服务器和客户端之间进行数据交换时,需要确定以下内容的方法。

    • URL / HTTPメソッド(GET, POST, PUT, DELETE)

 

    リクエストボディ

在这些模式的组合下,要进行哪种处理呢…?

然而,每次项目都要决定这些格式都会产生无谓的学习成本。

因此,我们通过将API数据交互方式进行泛化,大大降低了学习成本。

把GraphQL的整体概念掌握住

在具体查看特征之前,需要对在GraphQL中使用的文件有一个整体了解。

GraphqlArchi.png

如图所示,GraphQL由四个组成部分构成。

    1. 数据源

 

    1. 解析器

 

    1. 模式

 

    查询

为了方便说明,我将从右边所列出的内容开始写。

1. 数据来源

这是存储着希望通过API获取(或操作)的数据的地方。

例如,可以列举DB服务器/文件服务器/REST API等。

只要是程序可以操作的地方,基本上任何地方都有可能成为数据源。

解决者

这是定义处理的地方。

在这里定义的函数可以被客户端调用以获取数据源(或进行其他操作)。

在解析器中定义的函数可以分为三种类型。

項目名説明1クエリデータを取得する関数群2ミューテーションデータを「作成, 更新, 削除」する関数群3サブスクリプションあるテーブルを監視して、更新されたらそのデータをリアルタイムに取得する…関数群 (細かい説明は後述)

在解析器内,可以将这些方法分别定义为Query/Mutation/Subscription的“值”。

// リゾルバのコード例(モジュールによって書き方は若干変わるので、イメージ程度に思っていただければ...)
const resolvers = {
  // <クエリ>: データの取得
  Query: {
    books: () => {
      // DBに接続してデータを取ってくる処理を書く
      // ...このような処理を、仮にfetchFromDBと書き置いている
      const result = fetchFromDB(); 
      return result;
    }
  },
  // <ミューテーション>: データの作成, 更新, 削除
  Mutation: {
    createBook: (_, args) => {
      // argsで受け取ったデータをDBに追加する処理を書く
    },
    updateBook: (_, args) => {
      // argsで受け取ったデータでDBを更新する処理を書く
    }
  },
  // <サブスクリプション>: データの更新を監視
  Subscription: {
    subscribeBook: () => {
      // pub/subと呼ばれる通信で、Bookテーブルを監視する
    }
  },
};

3. 体系架构

因为一下子说太多会让人混乱,所以我会在后半部分解释!

即使忘记了也没有问题 ?

4. 查询

如图所示,只有在客户端处理中才会执行此操作。

查询是指定要执行解析器中定义的函数的位置。

如果您能理解到这一点,那就非常好!?接下来,让我们详细解释一下GraphQL的特点。

特点1. 只有一个终端点。

由于GraphQL单独很难传达其优点,因此我们将与REST API进行比较并继续推进。

在REST API中的终端点

我认为有许多人已经使用过REST API,所以我会先介绍一下。

在REST中,URL的设计常常使用一种被称为”资源导向”的设计方法。让我们来看一个具体的例子。

获取数据

假设我们想获取”ID=2″的组中”ID=3″的用户信息,我们可以使用REST进行以下请求:
※以下所有内容都是虚拟的URL

获取 https://example.com/rest/data/v2/groups/2/users/3/infos

数据更新

如果要更新相同的资源,请按以下方式发出请求。

发帖(或更新)https://example.com/rest/data/v2/groups/2/users/3/infos

(リクエストボディ)  
{
  height: 180,
  weight: 80
}

即使,REST API 是

    • リソースを、URLで階層を追って指定

 

    その情報に対して行う操作(作成, 更新, 削除など)を HTTPメソッド で指定

采取这种形式。

在GraphQL中的端点。

在GraphQL中,只有一个端点。

刚才和之前一样, (Xian houdou tongyong),

获取属于group id=2的用户id=3的信息。

即使进行了以上请求,也要在以下端点上进行POST请求。

发送一个 POST 请求到 https://example.com/graphql

在所有的“取得”,“追加/更新”,“删除”操作中,我们需要通过“POST”请求在这里发送。那么,具体的资源和操作应该在哪里指定?

答案很简单,只需在「请求体」中使用称为「查询」的特殊书写方式!

更准确地说,

    • リゾルバに諸々のデータ操作を関数として定義

 

    クエリでどの関数を使うのか指定

以这样的形式呈现

优势

通过在查询中指定多个解析器函数,可以在一次请求中获取”多个资源”。

举例来说,以下查询可以想象成请求主体。
通过这样一次通信,您可以同时获取“书名列表”和“用户列表”。

Query hogehogeQuery {
  books {
    title
  }
  users {
    name
    age
    height
  }
}

在这种情况下,也许会担心一次通信的数据量会增加,因为可以一并获取所有的数据。但实际上,由于可以只返回所需的数据作为返回值,所以通信量可能反而会减少。

在之前的例子中,假设 resolver 函数将 id、title、author 和 pages 等信息设置为返回值。

然而,在前一次查询的执行结果中,只有书籍的标题作为对象返回。

您可以将返回值限制在仅使用数据。

// 戻り値の例
"hogehogeQuery": {
  "data": {
    "books": [
      {
        "title": "三国志"
      },
      {
        "title": "徒然草"
      },
      {
        "title": "平家物語"
      },
    ],
    "users": [
      {
        "name" : "ほげ太郎",
        "age" : 30,
        "height" : 180,
      }
    ]
  }
}

总结至此,以下是收集到的优点。

与REST API进行比较…

    • 1回のリクエストで複数のデータを取得することが可能

 

    通信の総量は減る

→ 换句话说,它的通信成本效益很高!

特点2. 可以对交互数据进行类型检查。

在这一章中,我们将详细说明之前跳过的“模式”概念。

スクリーンショット 2021-07-05 15.37.39.png

如上图所示,架构能够在“查询和解析器之间”对类型进行检查。

具体而言,我们定义了解析器函数的「参数」和「返回值」类型如下所示。

type Query {
  books: [{
    id: ID!
    title: String
    pages: Int
    authors: [{
      firstName: String
      lastName: String
    }] 
  }]
}
type Mutation {
  // mutationメソッドの型
}
type Subscription {
  // subscriptionメソッドの型
}

这次我们不会详细讨论具体定义上的细节。

简单来说,如果执行了解决器的books查询…

    • 戻り値は書籍の配列

 

    • 書籍のtitleは文字列型

 

    書籍のpagesは整数型

可能会有各种限制执行。

另外,可以从更进一步的定义中提取出小型定义。

type Book {
  id: ID!
  title: String
  pages: Int
  authors: [Author] 
}
type Author {
  firstName: String
  lastName: String  
}
type Query {
  books: [Book]
}
type Mutation {
  // mutationメソッドの型
}
type Subscription {
  // subscriptionメソッドの型
}

看起来更容易了!(并且维护性也提高了)
通过限制这样做,可以享受到类型定义所带来的所有好处。

附带工具「GraphiQL」

通过努力阅读架构schema,

    • リゾルバにはどういった関数があるのか

 

    • リゾルバの関数は引数にどういったデータを取るのか

 

    リゾルバの関数は戻り値にどういったデータが返ってくるのか

可以理解为,也就是说,这个模式与“在客户端和服务器端之间如何交换数据”这一规范(接口规范)是等同的。

但是这样阅读起来不是很难吗…?
没关系!很多GraphQL模块都附带了一个很棒的工具叫做「GraphiQL」。

image.png

当你访问 GraphiQL 时,你可以以易于访问的方式查看模式。

在其他方面,可以方便地进行API的连接测试是一个很好的优点。
在实际使用时,请务必尝试利用!

特征3. 实时通信

最近一直在談論的是「訂閱(Subscription)」功能,其中包括解析器定義和模式定義。

这个功能使用了pub/sub的通信方式来检测和获取信息的更新。

因此,在像聊天应用程序这样需要实时性的应用开发中非常有用!

如果你对GraphQL感兴趣的话…

我认为您已经完全理解了GraphQL的整体概念。

我希望您能够参考我写的博客,因为在开始实施时,我们需要具体地动手去做。

GraphQL入门第1节:理解其机制 / とと日志
GraphQL入门第2节:使用Apollo搭建GraphQL服务器 / とと日志
GraphQL入门第3节:编写GraphQL模式的方法第1部分 / とと日志
GraphQL入门第4节:编写GraphQL模式的方法第2部分 / とと日志

希望這篇文章能讓大家對GraphQL有濃厚的興趣。

bannerAds