0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

I tried creating a Fullstack Web Application with TypeScript & GraphQL【 TodoList 】

Last updated at Posted at 2023-12-15

Technologies used

Backend:

  • Typescript
  • Node.js
  • Express
  • Apollo Server v4
  • sqlite
  • Prisma

Frontend:

  • Typescript
  • React
  • Apollo Client
  • Tailwindcss
  • vite

1 - Project setup

① Create a project

mkdir <Project Name>
cd <Project Name>
npm init -y

② Use the workspace function
※ A function that manages multiple functions.

mkdir packages

③ Add code to package.json

package.json
//省略
"license": "ISC",
  "workspaces": [
    "packages/*"
   ],

④ Create frontend and backend folders in packages folder

⑤ Open three terminals and rename them root, frontend, and backend.

⑥ Go to backend terminal

cd packages/backend/
npm init -y

⑦ Go to frontend terminal

cd packages/frontend/
npm create vite@latest . -- --template react-ts

⑧ Go to root terminal

npm i

⑨ Allow root to control forontend and backend

root/package.json
//省略
"scripts": {
    "dev:front": "npm run dev -w frontend"
  },
npm run dev:front

⑩ Prepare typescript in backend

Create src folder and index.ts

npm i -DE typescript @types/node nodemon
touch backend
backend/tsconfig.json
{
  "compilerOptions": {
    "target": "ES2022",
    "module": "NodeNext",
    "outDir": "./dist",
    "esModuleInterop": true,
    "forceConsistentCasingInFileNames": true,
    "allowSyntheticDefaultImports": true,
    "strict": true,
    "skipLibCheck": true,
    "moduleResolution": "NodeNext"
  }
}
backend/package.json
//省略
"main": "index.js",
  "type": "module",
  "scripts": {
    "dev": "nodemon dist/index.js",
    "watch":"tsc --watch",
    "build":"tsc",
    "start": "node dist/index.js",
    "lint":"eslint --fix \"./src/**/*.{js,jsx,ts,tsx,json}\""
npm run lint

⑪ Allow root to control forontend and backend

root/package.json
//省略
"scripts": {
    "build": "npm run build:back && npm run build:front",
    "build:back": "npm run build -w backend",
    "build:front": "npm run build -w frontend",
    "dev:back": "npm run dev -w backend",
    "watch:back": "npm run watch -w backend",
    "dev:front": "npm run dev -w frontend"
  },
npm run build

⑫ Add eslint to backend

npm i -ED eslint
npx eslint --init

※ shift + option + f (Run Prettier)

backend/src/.eslintrc.cjs
//省略
extends: [
    'eslint:recommended',
    'plugin:@typescript-eslint/recommended',
    'plugin:@typescript-eslint/recommended-requiring-type-checking',
  ],
//省略
 parserOptions: {
        sourceType: 'script',
        tsconfigRootDir: __dirname,//Add code
        project: ['tsconfig.eslint.json'],//Add code
      },

⑬ Add tsconfig.eslint.json to backend/src

backend/src/tsconfig.eslint.json
{
  "extends": "./tsconfig.json",
  "include": ["src/**/*.ts", ".eslintrc.cjs"],
  "exclude": ["node_modules"]
}

※ shift + command + p (open command palette:Developer:Reload Window)

⑭ Add eslint to frontend

npm i -ED eslint
npx eslint --init
npm i -ED eslint-plugin-react-hooks
frontend/eslintrc.cjs
extends: [
    'eslint:recommended',
    'plugin:react/recommended',
    'plugin:react-hooks/recommended',//Add code
    'plugin:@typescript-eslint/recommended',
  ],

  //省略
 parserOptions: {
        sourceType: 'script',
        tsconfigRootDir: __dirname,//Add code
        project: ['tsconfig.eslint.json'],//Add code
      },

⑮ Add tsconfig.eslint.json to frontend/src

frontend/src/tsconfig.eslint.json
{
  "extends": "./tsconfig.json",
  "include": ["src/**/*.ts", ".eslintrc.cjs"],
  "exclude": ["node_modules"]
}

2 - Launching a minimal Apollo server

① Enter the backend terminal and install the necessary libraries

npm i express graphql @apollo/server
npm i -ED @types/express

② Start up apollo server

backend / src / index.ts
import http from 'http';

import { ApolloServer } from '@apollo/server';
import { ApolloServerPluginDrainHttpServer } from '@apollo/server/plugin/drainHttpServer';
import { expressMiddleware } from '@apollo/server/express4';
import express from 'express';
import { mergeResolvers, mergeTypeDefs } from '@graphql-tools/merge';

const typeDefs = `#graphql
    type Query {
    health: Boolean
}
`;

const resolvers = {
  Query: {
    health: async (_: any, args: any, context: MyContext, info: any) => {
      return true;
    },
  },
};

type MyContext = {
  req: express.Request;
  res: express.Response;
};

async function main() {
  const PORT = process.env.PORT || 5555;
  const app = express();

  const httpSever = http.createServer(app);
  const server = new ApolloServer<MyContext>({
    typeDefs: mergeTypeDefs([typeDefs]),
    resolvers: mergeResolvers([resolvers]),
    plugins: [ApolloServerPluginDrainHttpServer({ httpServer: httpSever })],
  });
  await server.start();
  app.use(express.json());
  app.use(
    '/graphql',
    expressMiddleware(server, {
      context: async ({ req, res }) => ({ req, res }),
    })
  );
  await new Promise<void>((resolve) => {
    httpSever.listen({ port: PORT }, resolve);
  });
  console.log(`server is up and running at http://localhost:{PORT}`);
}

main().catch((error) => {
  console.error(error);
  process.exit(1);
});

3 - Adding a Graphql code generator

① Create modules/root/greet/greet.typeDefs.ts for refactoring

modules/root/greet/greetTypeDefs.ts
const typeDefs = `#graphql
    type Query {
    greet: String
}
`;
export default typeDefs;

② Create modules/root/greet/greet.resolversts.ts for refactoring

modules/root/greet/greet.resolversts.ts
import { MyContext } from '../../../types/graphql.js';

const resolvers = {
  Query: {
    health: async (_: any, args: any, context: MyContext, info: any) => {
      return true;
    },
  },
};

export default resolvers;

③ Create/types/graphql.ts

types/graphql.ts
import express from 'express';

export type MyContext = {
  req: express.Request;
  res: express.Response;
};

④ Refactor backend/src/index.ts

backend / src / index.ts
import http from 'http';

import { ApolloServer } from '@apollo/server';
import { ApolloServerPluginDrainHttpServer } from '@apollo/server/plugin/drainHttpServer';
import { expressMiddleware } from '@apollo/server/express4';
import express from 'express';
import { mergeResolvers, mergeTypeDefs } from '@graphql-tools/merge';
import { MyContext } from './types/graphql.js';
import greetTypeDefs from './modules/root/greet/greet.typeDefs.js';
import greetResolvers from './modules/root/greet/greet.resolversts.js';
import makeTodoTypeDefs from './modules/todos/make-todo/make-todo.typeDefs.js';
import makeTodoResolvers from './modules/todos/make-todo/make-todo.resolvers.js';
import TodoTypeDefs from './modules/root/models/todo.typeDefs.js';

async function main() {
  const PORT = process.env.PORT || 5555;
  const app = express();

  const httpSever = http.createServer(app);
  const server = new ApolloServer<MyContext>({
    typeDefs: mergeTypeDefs([greetTypeDefs, makeTodoTypeDefs, TodoTypeDefs]),
    resolvers: mergeResolvers([greetResolvers, makeTodoResolvers]),
    plugins: [ApolloServerPluginDrainHttpServer({ httpServer: httpSever })],
  });
  await server.start();
  app.use(express.json());
  app.use(
    '/graphql',
    expressMiddleware(server, {
      context: async ({ req, res }) => ({ req, res }),
    })
  );
  await new Promise<void>((resolve) => {
    httpSever.listen({ port: PORT }, resolve);
  });
  console.log(`server is up and running at http://localhost:{PORT}`);
}

main().catch((error) => {
  console.error(error);
  process.exit(1);
});

⑤ Create todos folder get-todo, get-todos, make-todo,
remove-todo, update-todo folder in modules folder

⑥ Create make-todo.typeDefs.ts and make-todo.resolvers.ts in make-todo

make-todo/make-todo.typeDefs.ts
const typeDefs = `#graphql

    input MakeTodoInput {
        title: String!
}

type MakeTodoRespose {
   todo:Todo!
}

type Mutation {
   makeTodo(MakeTodoInput:MakeTodoInput!):MakeTodoRespose!
}
`;
export default typeDefs;
make-todo/make-todo.resolvers.ts
import { title } from 'process';
import { Resolvers } from '../../../_generated_/graphql.js';
import { MyContext } from '../../../types/graphql.js';
import crypto from 'crypto';

const resolvers: Resolvers<MyContext> = {
  Mutation: {
    makeTodo: async (
      _: any,
      args: { makeTodoInput },
      context: MyContext,
      info: any
    ) => {
      const todoItem = {
        id: crypto.randomUUID(),
        title: makeTodoInput.title,
        updatedAt: new Date().toISOString(),
        createdAt: new Date().toISOString(),
      };

      return 'todo has been created !';
    },
  },
};

export default resolvers;

⑦ Automate type specification

npm i -ED @graphql-codegen/cli
npx graphql-code-generator init
make-todo/make-todo.resolvers.ts
import { Resolvers } from '../../../_generated_/graphql.js';
import { MyContext } from '../../../types/graphql.js';
import crypto from 'crypto';

const resolvers: Resolvers<MyContext> = {
  Mutation: {
    makeTodo: async (
      _: any,
      args: { makeTodoInput },
      context: MyContext,
      info: any
    ) => {
      const todoItem = {
        id: crypto.randomUUID(),
        title: makeTodoInput.title,
        updatedAt: new Date().toISOString(),
        createdAt: new Date().toISOString(),
      };

      return 'todo has been created !';
    },
  },
};

export default resolvers;

⑧ Create a files generated by codegen.yml

backend/src/codegen.yml
overwrite: true
schema: 'http://localhost:5555/graphql'
generates:
  src/_generated_/graphql.ts:
    plugins:
      - 'typescript'
      - 'typescript-resolvers'

⑨ Remove ^ in package.json and run npm i

npm i

⑩ backend/src/generated/graphql.ts

⑪ type Todo {
id: String!
title: String!
updatedAt: String!
createdAt: String!
} will be used elsewhere, so create a file to share.

create root/models/todo.typeDefs.ts

root/models/todo.typeDefs.ts
const typeDefs = `#graphql
type Todo {
    id: String!
    title: String!
    updatedAt: String!
    createdAt: String!
    }
`;

export default typeDefs;

4 - Automatic import of TypeDefs and Resolvers

① Install the library

//backend
npm i -E glob
npm i -ED @types/glob copyfiles

② Create buildSchema.ts in the utils folder

utils/buildSchema.ts

③ Create make-todo.graphql in make-todo folder

make-todo/make-todo.graphql

④ Create greet.graphql in greet folder

greet/greet.graphql

⑤ Delete make-todo.typeDefs.ts in make-todo folder

⑥ Delete greet.typeDefs.ts in greet folder

⑦ Create todo.graphql in modeles folder

modeles/todo.graphql

⑧ Delete todo.typeDefs.ts in greet folder

⑨ Refactor backend/src/index.ts

backend / src / index.ts

⑩ Add code to backend/src/package.json

backend/src/package.json
//省略
"scripts": {
    //省略
    "gen": "graphql-codegen --config codegen.yml",
    "cpgql": "copyfiles -u 1 src/**/*.graphql ./dist "
  },

5 - Prisma preparation & TodoCRUD implementation

公式サイト:prisma

① Install prisma in your backend project

npm i -E prisma@prisma/client
npx prisma init

② Edit .env in backend

backend/.env

DATABASE_URL="file:./dev.db"

③ Add code to prisma/schema.prisma

prisma/schema.prisma
generator client {
  provider = "prisma-client-js"
}

datasource db {
  provider = "sqlite"
  url      = env("DATABASE_URL")
}

model Todo{
  id String @id @default(uuid())
  title String
  isCompleted Boolean @default(false)
  createdAt DateTime @default(now())
  updatedAt DateTime @updatedAt
}

④ Create migration file in backend

npx prisma migrate dev --name init
npx prisma studio //server starts up

④ Edit backend/src/index.ts to use Prisma

backend / src / index.ts
import http from 'http';

import { ApolloServer } from '@apollo/server';
import { ApolloServerPluginDrainHttpServer } from '@apollo/server/plugin/drainHttpServer';
import { expressMiddleware } from '@apollo/server/express4';
import express from 'express';
import { PrismaClient } from '@prisma/client';
import { MyContext } from './types/graphql.js';
import { buildSchema } from './utils/buildSchema.js';

const prismaClient = new PrismaClient();

async function main() {
  await prismaClient.$connect();

  const PORT = process.env.PORT || 5555;
  const app = express();

  const httpSever = http.createServer(app);
  const server = new ApolloServer<MyContext>({
    schema: await buildSchema(),
    plugins: [ApolloServerPluginDrainHttpServer({ httpServer: httpSever })],
  });
  await server.start();
  app.use(express.json());
  app.use(
    '/graphql',
    expressMiddleware(server, {
      context: async ({ req, res }) => ({ req, res }),
    })
  );
  await new Promise<void>((resolve) => {
    httpSever.listen({ port: PORT }, resolve);
  });
  console.log(`server is up and running at http://localhost:{PORT}`);
}

main().catch(async (error) => {
  console.error(error);
  await prismaClient.$disconnect();
  process.exit(1);
});

⑤ Create/types/graphql.ts

types/graphql.ts

⑥ Edit make-todo/make-todo.resolvers.ts

make-todo/make-todo.resolvers.ts
import crypto from 'crypto';
import { Resolvers } from '../../../_generated_/graphql.js';
import { MyContext } from '../../../types/graphql.js';

export const resolvers: Resolvers<MyContext> = {
  Mutation: {
    makeTodo: async (_, { makeTodoInput }, { prismaClient }, info) => {
      const newTodo = await prismaClient.todo.create({
        date: {
          title: makeTodoInput.title,
        },
      });
      return {
        todo: {
          ...newTodo,
          updatedAt: newTodo.updatedAt.toISOString(),
          createdAt: newTodo.createdAt.toISOString(),
        },
      };
    },
  },
};

⑦ Add code to backend/src/package.json

backend/src/package.json
//省略
"scripts": {
    //省略
    "gen": "graphql-codegen --config codegen.yml",
    "gen:db": "prisma migrate dev --name",
    "gui:db": "prisma studio",
    "cpgql": "copyfiles -u 1 src/**/*.graphql ./dist "
  },

⑧ Create migration file in backend

npm run gen:db -- fix-type-todo-table
npm run gui:db

⑨ Create get-todos.graphql, get-todos.resolvers.ts in get-todos folder

get-todos/get-todos.graphql
type GetTodosResponse {
  getTodos: [Todo]
}

type Query {
  getTodos: GetTodosResponse
}
npm run cpgql
npm run gen:gql

⑩ Create remove-todo.graphql,remove-todo.resolvers.ts in remove-todo folder

remove-todo/remove-todo.graphql
input UpdateTodoInput {
  todoId: String!
  title: String
  isCompleted: Boolean
}

type UpdateTodoResponse {
  todo: Todo!
}

type Mutation {
  updateTodo(updateTodoInput: UpdateTodoInput!): UpdateTodoResponse!
}

npm run cpgql
npm run gen:gql
remove-todo/remove-todo.resolvers.ts
import { GraphQLError } from 'graphql';
import { Resolvers } from '../../../_generated_/graphql.js';
import { MyContext } from '../../../types/graphql.js';

export const resolvers: Resolvers<MyContext> = {
  Mutation: {
    removeTodo: async (_, { removeTodoInput }, { prismaClient }, info) => {
      const existingTodo = await prismaClient.todo.findUnique({
        where: {
          id: removeTodoInput.todoId,
        },
      });
      if (!existingTodo) {
        throw new GraphQLError('Not found');
      }
      await prismaClient.todo.delete({
        where: {
          id: existingTodo.id,
        },
      });
      return {
        todo: {
          ...existingTodo,
          updatedAt: existingTodo.updatedAt.toISOString(),
          createdAt: existingTodo.createdAt.toISOString(),
        },
      };
    },
  },
};

⑩ Create update-todo.graphql,update-todo.resolvers.ts in update-todo folder

update-todo/update-todo.graphql
input UpdateTodoInput {
  todoId: String!
  title: String
  isCompleted: Boolean
}

type UpdateTodoResponse {
  todo: Todo!
}

type Mutation {
  updateTodo(updateTodoInput: UpdateTodoInput!): UpdateTodoResponse!
}
update-todo/update-todo.resolvers.ts
import { GraphQLError } from 'graphql';
import { Resolvers } from '../../../_generated_/graphql.js';
import { MyContext } from '../../../types/graphql.js';
import { title } from 'process';

export const resolvers: Resolvers<MyContext> = {
  Mutation: {
    updateTodo: async (_, { updateTodoInput }, { prismaClient }, info) => {
      const existingTodo = await prismaClient.todo.findUnique({
        where: {
          id: updateTodoInput.todoId,
        },
      });
      if (!existingTodo) {
        throw new GraphQLError('Not found');
      }

      if (typeof updateTodoInput.title === 'string') {
        existingTodo.title = updateTodoInput.title;
      }

      if (typeof updateTodoInput.isCompleted === 'boolean') {
        existingTodo.isCompleted = updateTodoInput.isCompleted;
      }

      await prismaClient.todo.update({
        where: {
          id: existingTodo.id,
        },
        date: {
          title: existingTodo.title,
          isCompleted: existingTodo.isCompleted,
        },
      });

      return {
        todo: {
          ...existingTodo,
          updatedAt: existingTodo.updatedAt.toISOString(),
          createdAt: existingTodo.createdAt.toISOString(),
        },
      };
    },
  },
};


⑪ Create get-todo.graphql,get-todo.resolvers.ts in get-todo folder

get-todo/get-todo.graphql
input GetTodoInput {
  todoId: String!
}

type GetTodoRespose {
  todo: Todo!
}

type Query {
  getTodo(GetTodo: GetTodoInput!): GetTodoRespose!
}
get-todo/get-todo.resolvers.ts
import { Resolvers } from '../../../_generated_/graphql.js';
import { MyContext } from '../../../types/graphql.js';

export const resolvers: Resolvers<MyContext> = {
  Query: {
    getTodo: async (_, { getTodoInput }, { prismaClient }, info) => {
      const existingTodo = await prismaClient.todo.findUnique({
        where: {
          id: getTodoInput.todoId,
        },
      });
      if (!existingTodo) {
        throw new GraphQLError('Not found');
      }
      return {
        todos: {
          ...existingTodo,
          updatedAt: existingTodo.updatedAt.toISOString(),
          createdAt: existingTodo.createdAt.toISOString(),
        },
      };
    },
  },
};

6 - Adding DateTime Scalar

① Create scalars/datetime folder and datetime.graphql, datetime.resolvers.ts in root folder

root/scalars/datetime/datetime.graphql


② Adding DateTime Scalar

codegen.yml
overwrite: true
schema: 'http://localhost:5555/graphql'
generates:
  src/__generated__/graphql.ts:
  config:
  scalars:
  DateTime: 'Date'
plugins:
  - 'typescript'
  - 'typescript-resolvers'
npm i -E graphql-scalars

7- Implementation of Tailwind CSS and Apollo Client

① Install Tailwind CSS on the frontend

npm i -DE tailwindcss postcss autoprefixer
npx tailwindcss init -p

② Edit tailwind.config.js

tailwind.config.js
/** @type {import('tailwindcss').Config} */
module.exports = {
  content: ['index.html', 'src/**/:/{js,ts,jsx,tsx}'],
  theme: {
    extend: {},
  },
  plugins: [],
};

③ Edit frontend/src/index.css

frontend/src/index.css
@tailwind base;
@tailwind components;
@tailwind utilities;

④ Edit frontend/src/App.tsx

frontend/src/App.tsx

⑤ Share resources across origins in backend

npm i -E cors
npm i -ED @types/cors

⑥ Edit backend/src/index.ts

backend/src/index.ts
//omission
import cors from 'cors';
//omission

app.use(
    cors({
      origin: 'http://localhost:5173',
    })
  );

⑦ Install to frontend

npm i --save-dev @types/react
npm i react-dom
npm i vite
npm i @types/vite 
npm i @vitejs/plugin-react
npm i -E graphql @apollo/client
npm i -DE @graphql-codegen/cli

⑧ Set up apollo/client

frontend/src/main.tsx
declare module 'react-dom/client';
import React from 'react';
import ReactDOM from 'react-dom/client';
import App from './App.tsx';
import './index.css';
import { ApolloClient, ApolloProvider, InMemoryCache } from '@apollo/client';

const apolloClient = new ApolloClient({
  uri: 'http://localhost:5555/graphql', // Adjust the GraphQL endpoint URL as needed
  cache: new InMemoryCache(),
});

ReactDOM.createRoot(document.getElementById('root')!).render(
  <React.StrictMode>
    <ApolloProvider client={apolloClient}>
      <App />
    </ApolloProvider>
  </React.StrictMode>
);

⑨ Edit frontend/src/App.tsx

frontend/src/App.tsx


⑩ Automate type specification in frontend

npm i -ED @graphql-codegen/cli
mkdir src/_generated_
mkdir src/graphql
npx graphql-code-generator init
npm i -DE @graphql-codegen/typescript-react-apollo @graphql-codegen/typescript @graphql-codegen/typescript-operations

⑪ Edit frontend/codegen.yml

frontend/codegen.yml
overwrite: true
schema: 'http://localhost:5555/graphql'
documents: 'src/graphql/**/*.graphql'
generates:
  src/__generated__/graphql.ts:
    config:
      scalars:
        DateTime: 'Date'
plugins: ['typescript-react-apollo', 'typescript', 'typescript-operations']

⑫ Create todos/queries/get-todo.graphql in graphql file

Create todos/queries/get-todo.graphql in graphql file
const getTodoQuery = gql`
  query Todos {
    getTodos {
      todos {
        id
        title
        isCompleted
        createAt
        updateAt
      }
    }
  }
`;
npm run gen

⑬ Create graphql.tsx in generated file

_generated_/graphql.tsx
import { gql } from '@apollo/client';
import * as Apollo from '@apollo/client';
export type Maybe<T> = T | null;
export type InputMaybe<T> = Maybe<T>;
export type Exact<T extends { [key: string]: unknown }> = { [K in keyof T]: T[K] };
export type MakeOptional<T, K extends keyof T> = Omit<T, K> & { [SubKey in K]?: Maybe<T[SubKey]> };
export type MakeMaybe<T, K extends keyof T> = Omit<T, K> & { [SubKey in K]: Maybe<T[SubKey]> };
const defaultOptions = {} as const;
/** All built-in and custom scalars, mapped to their actual values */
export type Scalars = {
  ID: string;
  String: string;
  Boolean: boolean;
  Int: number;
  Float: number;
  Void: void;
};

export type CheckAuthResponse = {
  __typename?: 'CheckAuthResponse';
  user?: Maybe<User>;
};

export type ConfirmEmailInput = {
  token: Scalars['String'];
};

export type ConfirmEmailResponse = {
  __typename?: 'ConfirmEmailResponse';
  user?: Maybe<User>;
};

export type LoginInput = {
  email: Scalars['String'];
  password: Scalars['String'];
};

export type LoginResponse = {
  __typename?: 'LoginResponse';
  user?: Maybe<User>;
};

export type Mutation = {
  __typename?: 'Mutation';
  confirmEmail?: Maybe<ConfirmEmailResponse>;
  login?: Maybe<LoginResponse>;
  logout?: Maybe<Scalars['Void']>;
  register?: Maybe<RegisterResponse>;
};


export type MutationConfirmEmailArgs = {
  confirmEmailInput: ConfirmEmailInput;
};


export type MutationLoginArgs = {
  loginInput: LoginInput;
};


export type MutationRegisterArgs = {
  registerInput: RegisterInput;
};

export type Query = {
  __typename?: 'Query';
  checkAuth?: Maybe<CheckAuthResponse>;
  health?: Maybe<Scalars['Boolean']>;
};

export type RegisterInput = {
  email: Scalars['String'];
  password: Scalars['String'];
};

export type RegisterResponse = {
  __typename?: 'RegisterResponse';
  user?: Maybe<User>;
};

export type User = {
  __typename?: 'User';
  createdAt?: Maybe<Scalars['String']>;
  email?: Maybe<Scalars['String']>;
  id?: Maybe<Scalars['String']>;
  updatedAt?: Maybe<Scalars['String']>;
};

export type ConfirmEmailMutationVariables = Exact<{
  confirmEmailInput: ConfirmEmailInput;
}>;


export type ConfirmEmailMutation = { __typename?: 'Mutation', confirmEmail?: { __typename?: 'ConfirmEmailResponse', user?: { __typename?: 'User', id?: string | null, email?: string | null, createdAt?: string | null, updatedAt?: string | null } | null } | null };

export type LoginMutationVariables = Exact<{
  loginInput: LoginInput;
}>;


export type LoginMutation = { __typename?: 'Mutation', login?: { __typename?: 'LoginResponse', user?: { __typename?: 'User', id?: string | null, email?: string | null, createdAt?: string | null, updatedAt?: string | null } | null } | null };

export type LogoutMutationVariables = Exact<{ [key: string]: never; }>;


export type LogoutMutation = { __typename?: 'Mutation', logout?: void | null };

export type RegisterMutationVariables = Exact<{
  registerInput: RegisterInput;
}>;


export type RegisterMutation = { __typename?: 'Mutation', register?: { __typename?: 'RegisterResponse', user?: { __typename?: 'User', id?: string | null, email?: string | null, createdAt?: string | null, updatedAt?: string | null } | null } | null };

export type CheckAuthQueryVariables = Exact<{ [key: string]: never; }>;


export type CheckAuthQuery = { __typename?: 'Query', checkAuth?: { __typename?: 'CheckAuthResponse', user?: { __typename?: 'User', id?: string | null, email?: string | null, updatedAt?: string | null, createdAt?: string | null } | null } | null };


export const ConfirmEmailDocument = gql`
    mutation ConfirmEmail($confirmEmailInput: ConfirmEmailInput!) {
  confirmEmail(confirmEmailInput: $confirmEmailInput) {
    user {
      id
      email
      createdAt
      updatedAt
    }
  }
}
    `;
export type ConfirmEmailMutationFn = Apollo.MutationFunction<ConfirmEmailMutation, ConfirmEmailMutationVariables>;

/**
 * __useConfirmEmailMutation__
 *
 * To run a mutation, you first call `useConfirmEmailMutation` within a React component and pass it any options that fit your needs.
 * When your component renders, `useConfirmEmailMutation` returns a tuple that includes:
 * - A mutate function that you can call at any time to execute the mutation
 * - An object with fields that represent the current status of the mutation's execution
 *
 * @param baseOptions options that will be passed into the mutation, supported options are listed on: https://www.apollographql.com/docs/react/api/react-hooks/#options-2;
 *
 * @example
 * const [confirmEmailMutation, { data, loading, error }] = useConfirmEmailMutation({
 *   variables: {
 *      confirmEmailInput: // value for 'confirmEmailInput'
 *   },
 * });
 */
export function useConfirmEmailMutation(baseOptions?: Apollo.MutationHookOptions<ConfirmEmailMutation, ConfirmEmailMutationVariables>) {
        const options = {...defaultOptions, ...baseOptions}
        return Apollo.useMutation<ConfirmEmailMutation, ConfirmEmailMutationVariables>(ConfirmEmailDocument, options);
      }
export type ConfirmEmailMutationHookResult = ReturnType<typeof useConfirmEmailMutation>;
export type ConfirmEmailMutationResult = Apollo.MutationResult<ConfirmEmailMutation>;
export type ConfirmEmailMutationOptions = Apollo.BaseMutationOptions<ConfirmEmailMutation, ConfirmEmailMutationVariables>;
export const LoginDocument = gql`
    mutation Login($loginInput: LoginInput!) {
  login(loginInput: $loginInput) {
    user {
      id
      email
      createdAt
      updatedAt
    }
  }
}
    `;
export type LoginMutationFn = Apollo.MutationFunction<LoginMutation, LoginMutationVariables>;

/**
 * __useLoginMutation__
 *
 * To run a mutation, you first call `useLoginMutation` within a React component and pass it any options that fit your needs.
 * When your component renders, `useLoginMutation` returns a tuple that includes:
 * - A mutate function that you can call at any time to execute the mutation
 * - An object with fields that represent the current status of the mutation's execution
 *
 * @param baseOptions options that will be passed into the mutation, supported options are listed on: https://www.apollographql.com/docs/react/api/react-hooks/#options-2;
 *
 * @example
 * const [loginMutation, { data, loading, error }] = useLoginMutation({
 *   variables: {
 *      loginInput: // value for 'loginInput'
 *   },
 * });
 */
export function useLoginMutation(baseOptions?: Apollo.MutationHookOptions<LoginMutation, LoginMutationVariables>) {
        const options = {...defaultOptions, ...baseOptions}
        return Apollo.useMutation<LoginMutation, LoginMutationVariables>(LoginDocument, options);
      }
export type LoginMutationHookResult = ReturnType<typeof useLoginMutation>;
export type LoginMutationResult = Apollo.MutationResult<LoginMutation>;
export type LoginMutationOptions = Apollo.BaseMutationOptions<LoginMutation, LoginMutationVariables>;
export const LogoutDocument = gql`
    mutation Logout {
  logout
}
    `;
export type LogoutMutationFn = Apollo.MutationFunction<LogoutMutation, LogoutMutationVariables>;

/**
 * __useLogoutMutation__
 *
 * To run a mutation, you first call `useLogoutMutation` within a React component and pass it any options that fit your needs.
 * When your component renders, `useLogoutMutation` returns a tuple that includes:
 * - A mutate function that you can call at any time to execute the mutation
 * - An object with fields that represent the current status of the mutation's execution
 *
 * @param baseOptions options that will be passed into the mutation, supported options are listed on: https://www.apollographql.com/docs/react/api/react-hooks/#options-2;
 *
 * @example
 * const [logoutMutation, { data, loading, error }] = useLogoutMutation({
 *   variables: {
 *   },
 * });
 */
export function useLogoutMutation(baseOptions?: Apollo.MutationHookOptions<LogoutMutation, LogoutMutationVariables>) {
        const options = {...defaultOptions, ...baseOptions}
        return Apollo.useMutation<LogoutMutation, LogoutMutationVariables>(LogoutDocument, options);
      }
export type LogoutMutationHookResult = ReturnType<typeof useLogoutMutation>;
export type LogoutMutationResult = Apollo.MutationResult<LogoutMutation>;
export type LogoutMutationOptions = Apollo.BaseMutationOptions<LogoutMutation, LogoutMutationVariables>;
export const RegisterDocument = gql`
    mutation Register($registerInput: RegisterInput!) {
  register(registerInput: $registerInput) {
    user {
      id
      email
      createdAt
      updatedAt
    }
  }
}
    `;
export type RegisterMutationFn = Apollo.MutationFunction<RegisterMutation, RegisterMutationVariables>;

/**
 * __useRegisterMutation__
 *
 * To run a mutation, you first call `useRegisterMutation` within a React component and pass it any options that fit your needs.
 * When your component renders, `useRegisterMutation` returns a tuple that includes:
 * - A mutate function that you can call at any time to execute the mutation
 * - An object with fields that represent the current status of the mutation's execution
 *
 * @param baseOptions options that will be passed into the mutation, supported options are listed on: https://www.apollographql.com/docs/react/api/react-hooks/#options-2;
 *
 * @example
 * const [registerMutation, { data, loading, error }] = useRegisterMutation({
 *   variables: {
 *      registerInput: // value for 'registerInput'
 *   },
 * });
 */
export function useRegisterMutation(baseOptions?: Apollo.MutationHookOptions<RegisterMutation, RegisterMutationVariables>) {
        const options = {...defaultOptions, ...baseOptions}
        return Apollo.useMutation<RegisterMutation, RegisterMutationVariables>(RegisterDocument, options);
      }
export type RegisterMutationHookResult = ReturnType<typeof useRegisterMutation>;
export type RegisterMutationResult = Apollo.MutationResult<RegisterMutation>;
export type RegisterMutationOptions = Apollo.BaseMutationOptions<RegisterMutation, RegisterMutationVariables>;
export const CheckAuthDocument = gql`
    query CheckAuth {
  checkAuth {
    user {
      id
      email
      updatedAt
      createdAt
    }
  }
}
    `;

/**
 * __useCheckAuthQuery__
 *
 * To run a query within a React component, call `useCheckAuthQuery` and pass it any options that fit your needs.
 * When your component renders, `useCheckAuthQuery` returns an object from Apollo Client that contains loading, error, and data properties
 * you can use to render your UI.
 *
 * @param baseOptions options that will be passed into the query, supported options are listed on: https://www.apollographql.com/docs/react/api/react-hooks/#options;
 *
 * @example
 * const { data, loading, error } = useCheckAuthQuery({
 *   variables: {
 *   },
 * });
 */
export function useCheckAuthQuery(baseOptions?: Apollo.QueryHookOptions<CheckAuthQuery, CheckAuthQueryVariables>) {
        const options = {...defaultOptions, ...baseOptions}
        return Apollo.useQuery<CheckAuthQuery, CheckAuthQueryVariables>(CheckAuthDocument, options);
      }
export function useCheckAuthLazyQuery(baseOptions?: Apollo.LazyQueryHookOptions<CheckAuthQuery, CheckAuthQueryVariables>) {
          const options = {...defaultOptions, ...baseOptions}
          return Apollo.useLazyQuery<CheckAuthQuery, CheckAuthQueryVariables>(CheckAuthDocument, options);
        }
export type CheckAuthQueryHookResult = ReturnType<typeof useCheckAuthQuery>;
export type CheckAuthLazyQueryHookResult = ReturnType<typeof useCheckAuthLazyQuery>;
export type CheckAuthQueryResult = Apollo.QueryResult<CheckAuthQuery, CheckAuthQueryVariables>;

Reference site

【TypeScript & GraphQL】で Fullstack Web Application開発 #1 - プロジェクトセットアップ
【TypeScript & GraphQL】で Fullstack Web Application開発 #2 - ミニマムなApollo serverの立ち上げ
【TypeScript & GraphQL】で Fullstack Web Application開発 #3 - Graphql コードジェネレーターの追加
【TypeScript & GraphQL】で Fullstack Web Application開発 #4 - TypeDefsとResolversの自動インポート
【TypeScript & GraphQL】で Fullstack Web Application開発 #5 - Prismaの準備&TodoCRUDの実装
【TypeScript & GraphQL】で Fullstack Web Application開発 #6 - DateTime Scalarの追加
【TypeScript & GraphQL】で Fullstack Web Application開発 #7- Tailwind CSSとApollo Clientの実装

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?