NodeJs实战-Express构建照片存储网站(2)-上传、展示文件

本博客介绍了如何使用Express构建一个照片存储网站,实现了文件上传和图片展示功能。通过设置静态资源目录,可以访问public文件夹下的图片。在photo页面,使用fs模块读取images文件夹下所有图片并展示。新增了上传页面路由和表单提交接口,通过multiparty中间件解析上传的文件,重命名并保存到服务器,最后重定向回照片展示页面。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

上一节使用的静态数据存储的图片的数据,本节增加如下功能
1–上传文件
2–展示文件
在这里插入图片描述

静态资源显示图片

app.js 中有指定了静态资源文件的路径

app.use(express.static(path.join(__dirname, 'public')));

有这一行的设置,可以访问 public 文件夹下面的静态资源
在这里插入图片描述
工程目录下面 public/images 下面有若干图片,启动服务之后,访问对应的地址就可以展示图片,比如图片的名字为 1669269355053_1.png,浏览器访问

http://127.0.0.1:3000/images/1669269355053_1.png

在这里插入图片描述

photo页面展示文件夹下的图片

修改 routes 文件下的 photo.js

var express = require('express');
var router = express.Router();
var multiparty = require('multiparty');
var fs = require('fs');
var destpath = "./public/images/";
var urlpath = "/images/";

// photos.push({
//   'name': 'photo1',
//   'path': '/images/abd3c3ec-922c-11e7-8a20-0242ac11000c.png'
// });
// photos.push({
//   'name': 'photo2',
//   'path': '/images/6db31128-39dd-11e7-895e-0242ac110016.png'
// });

/* GET photo page. */
router.get('/', function (req, res, next) {
    let arr = fs.readdir(destpath, function(err, files) {
      if (err) {
        console.log('读取文件夹错误:', err);
      } else {
        var photos = [];
        files.forEach(fileName => {
          let item = {
            'name':'',
            'path':''
          };
          item.name = findFileName(fileName);
          item.path = urlpath + fileName;
          photos.push(item);
        });
        res.render('photos', { title: 'Photos', data: photos });
      }
    });
});

function findFileType(originalFilename) {
  var lastIndex = originalFilename.lastIndexOf('.');
  if (lastIndex != -1) {
    return originalFilename.substring(lastIndex);
  }
  return originalFilename;
}

function findFileName(inputFileName) {
  var lastIndex = inputFileName.lastIndexOf('.');
  if (lastIndex != -1) {
    return inputFileName.substring(0, lastIndex);
  }
  return inputFileName;
}

module.exports = router;

展示文件夹下的所有图片

router.get('/', function (req, res, next) {
    let arr = fs.readdir(destpath, function(err, files) {
      if (err) {
        console.log('读取文件夹错误:', err);
      } else {
        var photos = [];
        files.forEach(fileName => {
          let item = {
            'name':'',
            'path':''
          };
          item.name = findFileName(fileName);
          item.path = urlpath + fileName;
          photos.push(item);
        });
        res.render('photos', { title: 'Photos', data: photos });
      }
    });
});
  1. 使用 fs 模块读取指定文件夹下面的所有文件
  2. 将图片名字拼接静态资源的前缀 /images/,作为 img 标签的 src 数据
  3. 将数据输出到 views/photos/index.ejs 视图
res.render('photos', { title: 'Photos', data: photos });

启动服务,访问

http://127.0.0.1:3000/photo

展示了 images 文件夹下面的所有图片
在这里插入图片描述

上传文件

增加上传页面的路由

  1. 修改 photo.js, 增加如下代码
router.get('/upload', function (req, res, next) {
  res.render('photos/upload', { title: '图片上传' });
});
  1. 增加路由对应的页面 upload.ejs
<!DOCTYPE html>
<html>
  <head>
    <title><%= title %></title>
    <link rel='stylesheet' href='/stylesheets/style.css' />
  </head>
  <body>
    <h1><%= title %></h1>
    <p>图片上传</p>
    <form method="post" enctype="multipart/form-data" action="/photo/submit" >
      <p><input type="text" name="name", placeholder="Name" /></p>
      <p><input type="file" name="file" /></p>
      <p><input type="submit" value="Upload" /></p>
    </form>
  </body>
</html>

编写 form 表单上传文件,需要指定 form 表单的 enctype 属性为 multipart/form-data,当点击提交的时候会调用后台的 /photo/submit接口
在这里插入图片描述

增加提交接口的路由

修改 photo.js

  1. 先引入 multiparty 模块用于解析表单
var multiparty = require('multiparty');
  1. 增加 /submit 路由
router.post('/submit', function (req, res, next) {
  var form = new multiparty.Form();
  form.encoding = 'utf-8';
  form.uploadDir = destpath;
  form.maxFilesSize = 20 * 1024 * 1024;
  form.parse(req, (err, fields, files) => {
    if (err) {
      console.log('解析上传文件错误:', err);
    } else {
      var originalFilename = files.file[0].originalFilename;
      var fileType = findFileType(originalFilename);
      var fileName = originalFilename;
      if (fields.name != null) {
        fileName = fields.name[0] + fileType;
      }
      var uploadedPath = files.file[0].path;
      var newFileName = destpath + new Date().getTime() + "_" + fileName;
      fs.rename(uploadedPath, newFileName, (err) => {
        if (err) {
          console.log('重命名文件错误:', err);
          throw err;
        }
        res.redirect('/photo');
      });
    }
  });

});

第一步:解析 form 表单

 var form = new multiparty.Form();
  form.encoding = 'utf-8';
  form.uploadDir = destpath;
  form.maxFilesSize = 20 * 1024 * 1024;
  form.parse(req, (err, fields, files) => {
  }));

第二步:重命名文件,用表单接收的name重命名

 fs.rename(uploadedPath, newFileName, (err) => {});

第三步:重定向到图片展示页面

 res.redirect('/photo');

网站效果图

  1. 启动服务
F:\Github\Nodejs\photo>npm start

> photo@0.0.0 start
> node ./bin/www
  1. 浏览器访问
http://127.0.0.1:3000/photo

在这里插入图片描述
3. 点击上传,跳转到表单上传页面
在这里插入图片描述
4. 填写完表单,点击upload,重定向到首页
在这里插入图片描述

项目地址

https://gitee.com/3281328128/photo/tree/master/

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Chengdu.S

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值