nestjs入门实战(二):上传图片

前言

本章节主要介绍nestjs服务端上传图片资源使用express中间件 multer,FileInterceptor,并通过express static生成静态目录暴露出图片资源地址,前端通过postman上传图片资源

项目目录结构

大致项目结构如下: src/upload为上传资源模块,根目录下uploads为上传资源存放位置

css 复制代码
nest-upload/
├── src/ 
│ ├── upload/ (处理上传资源模块)
│ │ ├── upload.controller.ts 
│ │ ├── upload.module.ts 
│ ├── app.module.ts 
│ ├── main.ts 
├── uploads/ (上传的文件将会存储在这里) 
├── .gitignore 
├── package.json 
├── tsconfig.json 
└── README.md

demo最终效果: Postman图片上传和访问

1. 快速创建nestjs 项目

这里通过nestjs CLI快速创建项目nest-upload,点击查看如何创建项目

shell 复制代码
nest new nest-upload
cd nest-upload 

创建成功后切换到项目内,由于nestjs基于 Express 框架构建,所以Express包已经自带不需要安装,其中multer,@types/multer依赖包需要安装

shell 复制代码
npm i multer @types/multer --save

再通过nestjs CLI快速创建 upload资源上传模块

shell 复制代码
nest g mo upload # 创建模块 
nest g co upload --no-spec # 创建controller层 

2. multer资源上传处理

图片资源上传后服务需要把资源存储到根目录下的uploads中,需要对启动文件 src/main.ts 判断是否有uploads目录,当没有uploads时候会自动创建

diff 复制代码
// src/main.ts

import { NestFactory } from '@nestjs/core';
import { AppModule } from './app.module';
+import { join } from 'path';
+import { existsSync, mkdirSync } from 'fs';

async function bootstrap() {
  const app = await NestFactory.create(AppModule);
+  const uploadDir = join(process.cwd(), 'uploads');
+  if (!existsSync(uploadDir)) {
+    mkdirSync(uploadDir);
+  }
  await app.listen(3000);
}
bootstrap();

upload.module.ts添加处理上传资源代码:

ts 复制代码
// src/upload/upload.module.ts

import { Module } from '@nestjs/common';
import { MulterModule } from '@nestjs/platform-express';
import { diskStorage } from 'multer';
import { extname, join } from 'path';
import { UploadController } from './upload.controller';
import { UploadService } from './upload.service';

// 获取项目根目录并设置上传目录
const uploadDir = join(process.cwd(), 'uploads');

@Module({
  imports: [
    MulterModule.register({
      storage: diskStorage({
        destination: (req, file, cb) => {
          cb(null, uploadDir);
        },
        filename: (req, file, cb) => {
          const ext = extname(file.originalname);
          const filename = `${Date.now()}${ext}`;
          cb(null, filename);
        },
      }),
      fileFilter: (req, file, cb) => {
        if (file.mimetype === 'image/jpeg' || file.mimetype === 'image/png') {
          cb(null, true);
        } else {
          cb(new Error('Only images are allowed...'), false);
        }
      },
    }),
  ],
  controllers: [UploadController],
  providers: [UploadService],
})
export class UploadModule { }

其中 fileFilter可以控制上传文件的类型,大小等

现在在upload.controller.ts创建上传图片接口: localhost:3000/upload/uploadImage 请求方式为Post, Post body中参数为file

ts 复制代码
// src/upload/upload.controller.ts

import { Controller, Post, UploadedFile, UseInterceptors } from '@nestjs/common';
import { FileInterceptor } from '@nestjs/platform-express';

@Controller('upload')
export class UploadController {

    @Post('/uploadImage')
    @UseInterceptors(FileInterceptor('file'))
    async uploadImage(@UploadedFile() file) {
        return "upload success"
     
    }
}

其中@FileInterceptor,@UploadedFile为nestjs框架提供的上传资源装饰器(查看文档)

3.Postman上传图片

首先需要安装Postman(资源下载),后创建上传图片资源请求,步骤:

之后点击 Select Files选择上传的图片,点击Send按钮上传图片,效果:

上方为nest-upload项目根目录下资源存放文件uploads生成上传图片资源情况

4. 生成静态资源目录

日常开发中,当资源上传成功后需要返回可访问资源的url地址,这里我们需要修改src/main.ts通过express static生成静态资源目录

diff 复制代码
// src/main.ts

import { NestFactory } from '@nestjs/core';
+ import * as express from 'express';
...

async function bootstrap() {
  ...
+ app.use('/uploads', express.static(join(process.cwd(), 'uploads')));  
  await app.listen(3000);
}
bootstrap();

修改upload.controller.ts图片上传成功后返回对应资源的url地址

diff 复制代码
// src/upload/upload.controller.ts
...

    async uploadImage(@UploadedFile() file) {
-        return "upload success"
+         const fileUrl = `http://localhost:3000/uploads/${file.filename}`; 
+         return {
+            url: fileUrl,
+         };
     
    }
}

再次使用Postman上传图片资源效果:

总结

资源上传为大部分应用都需要有的需求,nestjs通过FileInterceptor,UploadedFile生态支持上传资源,再通过express静态生成目录暴露出资源地址。nestjs是在express基础上封装的框架,所以项目中可以不需要安装express包依赖,直接使用express

相关推荐
坐吃山猪2 天前
Python22-PostMan调试MCP
测试工具·postman·mcp
Dumbness3 天前
一份 JSON 生成增删改查接口,入参清洗漏了什么:Number(" ") 是 0,搜 100% 把 1000 元券也搜出来
node.js·express
Dumbness6 天前
毕设后台导出 CSV 的 4 个坑:date 字段漏了公式防护,搜索框输入 % 能扫全表
node.js·express
光谱SpectrAI7 天前
打开 Postman 会改 Codex?Windows 上 4 处都没有
postman
yz_aiks7 天前
Postman 自动给 Claude Code、Codex、Cursor 装插件怎么查和卸载:本机实测 5 处痕迹(Postman 12.34)
安全·postman·ai编程·开发工具·claude code
Dumbness9 天前
一个手机号验证码登录接口的五个坑:无限发码、无限试码,传个数字就让 Express 进程退出
node.js·express
mewowaBc12 天前
postman使用细则
测试工具·postman·偏差
洋不写bug15 天前
HTTP(二):万字解析HTTP交互的请求、响应报文格式
网络协议·http·交互·postman·请求格式·响应格式·restful规范
星光开发者17 天前
基于springboot智慧草场牛羊管理系统-计算机毕设【课程设计】50360
vue.js·spring boot·后端·mysql·php·课程设计·express
vx_Biye_Design20 天前
django房屋租赁推荐系统78455-计算机课程设计、毕业设计
vue.js·spring boot·后端·python·django·课程设计·express