GraphQL - Запрос
Операция GraphQL может быть операцией чтения или записи. Запрос GraphQL используется для чтения или выборки значений, в то время как мутация используется для записи или публикации значений. В любом случае операция представляет собой простую строку, которую сервер GraphQL может анализировать и отвечать данными в определенном формате. Популярным форматом ответа, который обычно используется для мобильных и веб-приложений, является JSON.
Синтаксис для определения запроса следующий:
//syntax 1
query query_name{ someField }
//syntax 2
{ someField }
Ниже приведен пример запроса -
//query with name myQuery
query myQuery{
greeting
}
// query without any name
{
greeting
}
Из приведенного выше примера ясно, что ключевое слово запроса не является обязательным.
Запросы GraphQL помогают уменьшить избыточную выборку данных. В отличие от Restful API, GraphQL позволяет пользователю ограничивать поля, которые должны быть получены с сервера. Это означает меньшее количество запросов и меньший трафик в сети; что, в свою очередь, сокращает время отклика.
Иллюстрация 1. Запрос модели студента с настраиваемым полем
В этом примере у нас есть набор студентов, хранящихся в файле json. Каждая модель ученика имеет такие поля, как firstName, lastName и id, но не fullName. Здесь мы обсудим, как сделать запрос для получения fullName всех студентов. Для этого нам нужно создать поле fullName в обоих преобразователях схем.
Давайте посмотрим, как сделать эту иллюстрацию, используя следующие шаги -
Шаг 1 - Загрузите и установите необходимые зависимости для проекта
Создайте папку с именем query-app. Измените свой каталог наquery-appс терминала. Позже выполните шаги 3–5, описанные в главе «Настройка среды».
Шаг 2 - Создайте схему
Добавить schema.graphql файл в папке проекта query-app и добавьте следующий код -
type Query {
greeting:String
students:[Student]
studentById(id:ID!):Student
}
type Student {
id:ID!
firstName:String
lastName:String
fullName:String
}
Обратите внимание, что в поле fullName нет поляstudents.jsonфайл. Однако нам нужно получить полное имя студента с помощью запроса. В этом случае fullName будет настраиваемым полем, недоступным в источнике данных.
Шаг 3 - Создайте резолвер
Создать файл resolvers.js в папке проекта и добавьте следующий код -
const db = require('./db')
const Query = {
//resolver function for greeting
greeting:() => {
return "hello from TutorialsPoint !!!"
},
//resolver function for students returns list
students:() => db.students.list(),
//resolver function for studentbyId
studentById:(root,args,context,info) => {
//args will contain parameter passed in query
return db.students.get(args.id);
}
}
//for each single student object returned,resolver is invoked
const Student = {
fullName:(root,args,context,info) => {
return root.firstName+":"+root.lastName
}
}
module.exports = {Query,Student}
Шаг 4 - Запустите приложение
Создать server.jsфайл. См. Шаг 8 в главе «Настройка среды». Выполните в терминале команду npm start. Сервер будет работать на 9000 порте. Здесь мы используем GraphiQL в качестве клиента для тестирования приложения.
Откройте браузер и введите URL-адрес http://localhost:9000/graphiql. Введите в редакторе следующий запрос -
{
students{
id
fullName
}
}
Ответ на запрос приведен ниже -
{
"data": {
"students": [
{
"id": "S1001",
"fullName": "Mohtashim:Mohammad"
},
{
"id": "S1002",
"fullName": "Kannan:Sudhakaran"
},
{
"id": "S1003",
"fullName": "Kiran:Panigrahi"
}
]
}
}
Создать server.js и добавьте следующий код -
const bodyParser = require('body-parser');
const cors = require('cors');
const express = require('express');
const db = require('./db');
const port = 9000;
const app = express();
//loading type definitions from schema file
const fs = require('fs')
const typeDefs = fs.readFileSync('./schema.graphql',{encoding:'utf-8'})
//loading resolvers
const resolvers = require('./resolvers')
//binding schema and resolver
const {makeExecutableSchema} = require('graphql-tools')
const schema = makeExecutableSchema({typeDefs, resolvers})
//enabling cross domain calls and form post
app.use(cors(), bodyParser.json());
//enabling routes
const {graphiqlExpress,graphqlExpress} = require('apollo-server-express')
app.use('/graphql',graphqlExpress({schema}))
app.use('/graphiql',graphiqlExpress({endpointURL:'/graphql'}))
//registering port
app.listen(port, () => console.info(`Server started on port ${port}`));
Выполните в терминале команду npm start. Сервер будет работать на 9000 порте. Здесь мы используем GraphiQL в качестве клиента для тестирования приложения.
Откройте браузер и введите URL http://localhost:9000/graphiql. Введите в редакторе следующий запрос -
{
students{
id
fullName
}
}
Ответ на запрос приведен ниже -
{
"data": {
"students": [
{
"id": "S1001",
"fullName": "Mohtashim:Mohammad"
},
{
"id": "S1002",
"fullName": "Kannan:Sudhakaran"
},
{
"id": "S1003",
"fullName": "Kiran:Panigrahi"
}
]
}
}
Иллюстрация 2 - Вложенный запрос
Давайте создадим вложенный запрос для получения сведений о студентах и их колледжах. Мы будем работать с той же папкой проекта.
Шаг 1 - Отредактируйте схему
В файле схемы уже есть студенческое поле. Добавим полевой колледж и определим его тип.
type College {
id:ID!
name:String
location:String
rating:Float
}
type Student {
id:ID!
firstName:String
lastName:String
fullName:String
college:College
}
Шаг 2 - Измените resolver.js
Нам нужно добавить функцию распознавателя колледжа, как показано ниже. Функция распознавателя колледжа будет выполняться для каждого возвращенного объекта студента. В этом случае корневой параметр резолвера будет содержать student .
const Student = {
fullName:(root,args,context,info) => {
return root.firstName+":"+root.lastName
},
college:(root) => {
return db.colleges.get(root.collegeId);
}
}
module.exports = {Query,Student}
Решатель возвращает значение College каждого студента, вызывая метод get из коллекции College и передавая CollegeId . У нас есть ассоциативные отношения между студентом и колледжем через collegeId .
Шаг 3 - Протестируйте приложение
Откройте окно терминала и перейдите в папку проекта. Введите команду -npm start. Запустите браузер и введите URLhttp://localhost:9000/graphiql.
Введите следующий запрос в окне GraphiQL -
{
students{
id
firstName
college {
id
name
location
rating
}
}
}
Ответ на запрос приведен ниже -
{
"data": {
"students": [
{
"id": "S1001",
"firstName": "Mohtashim",
"college": {
"id": "col-102",
"name": "CUSAT",
"location": "Kerala",
"rating": 4.5
}
},
{
"id": "S1002",
"firstName": "Kannan",
"college": {
"id": "col-101",
"name": "AMU",
"location": "Uttar Pradesh",
"rating": 5
}
},
{
"id": "S1003",
"firstName": "Kiran",
"college": {
"id": "col-101",
"name": "AMU",
"location": "Uttar Pradesh",
"rating": 5
}
}
]
}
}
Что такое переменная запроса?
Если в запросе есть какие-то динамические значения, которые нужно передать, представьте эти динамические значения с помощью переменных. Следовательно, клиентские приложения могут повторно использовать запрос.
Иллюстрация
Давайте создадим простое приложение для понимания переменной запроса.
Шаг 1 - Редактировать файл схемы
Добавьте поле sayHello, которое принимает строковый параметр и возвращает строку. Значения имени будут динамическими в клиентском приложении.
type Query {
sayHello(name:String!):String
}
Шаг 2 - Отредактируйте файл resolver.js
Добавьте резолвер sayHello, который принимает параметр, как показано ниже -
sayHello:(root,args,context,info) => `Hi ${args.name} GraphQL server says Hello to you!!`
Шаг 3 - Объявление переменной запроса в GraphiQL
Переменная объявляется с помощью $, за которым следует имя переменной. Например: $ myname_Variable.
После объявления $ myname_Variable ее необходимо использовать с синтаксисом именованного запроса. Запрос myQuery принимает строковое значение и передает его в sayHello, как показано ниже -
query myQuery($myname_Variable:String!) {
sayHello(name:$myname_Variable)
}
Задайте значение для $ myname_Variable как объект JSON в разделе «Переменные запроса» клиента GraphiQL.
{
"myname_Variable": "Mohtashim"
}
Вывод приведенного выше кода выглядит следующим образом:
{
"data": {
"sayHello": "Hi Mohtashim GraphQL server says Hello to you!!"
}
}
Как использовать переменную запроса с Enum
Давайте посмотрим, как использовать переменную запроса, когда параметр поля enum type.
Шаг 1. Отредактируйте файл schema.graphql
enum ColorType {
RED
BLUE
GREEN
}
type Query {
setFavouriteColor(color:ColorType):String
}
Функция setFavouriteColor принимает enum в качестве входных данных и возвращает строковое значение.
Шаг 2. Отредактируйте файл resolvers.js
Функция решателя setFavouriteColor получает root и args . К значению перечисления, переданному функции во время выполнения, можно получить доступ через параметр args.
setFavouriteColor:(root,args) => {
return "Your Fav Color is :"+args.color;
}
Шаг 3 - Объявление переменной запроса в GraphiQL
Запрос называется query_to_setColorкоторый принимает переменную с именем color_variable ColorType. Эта переменная передается в метод setFavouriteColor.
query query_to_setColor($color_variable:ColorType) {
setFavouriteColor(color:$color_variable)
}
В разделе переменных запроса GraphiQL введите следующий код -
{
"color_variable":"RED"
}
Ответ показан ниже -
{
"data": {
"setFavouriteColor": "Your Fav Color is: RED"
}
}