UNPKG

sqs-to-lambda-async

Version:
191 lines (156 loc) 6.29 kB
'use strict'; var _regenerator = require('babel-runtime/regenerator'); var _regenerator2 = _interopRequireDefault(_regenerator); var _asyncToGenerator2 = require('babel-runtime/helpers/asyncToGenerator'); var _asyncToGenerator3 = _interopRequireDefault(_asyncToGenerator2); var _lodash = require('lodash'); var _lodash2 = _interopRequireDefault(_lodash); var _awsSdk = require('aws-sdk'); var _awsSdk2 = _interopRequireDefault(_awsSdk); var _pForever = require('p-forever'); var _pForever2 = _interopRequireDefault(_pForever); var _pSettle = require('p-settle'); var _pSettle2 = _interopRequireDefault(_pSettle); function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } var debug = require('debug')('sqs-to-lambda-async'); var sqs = undefined; var lambda = undefined; function handleMessage() { var message = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {}; var kwargs = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {}; return new Promise(function (resolve, reject) { debug(`Incoming message: ${JSON.stringify(message)}`); var MessageFormatter = kwargs.MessageFormatter, FunctionName = kwargs.FunctionName, DeleteMessage = kwargs.DeleteMessage, QueueUrl = kwargs.QueueUrl; if (_lodash2.default.isEmpty(message)) { return resolve('Message is empty'); } if (typeof MessageFormatter !== 'function') { return reject('Message formatter is not a function.'); } if (typeof FunctionName !== 'string') { return reject('Function ARN not valid.'); } var Payload = JSON.stringify(MessageFormatter(message)); debug(`Invoking lambda ${FunctionName}`); return lambda.invoke({ InvocationType: 'Event', FunctionName, Payload }, function (err, res) { if (err) { return reject(err); } if (DeleteMessage) { return sqs.deleteMessage({ QueueUrl, ReceiptHandle: message.ReceiptHandle }, function (deleteMessageErr) { return deleteMessageErr ? reject(deleteMessageErr) : resolve(res); }); } return resolve(res); }); }); } function receiveMessages() { var kwargs = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {}; return new Promise(function (resolve) { var recieveArgs = _lodash2.default.chain(kwargs).pick(['MaxNumberOfMessages', 'QueueUrl', 'WaitTimeSeconds', 'VisibilityTimeout']).pickBy().value(); sqs.receiveMessage(recieveArgs, function (err, data) { var messages = _lodash2.default.isArray(data.Messages) ? data.Messages : []; (0, _pSettle2.default)(messages.map(function (msg) { return handleMessage(msg, kwargs); })).then(resolve); }); }); } function handleLambdaCallback(kwargs) { var values = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : []; var PostInvoke = kwargs.PostInvoke; if (_lodash2.default.isArray(values) && _lodash2.default.isFunction(PostInvoke)) { try { values.forEach(function () { var obj = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {}; return obj.isFulfilled ? PostInvoke(undefined, obj.value) : PostInvoke(obj.reason || new Error('Unknown lambda error.')); }); } catch (err) { _lodash2.default.noop(); } } } function createReader(kwargs) { debug(`Creating reader with args: ${JSON.stringify(kwargs)}`); var readerIndex = -1; return (0, _pForever2.default)(function (previousVal) { handleLambdaCallback(kwargs, previousVal); readerIndex++; return readerIndex < kwargs.NumberOfRuns ? receiveMessages(kwargs) : _pForever2.default.end; }, []); } function setupServices() { debug('Setting up AWS services'); sqs = new _awsSdk2.default.SQS(); lambda = new _awsSdk2.default.Lambda(); } module.exports = function () { var _ref = (0, _asyncToGenerator3.default)(_regenerator2.default.mark(function _callee() { var mapping = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : []; var mappingIsValid, readers; return _regenerator2.default.wrap(function _callee$(_context) { while (1) { switch (_context.prev = _context.next) { case 0: debug(`Initializing with mapping ${JSON.stringify(mapping)}`); _context.prev = 1; mappingIsValid = _lodash2.default.chain(mapping).map(function () { var obj = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {}; return _lodash2.default.every([obj.functionName, obj.queueUrl]); }).every().value(); if (!(!_lodash2.default.isArray(mapping) || !mapping.length || !mappingIsValid)) { _context.next = 5; break; } throw new Error(`Your sqs/lambda mapping object must be an array of objects like {functionName: foo, queueUrl: bar}, got ${JSON.stringify(mapping)}`); case 5: setupServices(); readers = mapping.map(function (obj) { var msgArgs = _lodash2.default.chain(obj).mapKeys(function (val, key) { return _lodash2.default.camelCase(key); }).defaults({ maxNumberOfMessages: 5, waitTimeSeconds: 5, messageFormatter: function messageFormatter(a) { return a; }, numberOfRuns: Infinity, deleteMessage: false, postInvoke: _lodash2.default.noop }).mapKeys(function (val, key) { return _lodash2.default.upperFirst(key); }).value(); return createReader(msgArgs); }); _context.next = 9; return Promise.all(readers); case 9: _context.next = 14; break; case 11: _context.prev = 11; _context.t0 = _context['catch'](1); throw _context.t0; case 14: case 'end': return _context.stop(); } } }, _callee, this, [[1, 11]]); })); function run() { return _ref.apply(this, arguments); } return run; }();