通过 Node js Express 访问签名 URL 的 AWS S3
Accessing AWS S3 Signed URL via Node js Express
我正在尝试使用在 Node JS 和 Express 中创建的包装器 API 访问签署 URL 的 AWS S3。
我正在重定向 url 以使用 nginx 调用节点 API。在节点 API 中,我在从节点 API 返回响应之前根据 S3 URL 返回的文件类型设置 'Content-Type' 响应 headers。
当我访问 URL 以通过包装器节点 API 获取 S3 中的文档时,我没有获得任何内容。如果是 PDF 文件,我会看到空白屏幕。
下面是我用来在节点包装器 API 中从 S3 获取文档并中继相同响应的代码块。
const request = require('request');
request(s3SignedURL, function (error, result, body) {
if (!error) {
res.header('Content-Type','application/pdf');
res.end(body);
} else {
res.status(500).send(error);
}
});
[编辑]
我将上传 S3 文件的详细信息存储在 table 中,并在有人尝试访问文档时使用该 table 获取文档。下面是使用的完整代码。
const S3 = new AWS.S3();
app.get("/getFile/*", function (req, res) {
var urlInfo = req.url;
var urlInfoList = urlInfo.split("/");
var accessCode = urlInfoList[2];
var accessID = urlInfoList[3];
if (!!accessID && !!accessCode) {
db.getFileInfo(accessCode, accessID).then(function (fileInfo) {
if (fileInfo.length > 0) {
var S3Options = {
Bucket: Bucketname,
Key: fileInfo[0].fileS3Key,
};
S3.getObject(S3Options, function (err, data) {
res.attachment(fileInfo[0].fileS3Key);
res.send(data.Body);
});
// request(fileInfo[0].fileS3URL).pipe(res.set('Content-Type', 'application/pdf').set('Content-Disposition', 'inline'));
} else {
res.status(404).send("<html><head><title>404 Not Found</title></head><body bgcolor=\"white\"><center><h1>404 Not Found</h1></center><hr></body></html>");
}
}, function (fileErr) {
console.log('fileErr');
console.log(fileErr);
res.status(404).send("<html><head><title>404 Not Found</title></head><body bgcolor=\"white\"><center><h1>404 Not Found</h1></center><hr></body></html>");
});
} else {
res.status(404).send("<html><head><title>404 Not Found</title></head><body bgcolor=\"white\"><center><h1>404 Not Found</h1></center><hr></body></html>");
}
});
这方面的任何帮助都会非常有用。
您得到一个空白屏幕,因为您还需要发送 Content-Disposition
参数。
顺便说一下,预签名 url 的目的是从公开暴露的环境(AWS 环境之外)获得对 s3 对象的临时访问权。您不必使用来自后端服务的预签名 URL 机制,您可以通过 SDK
安全地访问对象
const express = require('express');
const app = express();
const request = require('request');
app.get('/download-file', function (req, res) {
// sdk way
var s3 = new AWS.S3({});
var options = {
Bucket: 'my-bucket-name',
Key: file,
};
s3.getObject(options, function (err, data) {
res.setHeader('Content-disposition', `inline; filename="${filename}"`);
res.end(data.Body, 'binary');
});
// http way
request('https://s3-ap-southeast-2.amazonaws.com/my-bucket-name/mypdf.pdf')
.pipe(res.set('Content-Type', 'application/pdf').set('Content-Disposition', 'inline; filename="mypdf.pdf"'))
})
我正在尝试使用在 Node JS 和 Express 中创建的包装器 API 访问签署 URL 的 AWS S3。
我正在重定向 url 以使用 nginx 调用节点 API。在节点 API 中,我在从节点 API 返回响应之前根据 S3 URL 返回的文件类型设置 'Content-Type' 响应 headers。
当我访问 URL 以通过包装器节点 API 获取 S3 中的文档时,我没有获得任何内容。如果是 PDF 文件,我会看到空白屏幕。
下面是我用来在节点包装器 API 中从 S3 获取文档并中继相同响应的代码块。
const request = require('request');
request(s3SignedURL, function (error, result, body) {
if (!error) {
res.header('Content-Type','application/pdf');
res.end(body);
} else {
res.status(500).send(error);
}
});
[编辑]
我将上传 S3 文件的详细信息存储在 table 中,并在有人尝试访问文档时使用该 table 获取文档。下面是使用的完整代码。
const S3 = new AWS.S3();
app.get("/getFile/*", function (req, res) {
var urlInfo = req.url;
var urlInfoList = urlInfo.split("/");
var accessCode = urlInfoList[2];
var accessID = urlInfoList[3];
if (!!accessID && !!accessCode) {
db.getFileInfo(accessCode, accessID).then(function (fileInfo) {
if (fileInfo.length > 0) {
var S3Options = {
Bucket: Bucketname,
Key: fileInfo[0].fileS3Key,
};
S3.getObject(S3Options, function (err, data) {
res.attachment(fileInfo[0].fileS3Key);
res.send(data.Body);
});
// request(fileInfo[0].fileS3URL).pipe(res.set('Content-Type', 'application/pdf').set('Content-Disposition', 'inline'));
} else {
res.status(404).send("<html><head><title>404 Not Found</title></head><body bgcolor=\"white\"><center><h1>404 Not Found</h1></center><hr></body></html>");
}
}, function (fileErr) {
console.log('fileErr');
console.log(fileErr);
res.status(404).send("<html><head><title>404 Not Found</title></head><body bgcolor=\"white\"><center><h1>404 Not Found</h1></center><hr></body></html>");
});
} else {
res.status(404).send("<html><head><title>404 Not Found</title></head><body bgcolor=\"white\"><center><h1>404 Not Found</h1></center><hr></body></html>");
}
});
这方面的任何帮助都会非常有用。
您得到一个空白屏幕,因为您还需要发送 Content-Disposition
参数。
顺便说一下,预签名 url 的目的是从公开暴露的环境(AWS 环境之外)获得对 s3 对象的临时访问权。您不必使用来自后端服务的预签名 URL 机制,您可以通过 SDK
安全地访问对象const express = require('express');
const app = express();
const request = require('request');
app.get('/download-file', function (req, res) {
// sdk way
var s3 = new AWS.S3({});
var options = {
Bucket: 'my-bucket-name',
Key: file,
};
s3.getObject(options, function (err, data) {
res.setHeader('Content-disposition', `inline; filename="${filename}"`);
res.end(data.Body, 'binary');
});
// http way
request('https://s3-ap-southeast-2.amazonaws.com/my-bucket-name/mypdf.pdf')
.pipe(res.set('Content-Type', 'application/pdf').set('Content-Disposition', 'inline; filename="mypdf.pdf"'))
})