GraphQL LogoGraphQL

物件類型

在許多情況下,您不想要從 API 傳回數字或字串。您想要傳回一個具有其自身複雜行為的物件。GraphQL 非常適合這種情況。

在 GraphQL 結構語言中,定義新物件類型的步驟與我們在範例中定義 Query 類型的步驟相同。每個物件都可以有傳回特定類型的欄位,以及接收參數的方法。例如,在 傳遞參數 文件中,我們有一個方法可以擲出一些隨機骰子

type Query {
rollDice(numDice: Int!, numSides: Int): [Int]
}

如果我們想要隨著時間推移,根據隨機骰子建立越來越多的方法,我們可以使用 RandomDie 物件類型來實作它。

type RandomDie {
roll(numRolls: Int!): [Int]
}
type Query {
getDie(numSides: Int): RandomDie
}

對於 RandomDie 類型,我們可以使用 ES6 類別,而不是根層解析器,其中解析器是實例方法。此程式碼顯示如何實作上述 RandomDie 結構

class RandomDie {
constructor(numSides) {
this.numSides = numSides
}
rollOnce() {
return 1 + Math.floor(Math.random() * this.numSides)
}
roll({ numRolls }) {
var output = []
for (var i = 0; i < numRolls; i++) {
output.push(this.rollOnce())
}
return output
}
}
var root = {
getDie: ({ numSides }) => {
return new RandomDie(numSides || 6)
},
}

對於不使用任何參數的欄位,您可以使用物件或實例方法上的屬性。因此,對於上述範例程式碼,numSidesrollOnce 實際上都可以用來實作 GraphQL 欄位,因此該程式碼也實作了

type RandomDie {
numSides: Int!
rollOnce: Int!
roll(numRolls: Int!): [Int]
}
type Query {
getDie(numSides: Int): RandomDie
}

將所有這些放在一起,以下是執行具有此 GraphQL API 的伺服器的範例程式碼

var express = require("express")
var { createHandler } = require("graphql-http/lib/use/express")
var { buildSchema } = require("graphql")
// Construct a schema, using GraphQL schema language
var schema = buildSchema(`
type RandomDie {
numSides: Int!
rollOnce: Int!
roll(numRolls: Int!): [Int]
}
type Query {
getDie(numSides: Int): RandomDie
}
`)
// This class implements the RandomDie GraphQL type
class RandomDie {
constructor(numSides) {
this.numSides = numSides
}
rollOnce() {
return 1 + Math.floor(Math.random() * this.numSides)
}
roll({ numRolls }) {
var output = []
for (var i = 0; i < numRolls; i++) {
output.push(this.rollOnce())
}
return output
}
}
// The root provides the top-level API endpoints
var root = {
getDie: ({ numSides }) => {
return new RandomDie(numSides || 6)
},
}
var app = express()
app.all(
"/graphql",
createHandler({
schema: schema,
rootValue: root,
})
)
app.listen(4000)
console.log("Running a GraphQL API server at localhost:4000/graphql")

當你對傳回物件類型的 API 發出 GraphQL 查詢時,你可以透過巢狀 GraphQL 欄位名稱一次呼叫物件上的多個方法。例如,如果你想要呼叫 rollOnce 來擲骰子一次,以及 roll 來擲骰子三次,你可以使用這個查詢來執行

{
getDie(numSides: 6) {
rollOnce
roll(numRolls: 3)
}
}

如果你使用 node server.js 執行此程式碼並瀏覽至 http://localhost:4000/graphql,你可以使用 GraphiQL 試用這些 API。

這種定義物件類型的做法通常比傳統的 REST API 具有優勢。你不需要先執行一個 API 要求來取得物件的基本資訊,然後再執行多個後續的 API 要求來找出關於該物件的更多資訊,你可以一次在一個 API 要求中取得所有資訊。這可以節省頻寬、讓你的應用程式執行得更快,並簡化你的用戶端邏輯。

到目前為止,我們看過的每個 API 都是設計用來傳回資料。為了修改儲存的資料或處理複雜的輸入,建議你瞭解變異和輸入類型

繼續閱讀 →變異和輸入類型