Как использовать NestJS с Prisma

В этом руководстве будет показано, как использовать Nest и Prisma для создания REST API. Вкратце: демонстрация проводилась с использованием Prisma v3.11.0.

Что такое Prisma?

Prisma — это объектно-реляционный преобразователь (ORM) Node и TypeScript нового поколения. Он предоставляет набор инструментов баз данных с открытым исходным кодом для PostgreSQL, MySQL, SQL Server, SQLite и MongoDB (в настоящее время находится в предварительной версии), что позволяет разработчикам создавать приложения быстрее и с меньшим количеством ошибок.

Prisma предоставляет вам декларативный метод для определения моделей данных и отношений вашего приложения в более понятном формате. Кроме того, если у вас уже есть база данных, вам не придется мучиться с созданием моделей базы данных с нуля, поскольку функции самоанализа Prisma сделают это за вас — они очень гибкие.

Для чего используется Prisma?

Prisma повышает безопасность типов, упрощая доступ к базе данных, сохраняя и сокращая повторяющийся шаблон CRUD. Prisma легко интегрируется в предпочитаемую вами платформу и представляет собой идеальный набор инструментов для работы с базами данных для создания надежных и масштабируемых веб-API. Prisma быстро интегрируется с различными платформами, такими как GraphQL , Next.js, Nest, Apollo и Express.js.

Prisma устраняет многие недостатки традиционных ORM, такие как отсутствие безопасности типов, смешанная бизнес-логика и логика хранения, а также непредсказуемые запросы, вызванные отложенной загрузкой.

Первоначальная настройка проекта

Чтобы начать работу с этим руководством, убедитесь, что у вас есть:

  • Node.js (≥v10.13.0, кроме v13) установлен.
  • Postman установлен

Прежде чем мы начнем создавать приложение Nest, вам необходимо установить Nest CLI с помощью следующей команды:

npm i -g @nestjs/cli

Подождите завершения установки. После завершения установки создайте новое приложение Nest с помощью следующей команды:

nest new prisma-api

Выберите npm в качестве предпочтительного менеджера пакетов и нажмите Enter. Приложение пройдет некоторые процессы установки. Пока вы ждете, вы можете выпить чашечку кофе.

После того, как npm установит все пакеты, необходимые для запуска приложения, измените каталог на папку проекта и запустите сервер с помощью команды ниже:

npm run start:dev

Начало работы с Prisma

В этом руководстве используется Prisma v3.11.0. Установите Prisma CLI в качестве зависимости разработки с помощью команды ниже:

npm install prisma --save-dev

После завершения установки вызовите CLI Prisma локально, используя npx, с помощью следующей команды:

npx prisma

Теперь создайте первоначальную настройку Prisma с помощью initкоманды Prisma:

npx prisma init

Приведенная выше команда создает новый каталог Prisma со следующими файлами:

  • schema.prisma: указывает подключение к базе данных и содержит схему базы данных.
  • .env: файл dotenv , обычно используемый для хранения учетных данных вашей базы данных в группе переменных среды.

Подключение к базе данных

С установленной Prisma настройка на вашем компьютере довольно проста. Для демонстрации в этом руководстве мы подключимся к базе данных SQLite. Чтобы начать, откройте файл datasource/schema.prisma и обновите содержимое с помощью приведенного ниже фрагмента кода:

generator client {
  provider = "prisma-client-js"
}

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

В приведенном выше фрагменте мы указали sqlite в качестве поставщика базы данных. Теперь измените файл .env, указав расположение файла базы данных.

DATABASE_URL="file:./todos.sqlite"

Создание схемы базы данных

Настроив подключение к базе данных, теперь вы можете создавать свои таблицы базы данных, определив схему в файле schema.prisma. Для демонстрации в этом руководстве мы определим схему Todo с помощью приведенного ниже фрагмента кода:

model Todo {
  id          Int      @id @default(autoincrement())
  title       String
  description String?
  completed   Boolean? @default(false)
  user        String
}  

Создайте файлы миграции SQL и запустите их в базе данных с помощью следующей команды:

npx prisma migrate dev --name init

Приведенная выше команда создаст структуру папок ниже:

prisma
 ┣ migrations
 ┃ ┣ 20220315212227_init
 ┃ ┃ ┗ migration.sql
 ┃ ┗ migration_lock.toml
 ┣ schema.prisma
 ┣ todos.sqlite
 ┗ todos.sqlite-journal
  

Настройка клиента Prisma и сервиса Prisma

Prisma Client — это типобезопасный клиент базы данных, созданный на основе вашего определения модели Prisma. Он предоставляет операции CRUD, адаптированные специально для ваших моделей.

