在Linux环境下使用Node.js实现文件的上传和下载功能,通常会借助一些流行的框架和中间件。以下是使用Express.js框架结合Multer(用于上传)和Express.static(用于下载)来实现这一功能的详细步骤。
首先,确保你的Linux系统上已经安装了Node.js和npm。你可以通过以下命令检查是否已安装:
node -v
npm -v
如果未安装,可以访问Node.js官网下载并安装适合你系统的版本。
创建一个新的项目目录并进入:
mkdir file-upload-download
cd file-upload-download
初始化一个新的Node.js项目:
npm init -y
安装Express.js和Multer:
npm install express multer
创建一个名为app.js
的文件,并添加以下代码:
const express = require('express');
const multer = require('multer');
const path = require('path');
const app = express();
// 设置存储引擎
const storage = multer.diskStorage({
destination: function (req, file, cb) {
cb(null, 'uploads/') // 设置上传文件的存储目录
},
filename: function (req, file, cb) {
cb(null, Date.now() + '-' + file.originalname) // 重命名文件以避免冲突
}
});
// 初始化上传
const upload = multer({
storage: storage,
limits: { fileSize: 10 * 1024 * 1024 }, // 限制文件大小为10MB
fileFilter: function (req, file, cb) {
checkFileType(file, cb);
}
}).single('file'); // 'file' 是表单中文件字段的名称
// 检查文件类型
function checkFileType(file, cb) {
// 允许的扩展名
const filetypes = /jpeg|jpg|png|gif/;
// 检查扩展名
const extname = filetypes.test(path.extname(file.originalname).toLowerCase());
// 检查MIME类型
const mimetype = filetypes.test(file.mimetype);
if (mimetype && extname) {
return cb(null, true);
} else {
cb('Error: Images Only!');
}
}
// 上传路由
app.post('/upload', (req, res) => {
upload(req, res, (err) => {
if (err) {
res.status(400).send({ message: err });
} else {
if (req.file == undefined) {
res.status(400).send({ message: 'No file selected!' });
} else {
res.send({
message: 'File uploaded!',
file: `uploads/${req.file.filename}`
});
}
}
});
});
// 启动服务器
const PORT = process.env.PORT || 3000;
app.listen(PORT, () => console.log(`Server started on port ${PORT}`));
在项目根目录下创建一个uploads
文件夹,用于存放上传的文件:
mkdir uploads
启动服务器:
node app.js
服务器将在http://localhost:3000
运行。
修改app.js
,添加下载路由:
// 下载路由
app.get('/download/:filename', (req, res) => {
const { filename } = req.params;
const filePath = path.join(__dirname, 'uploads', filename);
// 检查文件是否存在
fs.access(filePath, fs.constants.F_OK, (err) => {
if (err) {
return res.status(404).send({ message: 'File not found!' });
}
res.download(filePath, filename, (err) => {
if (err) throw err;
});
});
});
确保引入fs
模块:
const fs = require('fs');
完整代码如下:
const express = require('express');
const multer = require('multer');
const path = require('path');
const fs = require('fs');
const app = express();
// 设置存储引擎
const storage = multer.diskStorage({
destination: function (req, file, cb) {
cb(null, 'uploads/') // 设置上传文件的存储目录
},
filename: function (req, file, cb) {
cb(null, Date.now() + '-' + file.originalname) // 重命名文件以避免冲突
}
});
// 初始化上传
const upload = multer({
storage: storage,
limits: { fileSize: 10 * 1024 * 1024 }, // 限制文件大小为10MB
fileFilter: function (req, file, cb) {
checkFileType(file, cb);
}
}).single('file'); // 'file' 是表单中文件字段的名称
// 检查文件类型
function checkFileType(file, cb) {
// 允许的扩展名
const filetypes = /jpeg|jpg|png|gif/;
// 检查扩展名
const extname = filetypes.test(path.extname(file.originalname).toLowerCase());
// 检查MIME类型
const mimetype = filetypes.test(file.mimetype);
if (mimetype && extname) {
return cb(null, true);
} else {
cb('Error: Images Only!');
}
}
// 上传路由
app.post('/upload', (req, res) => {
upload(req, res, (err) => {
if (err) {
res.status(400).send({ message: err });
} else {
if (req.file == undefined) {
res.status(400).send({ message: 'No file selected!' });
} else {
res.send({
message: 'File uploaded!',
file: `uploads/${req.file.filename}`
});
}
}
});
});
// 下载路由
app.get('/download/:filename', (req, res) => {
const { filename } = req.params;
const filePath = path.join(__dirname, 'uploads', filename);
// 检查文件是否存在
fs.access(filePath, fs.constants.F_OK, (err) => {
if (err) {
return res.status(404).send({ message: 'File not found!' });
}
res.download(filePath, filename, (err) => {
if (err) throw err;
});
});
});
// 启动服务器
const PORT = process.env.PORT || 3000;
app.listen(PORT, () => console.log(`Server started on port ${PORT}`));
http://localhost:3000/upload
。file
,类型为File的字段,并选择要上传的文件。如果上传成功,你将收到类似以下的响应:
{
"message": "File uploaded!",
"file": "uploads/1697052345678-image.jpg"
}
http://localhost:3000/download/1697052345678-image.jpg
(将文件名替换为你实际上传的文件名)。在实际应用中,需要注意以下几点以确保文件上传和下载的安全性:
以下是完整的app.js
代码,整合了上传和下载功能:
const express = require('express');
const multer = require('multer');
const path = require('path');
const fs = require('fs');
const app = express();
// 设置存储引擎
const storage = multer.diskStorage({
destination: function (req, file, cb) {
cb(null, 'uploads/') // 设置上传文件的存储目录
},
filename: function (req, file, cb) {
cb(null, Date.now() + '-' + file.originalname) // 重命名文件以避免冲突
}
});
// 初始化上传
const upload = multer({
storage: storage,
limits: { fileSize: 10 * 1024 * 1024 }, // 限制文件大小为10MB
fileFilter: function (req, file, cb) {
checkFileType(file, cb);
}
}).single('file'); // 'file' 是表单中文件字段的名称
// 检查文件类型
function checkFileType(file, cb) {
// 允许的扩展名
const filetypes = /jpeg|jpg|png|gif/;
// 检查扩展名
const extname = filetypes.test(path.extname(file.originalname).toLowerCase());
// 检查MIME类型
const mimetype = filetypes.test(file.mimetype);
if (mimetype && extname) {
return cb(null, true);
} else {
cb('Error: Images Only!');
}
}
// 上传路由
app.post('/upload', (req, res) => {
upload(req, res, (err) => {
if (err) {
res.status(400).send({ message: err });
} else {
if (req.file == undefined) {
res.status(400).send({ message: 'No file selected!' });
} else {
res.send({
message: 'File uploaded!',
file: `uploads/${req.file.filename}`
});
}
}
});
});
// 下载路由
app.get('/download/:filename', (req, res) => {
const { filename } = req.params;
const filePath = path.join(__dirname, 'uploads', filename);
// 检查文件是否存在
fs.access(filePath, fs.constants.F_OK, (err) => {
if (err) {
return res.status(404).send({ message: 'File not found!' });
}
res.download(filePath, filename, (err) => {
if (err) throw err;
});
});
});
// 启动服务器
const PORT = process.env.PORT || 3000;
app.listen(PORT, () => console.log(`Server started on port ${PORT}`));
通过以上步骤,你可以在Linux环境下使用Node.js和Express.js实现文件的上传和下载功能。根据实际需求,你可以进一步扩展功能,例如添加用户认证、文件列表展示、删除文件等。同时,务必注意安全性,确保应用在生产环境中的稳定和安全运行。