Как вы получаете доступ к телу сообщения Amazon SNS с помощью Express/Node.js
Сейчас я перестраиваю приложение PHP в Node.js поверх Express.
Одна часть приложения - это URL-адрес обратного вызова, на который отправлено уведомление об анонсах Amazon.
Тело POST из SNS в настоящее время читается следующим образом в PHP (который работает):
$notification = json_decode(file_get_contents('php://input'));
В Express я пробовал следующее:
app.post('/notification/url', function(req, res) {
console.log(req.body);
});
Однако, наблюдая за консолью, это только регистрируется при создании сообщения:
{}
Итак, чтобы повторить вопрос: как вы получаете доступ к телу сообщения Amazon SNS с помощью Express/ Node.js
Ответы
Ответ 1
Другой подход - исправить заголовок Content-Type.
Вот код промежуточного кода для этого:
exports.overrideContentType = function(){
return function(req, res, next) {
if (req.headers['x-amz-sns-message-type']) {
req.headers['content-type'] = 'application/json;charset=UTF-8';
}
next();
};
}
Это предполагает наличие файла с именем util.js, расположенного в корневом каталоге проекта, с помощью:
util = require('./util');
в app.js и вызывается с включением:
app.use(util.overrideContentType());
перед
app.use(express.bodyParser());
в файле app.js. Это позволяет bodyParser() правильно анализировать тело...
Меньше навязчивый, и вы можете затем нормально обращаться к req.body.
Ответ 2
Это основано на ответе AlexGad. В частности, этот комментарий:
Стандартный экспресс-парсер будет обрабатывать только приложения /json, application/x-www-form-encoded и multipart/form-data. Я добавил код выше, чтобы разместить его перед вашим парсером.
app.post('/notification/url', function(req, res) {
var bodyarr = []
req.on('data', function(chunk){
bodyarr.push(chunk);
})
req.on('end', function(){
console.log( bodyarr.join('') )
})
})
Ответ 3
Взгляните на AWS Node.js SDK - он может получить доступ ко всем AWS конечных точек обслуживания.
var sns = new AWS.SNS();
// subscribe
sns.subscribe({topic: "topic", Protocol: "https"}, function (err, data) {
if (err) {
console.log(err); // an error occurred
} else {
console.log(data); // successful response - the body should be in the data
}
});
// publish example
sns.publish({topic: "topic", message: "my message"}, function (err, data) {
if (err) {
console.log(err); // an error occurred
} else {
console.log(data); // successful response - the body should be in the data
}
});
EDIT: проблема заключается в том, что стандартный синтаксический анализатор тела не обрабатывает plain/text, который SNS отправляет как тип содержимого. Вот код для извлечения необработанного тела. Поместите его перед парсером тела:
app.use(function(req, res, next) {
var d= '';
req.setEncoding('utf8');
req.on('d', function(chunk) {
d+= chunk;
});
req.on('end', function() {
req.rawBody = d;
next();
});
});
Затем вы можете использовать:
JSON.stringify(req.rawBody));
в вашем маршруте, чтобы создать объект javascript и соответствующим образом работать с сообщением SNS.
Вы также можете изменить синтаксический анализатор тела для обработки текста/простого текста, но это не отличная идея для изменения промежуточного программного обеспечения. Просто используйте приведенный выше код.