Crearea API-urilor GraphQL cu Node
Publicat: 2022-12-20GraphQL este noul cuvânt la modă în dezvoltarea API. În timp ce API-urile RESTful rămân cel mai popular mod de a expune datele din aplicații, ele vin cu multe limitări pe care GraphQL își propune să le rezolve.
GraphQL este un limbaj de interogare creat de Facebook, care a fost transformat într-un proiect open-source în 2015. Oferă o sintaxă intuitivă și flexibilă pentru descrierea și accesarea datelor într-un API.
Acest ghid va explora cum să construiți un proiect GraphQL Node.js. Vom folosi GraphQL pentru a construi o aplicație Todo în cadrul web Express.js pentru Node.
Ce este GraphQL?
Din documentația oficială: „GraphQL este un limbaj de interogare pentru API-uri și un timp de execuție pentru a îndeplini acele interogări cu datele existente. GraphQL oferă o descriere completă și ușor de înțeles a datelor din API-ul dvs., oferă clienților puterea de a cere exact ceea ce au nevoie și nimic mai mult, face mai ușoară evoluția API-urilor în timp și permite instrumente puternice pentru dezvoltatori.”
GraphQL este un timp de execuție pe partea de server pentru executarea de interogări folosind sistemul de tip pe care l-ați definit pentru datele dvs. De asemenea, GraphQL nu este legat de nicio bază de date sau motor de stocare specific. În schimb, este susținut de codul și depozitul de date existent. Puteți obține o comparație detaliată a acestor tehnologii cu ghidul GraphQL vs. RESTful API.
Pentru a crea un serviciu GraphQL, începeți prin a defini tipurile de schemă și a crea câmpuri folosind acele tipuri. Apoi, furnizați un rezolutor de funcție care să fie executat pe fiecare câmp și tastați ori de câte ori datele sunt solicitate de partea clientului.
Terminologie GraphQL
Sistemul de tip GraphQL este folosit pentru a descrie ce date pot fi interogate și ce date puteți manipula. Este nucleul GraphQL. Să discutăm diferite moduri în care putem descrie și manipula datele în GraphQ.
Tipuri
Tipurile de obiecte GraphQL sunt modele de date care conțin câmpuri puternic tipizate. Ar trebui să existe o mapare 1-la-1 între modelele dvs. și tipurile GraphQL. Mai jos este un exemplu de tip GraphQL:
type User { id: ID! # The "!" means required firstname: String lastname: String email: String username: String todos: [Todo] # Todo is another GraphQL type }
Întrebări
Interogarea GraphQL definește toate interogările pe care un client le poate rula pe API-ul GraphQL. Ar trebui să definiți un RootQuery care va conține toate interogările existente prin convenție.
Mai jos definim și mapăm interogările la API-ul RESTful corespunzător:
type RootQuery { user(id: ID): User # Corresponds to GET /api/users/:id users: [User] # Corresponds to GET /api/users todo(id: ID!): Todo # Corresponds to GET /api/todos/:id todos: [Todo] # Corresponds to GET /api/todos }
Mutații
Dacă interogările GraphQL sunt solicitări GET , mutațiile sunt solicitări POST , PUT , PATCH și DELETE care manipulează API-ul GraphQL.
Vom pune toate mutațiile într-o singură RootMutation pentru a demonstra:
type RootMutation { createUser(input: UserInput!): User # Corresponds to POST /api/users updateUser(id: ID!, input: UserInput!): User # Corresponds to PATCH /api/users removeUser(id: ID!): User # Corresponds to DELETE /api/users createTodo(input: TodoInput!): Todo updateTodo(id: ID!, input: TodoInput!): Todo removeTodo(id: ID!): Todo }
Ați observat utilizarea tipurilor -input pentru mutații precum UserInput , TodoInput . Este întotdeauna cea mai bună practică să definiți întotdeauna tipurile de intrare pentru crearea și actualizarea resurselor.
Puteți defini tipurile de intrare ca cel de mai jos:
input UserInput { firstname: String! lastname: String email: String! username: String! }
Rezolvatori
Rezolvatorii îi spun GraphQL ce să facă atunci când fiecare interogare sau mutație este solicitată. Este o funcție de bază care face munca grea de a lovi stratul bazei de date pentru a efectua operațiunile CRUD (creare, citire, actualizare, ștergere), lovirea unui punct final API RESTful intern sau apelarea unui microserviciu pentru a îndeplini cererea clientului.
Puteți crea un nou fișier resolvers.js și puteți adăuga următorul cod:
import sequelize from '../models'; export default function resolvers () { const models = sequelize.models; return { // Resolvers for Queries RootQuery: { user (root, { id }, context) { return models.User.findById(id, context); }, users (root, args, context) { return models.User.findAll({}, context); } }, User: { todos (user) { return user.getTodos(); } }, } // Resolvers for Mutations RootMutation: { createUser (root, { input }, context) { return models.User.create(input, context); }, updateUser (root, { id, input }, context) { return models.User.update(input, { ...context, where: { id } }); }, removeUser (root, { id }, context) { return models.User.destroy(input, { ...context, where: { id } }); }, // ... Resolvers for Todos go here } }; }
Schemă
Schema GraphQL este ceea ce GraphQL expune lumii. Prin urmare, tipurile, interogările și mutațiile vor fi incluse în schema pentru a fi expuse lumii.
Mai jos este cum să expuneți lumii tipuri, interogări și mutații:
schema { query: RootQuery mutation: RootMutation }
În scriptul de mai sus, am inclus RootQuery și RootMutation pe care le-am creat mai devreme pentru a fi expuse lumii.
Cum funcționează GraphQL cu Nodejs și Expressjs
GraphQL oferă o implementare pentru toate limbajele de programare majore, iar Node.js nu este scutit. Pe site-ul web oficial GraphQL, există o secțiune pentru suport JavaScript și, de asemenea, există și alte implementări ale GraphQL pentru a simplifica scrierea și codarea în GraphQL.
GraphQL Apollo oferă o implementare pentru Node.js și Express.js și facilitează începerea utilizării GraphQL.
Veți învăța cum să creați și să dezvoltați prima aplicație GraphQL în cadrul backend Nodes.js și Express.js folosind GraphQL Apollo în secțiunea următoare.
Configurarea GraphQL cu Express.js
Construirea unui server API GraphQL cu Express.js este simplă de început. În această secțiune, vom explora cum să construim un server GraphQL.
Inițializați proiectul cu Express
Mai întâi, trebuie să instalați și să configurați un nou proiect Express.js.
Creați un folder pentru proiectul dvs. și instalați Express.js folosind această comandă:
cd <project-name> && npm init -y npm install express
Comanda de mai sus creează un nou fișier package.json și instalează biblioteca Express.js în proiectul dvs.
În continuare, ne vom structura proiectul așa cum se arată în imaginea de mai jos. Acesta va conține diferite module pentru caracteristicile proiectului, cum ar fi utilizatori, todos etc.
Inițializați GraphQL
Să începem prin a instala dependențele GraphQL Express.js. Rulați următoarea comandă pentru a instala:
npm install apollo-server-express graphql @graphql-tools/schema --save
Crearea de scheme și tipuri
În continuare, vom crea un fișier index.js în folderul modules și vom adăuga următorul fragment de cod:
const { gql } = require('apollo-server-express'); const users = require('./users'); const todos = require('./todos'); const { GraphQLScalarType } = require('graphql'); const { makeExecutableSchema } = require('@graphql-tools/schema'); const typeDefs = gql` scalar Time type Query { getVersion: String! } type Mutation { version: String! } `; const timeScalar = new GraphQLScalarType({ name: 'Time', description: 'Time custom scalar type', serialize: (value) => value, }); const resolvers = { Time: timeScalar, Query: { getVersion: () => `v1`, }, }; const schema = makeExecutableSchema({ typeDefs: [typeDefs, users.typeDefs, todos.typeDefs], resolvers: [resolvers, users.resolvers, todos.resolvers], }); module.exports = schema;
Tutorial cod
Să analizăm fragmentul de cod și să-l descompunem:
Pasul 1
Mai întâi, am importat bibliotecile necesare și am creat tipuri de interogări și mutații implicite. Interogarea și mutația setează doar versiunea API-ului GraphQL pentru moment. Cu toate acestea, vom extinde interogarea și mutația pentru a include alte scheme pe măsură ce continuăm.
Pasul 2:
Apoi am creat un nou tip scalar pentru timp și primul nostru rezolutor pentru interogarea și mutația create mai sus. În plus, am generat și o schemă folosind funcția makeExecutableEchema .
Schema generată include toate celelalte scheme pe care le-am importat și va include și mai multe atunci când le creăm și le importăm.
Fragmentul de cod de mai sus arată că am importat diferite scheme în funcția makeExecutableEchema. Această abordare ne ajută în structurarea aplicației pentru complexitate. În continuare, vom crea schemele Todo și User pe care le-am importat.
Crearea Schemei Todo
Schema Todo arată operațiuni CRUD simple pe care le pot efectua utilizatorii aplicației. Mai jos este schema care implementează operațiunea Todo CRUD.
const { gql } = require('apollo-server-express'); const createTodo = require('./mutations/create-todo'); const updateTodo = require('./mutations/update-todo'); const removeTodo = require('./mutations/delete-todo'); const todo = require('./queries/todo'); const todos = require('./queries/todos'); const typeDefs = gql` type Todo { id: ID! title: String description: String user: User } input CreateTodoInput { title: String! description: String isCompleted: Boolean } input UpdateTodoInput { title: String description: String isCompleted: Boolean } extend type Query { todo(id: ID): Todo! todos: [Todo!] } extend type Mutation { createTodo(input: CreateTodoInput!): Todo updateTodo(id: ID!, input: UpdateTodoInput!): Todo removeTodo(id: ID!): Todo } `; // Provide resolver functions for your schema fields const resolvers = { // Resolvers for Queries Query: { todo, todos, }, // Resolvers for Mutations Mutation: { createTodo, updateTodo, removeTodo, }, }; module.exports = { typeDefs, resolvers };
Tutorial cod
Să analizăm fragmentul de cod și să-l descompunem:
Pasul 1:
Mai întâi, am creat o schemă pentru Todo folosind GraphQL type , input și extend . Cuvântul cheie extinde este folosit pentru a moșteni și adăuga noi interogări și mutații la interogarea rădăcină și mutația existentă pe care am creat-o mai sus.
Pasul 2:
Apoi, am creat un resolver, care este folosit pentru a prelua datele corecte atunci când este apelată o anumită interogare sau mutație.
Cu funcția de rezolvare activată, putem crea metode individuale pentru logica de afaceri și manipularea bazei de date, așa cum se arată în exemplul create-todo.js .
Creați un fișier create-user.js în folderul <code>./mutations</code> și adăugați logica de afaceri pentru a crea un nou Todo în baza de date.
const models = require('../../../models'); module.exports = async (root, { input }, context) => { return models.todos.push({ ...input }); };
Fragmentul de cod de mai sus este o modalitate simplificată de a crea un nou Todo în baza noastră de date folosind Sequelize ORM. Puteți afla mai multe despre Sequelize și despre cum să o configurați cu Node.js.
Puteți urma același pas pentru a crea multe scheme în funcție de aplicația dvs. sau puteți clona proiectul complet din GitHub.
În continuare, vom configura serverul cu Express.js și vom rula aplicația Todo nou creată cu GraphQL și Node.js
Configurarea și rularea serverului
În cele din urmă, ne vom configura serverul folosind biblioteca apollo-server-express pe care o instalăm mai devreme și o vom configura.
Apollo -server-express este un simplu wrapper al Apollo Server pentru Express.js. Este recomandat deoarece a fost dezvoltat pentru a se potrivi în dezvoltarea Express.js.
Folosind exemplele pe care le-am discutat mai sus, să configuram serverul Express.js să funcționeze cu apollo-server-express nou instalat.
Creați un fișier server.js în directorul rădăcină și inserați următorul cod:
const express = require('express'); const { ApolloServer } = require('apollo-server-express'); const schema = require('./modules'); const app = express(); async function startServer() { const server = new ApolloServer({ schema }); await server.start(); server.applyMiddleware({ app }); } startServer(); app.listen({ port: 3000 }, () => console.log(`Server ready at http://localhost:3000`) );
În codul de mai sus, ați creat cu succes primul server CRUD GraphQL pentru Todos și utilizatori. Puteți porni serverul de dezvoltare și puteți accesa terenul de joacă folosind http://localhost:3000/graphql. Dacă totul are succes, ar trebui să vi se prezinte ecranul de mai jos:
rezumat
GraphQL este o tehnologie modernă susținută de Facebook care simplifică munca obositoare implicată în crearea de API-uri la scară largă cu modele arhitecturale REST.
Acest ghid a elucidat GraphQL și a demonstrat cum să dezvolți primul tău API GraphQL cu Express.js.
Spuneți-ne ce construiți folosind GraphQL.