Установите клиент Prisma с помощью команды ниже:

npm install @prisma/client

После настройки клиента Prisma создайте файл prisma.service в папке src, чтобы абстрагировать API клиента Prisma для запросов к базе данных внутри службы, используя приведенный ниже фрагмент кода:

import { INestApplication, Injectable, OnModuleInit } from '@nestjs/common';
import { PrismaClient } from '@prisma/client';

@Injectable()
export class PrismaService extends PrismaClient implements OnModuleInit {
  async onModuleInit() {
    await this.$connect();
  }

  async enableShutdownHooks(app: INestApplication) {
    this.$on('beforeExit', async () => {
      await app.close();
    });
  }
}

В приведенном выше фрагменте кода мы создали новый код PrismaService, который отвечает за создание экземпляров PrismaClient и подключение к вашей базе данных.

Создание todo модуля

Настроив сервис Prisma, сгенерируйте todoмодуль для всей todoлогики с помощью команды ниже:

nest generate module todo

Затем сгенерируйте служебный файл для пользовательского модуля с помощью команды ниже:

nest generate service todo/service/todo --flat

Затем обновите содержимое файла todo.service, используя приведенный ниже фрагмент кода:

import { Injectable } from '@nestjs/common';
import { PrismaService } from '../../prisma.service';
import { Todo, Prisma } from '@prisma/client';
@Injectable()
export class TodoService {
  constructor(private prisma: PrismaService) {}
  async getAllTodo(): Promise<Todo[]> {
    return this.prisma.todo.findMany();
  }
  async getTodo(id: number): Promise<Todo | null> {
    return this.prisma.todo.findUnique({ where: { id: Number(id) } });
  }
  async createTodo(data: Todo): Promise<Todo> {
    return this.prisma.todo.create({
      data,
    });
  }
  async updateTodo(id: number): Promise<Todo> {
    return this.prisma.todo.update({
      where: { id: Number(id) },
      data: { completed: true },
    });
  }
  async deleteTodo(id: number): Promise<Todo> {
    return this.prisma.todo.delete({
      where: { id: Number(id) },
    });
  }
}

В приведенном выше фрагменте кода мы создали все операции CRUD для службы нашего пользователя.

Теперь сгенерируйте todo контроллер, чтобы определить все маршруты API для пользовательской службы с помощью команды ниже:

nest generate controller tod/controller/todo --flat

Обновите содержимое файла , используя приведенный ниже фрагмент кода:todo.controller.ts

import {
  Controller,
  Get,
  Param,
  Post,
  Body,
  Put,
  Delete,
} from '@nestjs/common';
import { TodoService } from '../service/todo.service';
import { Todo } from '@prisma/client';
@Controller('api/v1/todo')
export class TodoController {
  constructor(private readonly todoService: TodoService) {}
  @Get()
  async getAllTodo(): Promise<Todo[]> {
    return this.todoService.getAllTodo();
  }
  @Post()
  async createTodo(@Body() postData: Todo): Promise<Todo> {
    return this.todoService.createTodo(postData);
  }
  @Get(':id')
  async getTodo(@Param('id') id: number): Promise<Todo | null> {
    return this.todoService.getTodo(id);
  }
  @Put(':id')
  async Update(@Param('id') id: number): Promise<Todo> {
    return this.todoService.updateTodo(id);
  }
  @Delete(':id')
  async Delete(@Param('id') id: number): Promise<Todo> {
    return this.todoService.deleteTodo(id);
  }
}

Откройте файл todo.module.ts, импортируйте PrismaService и добавьте его в массив поставщиков с помощью приведенного ниже фрагмента кода:

...
import { PrismaService } from 'src/prisma.service';

@Module({
  controllers: [...],
  providers: [..., PrismaService],
})
...

На этом этапе вы успешно создали REST API Nest Prisma! Теперь давайте протестируем приложение с помощью Postman.

Тестируем наше приложение

Создав все маршруты API для демонстрационного приложения, запустите Postman и протестируйте конечные точки.

Добавить todo маршрут:

Добавить маршрут задач

Получить todo маршрут:

Получить маршрут Todo

Продолжайте и поиграйте с другими конечными точками.

Заключение

Из этого руководства вы узнали, как использовать NestJS с Prisma для создания REST API. Мы начали со знакомства с этими инструментами, узнали, как создать проект Nest и настроить Prisma с помощью SQLite. Мы также определили todo схему, выполнили миграцию и выполнили операции CRUD с помощью Prisma.

Теперь, когда у вас есть эти знания, как бы вы использовали Prisma в своем следующем проекте Nest? Возможно, вы сможете узнать больше об операциях Prisma CRUD и добавить дополнительные функции в демонстрационное приложение.