koa2+sequelize上传文件以及删除文件

koa2实现上传文件需要中间件的帮助,由三种可以使用的,这里使用koa-body来实现

需要注意的是koa-body有一些坑需要注意:

  1. 位置 use的位置要在app.use(router.routes());之前
  2. 不能同时与koa-bodyparser同时使用,否则在post请求时会出现请求被拦截的情况
    app.ts:
import * as koaBody from 'koa-body';
import * as Router from 'koa-router';
import AppRoutes from './routes';

const router = new Router();
// 相当于注册每一个路由,在路由文件里规定路径和方法
AppRoutes.forEach(route => router[route.method](route.path, route.action));

// 上传需要配置的中间件 引入位置讲究,且与bodyparser冲突
app.use(koaBody({
  multipart: true,
  formidable: {
  uploadDir: path.join(__dirname, 'public/upload/'), // 设置文件上传目录
    maxFileSize: 500 * 1024 * 1024,    // 设置上传文件大小最大限制,默认5M
  },
}));

app.use(router.routes());
app.use(router.allowedMethods());

上传逻辑部分:

export const uploadFile = async (ctx, next) => {
  // 上传多个文件
  const uId = 2;
  const req = ctx.request.body;
  const file = ctx.request.files.item; // 获取上传文件
  // console.log(file);
  // 创建可读流
  const reader = fs.createReadStream(file.path);
  const filePath = path.resolve(`src/public/upload/${file.name}`);
  // 生成hash
  const fsHash = crypto.createHash('md5');
  const buffer = fs.readFileSync(file.path);
  fsHash.update(buffer);
  const fileHash = fsHash.digest('hex');
  console.log('文件的MD5是:%s', fileHash);
  // hash未重复时才添加
  await fileModel.findOrCreate({
    where: {
      fileHash,
    },
    defaults: {
      proId: req.projectId,
      fileName,
      filePath,
      fileCreateTime: new Date(),
      fileHash,
    },
  })
    .spread((files, created) => {
      console.log('文件recur是:');
      console.log(created);
      if (created) { // true为添加成功
      // 创建可写流
        const upStream = fs.createWriteStream(filePath);
        // 可读流通过管道写入可写流
        reader.pipe(upStream);
        /* 同步读取文件,会产生阻塞 */
        return ctx.body = { code: 200, msg: '上传成功!' };
      } // false已经存在
      return ctx.body = { code: 403, msg: '文件重复' };
    });
};

删除文件逻辑部分:

/* 删除文件---根据file_id */
export const deleteSomeFile = async (ctx, next) => {
  const uId = 2;
  const req = ctx.request.query;
  /* 先找到这个文件的project_id和file_type不用前端传值了 */
  const del = await fileModel.findOne({
	// 查找
	 where: { fileId: req.file_id },
  });
  /* 删除数据库中对应file_id的文件 */
  await fileModel.destroy({
    where: {
      fileId,
    },
    attributes: [ 'proId' ],
  });
  console.log(del);
  // 注意 删除时要把文件真的删除 不仅只是从数据库里删除
  const filePath = path.resolve(`src/public/upload/${del.fileName}`);
  deleteRecursive(filePath);
  /* 删除后返回当前文件列表 */
  const data = await dispalyList(del.proId);
  return ctx.body = { retcode: 0, result: { data, msg: 'success' } };
};

// 判断文件是否存在再删除
const deleteRecursive = (url: string) => {
  // 判断给定的路径是否存在
  if (fs.existsSync(url)) {
    fs.unlinkSync(url);
  } else {
    console.log('给定的路径不存在,请给出正确的路径');
  }
};

你可能感兴趣的:(koa)