parrot-middleware
Advanced tools
Comparing version 3.1.0 to 4.0.1
@@ -1,2 +0,2 @@ | ||
'use strict'; | ||
"use strict"; | ||
@@ -8,20 +8,29 @@ Object.defineProperty(exports, "__esModule", { | ||
var _express = require('express'); | ||
var _express = require("express"); | ||
var _bodyParser = require('body-parser'); | ||
var _bodyParser = _interopRequireDefault(require("body-parser")); | ||
var _bodyParser2 = _interopRequireDefault(_bodyParser); | ||
var _ParrotMiddleware = _interopRequireDefault(require("./ParrotMiddleware")); | ||
var _ParrotMiddleware = require('./ParrotMiddleware'); | ||
var _ParrotMiddleware2 = _interopRequireDefault(_ParrotMiddleware); | ||
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } | ||
/* | ||
* Copyright (c) 2018 American Express Travel Related Services Company, Inc. | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except | ||
* in compliance with the License. You may obtain a copy of the License at | ||
* | ||
* http://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software distributed under the License | ||
* is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express | ||
* or implied. See the License for the specific language governing permissions and limitations under | ||
* the License. | ||
*/ | ||
function parrot(scenarios) { | ||
var parrotMiddleware = new _ParrotMiddleware2.default(scenarios); | ||
var parrotMiddleware = new _ParrotMiddleware.default(scenarios); | ||
var jsonParser = _bodyParser2.default.json(); | ||
var jsonParser = _bodyParser.default.json(); | ||
var parrotRouter = (0, _express.Router)(); | ||
parrotRouter.post('/parrot/scenario', function (req, res) { | ||
@@ -31,26 +40,9 @@ parrotMiddleware.setActiveScenario(req.body.scenario); | ||
}); | ||
parrotRouter.get('/parrot/scenario', function (req, res) { | ||
res.json(parrotMiddleware.getActiveScenario()); | ||
}); | ||
parrotRouter.get('/parrot/scenarios', function (req, res) { | ||
res.json(parrotMiddleware.getScenarios()); | ||
}); | ||
return [jsonParser, parrotRouter, parrotMiddleware.resolve]; | ||
} /* | ||
* Copyright (c) 2018 American Express Travel Related Services Company, Inc. | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except | ||
* in compliance with the License. You may obtain a copy of the License at | ||
* | ||
* http://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software distributed under the License | ||
* is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express | ||
* or implied. See the License for the specific language governing permissions and limitations under | ||
* the License. | ||
*/ | ||
module.exports = exports['default']; | ||
} |
@@ -1,2 +0,2 @@ | ||
'use strict'; | ||
"use strict"; | ||
@@ -6,50 +6,53 @@ Object.defineProperty(exports, "__esModule", { | ||
}); | ||
exports.default = void 0; | ||
var _typeof2 = require('babel-runtime/helpers/typeof'); | ||
var _parrotCore = _interopRequireDefault(require("parrot-core")); | ||
var _typeof3 = _interopRequireDefault(_typeof2); | ||
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } | ||
var _getPrototypeOf = require('babel-runtime/core-js/object/get-prototype-of'); | ||
function _typeof(obj) { if (typeof Symbol === "function" && typeof Symbol.iterator === "symbol") { _typeof = function _typeof(obj) { return typeof obj; }; } else { _typeof = function _typeof(obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; }; } return _typeof(obj); } | ||
var _getPrototypeOf2 = _interopRequireDefault(_getPrototypeOf); | ||
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } | ||
var _classCallCheck2 = require('babel-runtime/helpers/classCallCheck'); | ||
function _possibleConstructorReturn(self, call) { if (call && (_typeof(call) === "object" || typeof call === "function")) { return call; } return _assertThisInitialized(self); } | ||
var _classCallCheck3 = _interopRequireDefault(_classCallCheck2); | ||
function _getPrototypeOf(o) { _getPrototypeOf = Object.setPrototypeOf ? Object.getPrototypeOf : function _getPrototypeOf(o) { return o.__proto__ || Object.getPrototypeOf(o); }; return _getPrototypeOf(o); } | ||
var _possibleConstructorReturn2 = require('babel-runtime/helpers/possibleConstructorReturn'); | ||
function _assertThisInitialized(self) { if (self === void 0) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return self; } | ||
var _possibleConstructorReturn3 = _interopRequireDefault(_possibleConstructorReturn2); | ||
function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function"); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, writable: true, configurable: true } }); if (superClass) _setPrototypeOf(subClass, superClass); } | ||
var _inherits2 = require('babel-runtime/helpers/inherits'); | ||
function _setPrototypeOf(o, p) { _setPrototypeOf = Object.setPrototypeOf || function _setPrototypeOf(o, p) { o.__proto__ = p; return o; }; return _setPrototypeOf(o, p); } | ||
var _inherits3 = _interopRequireDefault(_inherits2); | ||
function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } | ||
var _parrotCore = require('parrot-core'); | ||
var ParrotMiddleware = | ||
/*#__PURE__*/ | ||
function (_Parrot) { | ||
_inherits(ParrotMiddleware, _Parrot); | ||
var _parrotCore2 = _interopRequireDefault(_parrotCore); | ||
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } | ||
var ParrotMiddleware = function (_Parrot) { | ||
(0, _inherits3.default)(ParrotMiddleware, _Parrot); | ||
function ParrotMiddleware() { | ||
var _ref; | ||
var _getPrototypeOf2; | ||
var _temp, _this, _ret; | ||
var _this; | ||
(0, _classCallCheck3.default)(this, ParrotMiddleware); | ||
_classCallCheck(this, ParrotMiddleware); | ||
for (var _len = arguments.length, args = Array(_len), _key = 0; _key < _len; _key++) { | ||
for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) { | ||
args[_key] = arguments[_key]; | ||
} | ||
return _ret = (_temp = (_this = (0, _possibleConstructorReturn3.default)(this, (_ref = ParrotMiddleware.__proto__ || (0, _getPrototypeOf2.default)(ParrotMiddleware)).call.apply(_ref, [this].concat(args))), _this), _this.normalizeRequest = function (req) { | ||
_this = _possibleConstructorReturn(this, (_getPrototypeOf2 = _getPrototypeOf(ParrotMiddleware)).call.apply(_getPrototypeOf2, [this].concat(args))); | ||
_defineProperty(_assertThisInitialized(_this), "normalizeRequest", function (req) { | ||
return req; | ||
}, _this.resolver = function (req, res, next) { | ||
}); | ||
_defineProperty(_assertThisInitialized(_this), "resolver", function (req, res, next) { | ||
return function (response) { | ||
if (res.headersSent) { | ||
return; | ||
} else if (!response) { | ||
} | ||
if (!response) { | ||
next(); | ||
@@ -61,6 +64,5 @@ return; | ||
status = response.status; | ||
res.status(status); | ||
if ((typeof body === 'undefined' ? 'undefined' : (0, _typeof3.default)(body)) === 'object') { | ||
if (_typeof(body) === 'object') { | ||
res.json(body); | ||
@@ -73,21 +75,11 @@ } else if (typeof body === 'undefined') { | ||
}; | ||
}, _temp), (0, _possibleConstructorReturn3.default)(_this, _ret); | ||
}); | ||
return _this; | ||
} | ||
return ParrotMiddleware; | ||
}(_parrotCore2.default); /* | ||
* Copyright (c) 2018 American Express Travel Related Services Company, Inc. | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except | ||
* in compliance with the License. You may obtain a copy of the License at | ||
* | ||
* http://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software distributed under the License | ||
* is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express | ||
* or implied. See the License for the specific language governing permissions and limitations under | ||
* the License. | ||
*/ | ||
}(_parrotCore.default); | ||
exports.default = ParrotMiddleware; | ||
module.exports = exports['default']; | ||
var _default = ParrotMiddleware; | ||
exports.default = _default; |
{ | ||
"name": "parrot-middleware", | ||
"version": "3.1.0", | ||
"version": "4.0.1", | ||
"contributors": [ | ||
@@ -23,11 +23,13 @@ "Jack Cross <jack.cross1@aexp.com>", | ||
"dependencies": { | ||
"babel-runtime": "^6.0.0", | ||
"body-parser": "^1.15.2", | ||
"express": "^4.16.2", | ||
"parrot-core": "^3.1.0" | ||
"parrot-core": "^4.0.1" | ||
}, | ||
"devDependencies": { | ||
"babel-cli": "^6.24.1", | ||
"rimraf": "^2.2.8" | ||
} | ||
"@babel/cli": "^7.8.4", | ||
"@babel/core": "^7.7.7", | ||
"babel-preset-amex": "^3.3.0", | ||
"rimraf": "^3.0.0" | ||
}, | ||
"gitHead": "05e11da9241f5737ada24cfeb613f4f98e2abb89" | ||
} |
156
README.md
@@ -5,5 +5,57 @@ # parrot-middleware | ||
Given a collection of Parrot scenarios which each have a list of request and response pairs, the parrot middleware will intercept the `request`s that match the paths in the active scenario. The middleware will also expose 3 additional routes which are detailed below: `GET /parrot/scenario`, `POST /parrot/scenario`, `GET /parrot/scenarios`. | ||
## Example | ||
Let's walk through how to set up some scenarios using the parrot-middleware. | ||
### Define your scenarios | ||
Add a file to the root of your project called [`scenarios.js`](/americanexpress/parrot/blob/master/SCENARIOS.md): | ||
```js | ||
// scenarios.js | ||
const scenarios = { | ||
'has one ship': [ | ||
{ | ||
request: '/ship_log', | ||
response: { | ||
body: [{ name: 'The Jolly Roger', captain: 'Captain Hook' }], | ||
}, | ||
}, | ||
], | ||
'has more ships': [ | ||
{ | ||
request: '/ship_log', | ||
response: { | ||
body: [ | ||
{ name: 'The Jolly Roger', captain: 'Captain Hook' }, | ||
{ name: 'The Black Pearl', captain: 'Jack Sparrow' }, | ||
{ name: 'Flying Dutchman', captain: 'Davy Jones' }, | ||
{ name: 'The Wanderer', captain: 'Captain Ron' }, | ||
], | ||
}, | ||
}, | ||
], | ||
'has a server error': [ | ||
{ | ||
request: '/ship_log', | ||
response: { | ||
status: 500, | ||
}, | ||
}, | ||
], | ||
}; | ||
export default scenarios; | ||
``` | ||
This file has three scenarios: `has one ship`, `has more ships`, and `has a server error`. Each scenario is mocking a single request: `/ship_log`. This means that depending on which scenario is active, hitting `/ship_log` will return different responses. | ||
### Providing the middleware | ||
Now let's create a tiny web server. Add a file named `server.js` to the root of your project. Make sure that you `npm install express parrot-middleware` before running `server.js`: | ||
```js | ||
// server.js | ||
import express from 'express'; | ||
@@ -17,17 +69,105 @@ import parrot from 'parrot-middleware'; | ||
app.listen(3000); | ||
app.listen(3001); | ||
``` | ||
Once the server is running, the following endpoints are exposed to interact with your scenarios: | ||
### Setting the active scenario | ||
### GET `/parrot/scenario` | ||
Let's get our server running. Run `node server.js` from the command line, which will spin up our tiny web server on `http://localhost:3001`. | ||
Responds with the name of the currently active scenario. | ||
Now that our server is running, we can set the active scenario by sending a POST request to `http://localhost:3001/parrot/scenario` with a JSON payload that contains a single key/value pair `"scenario": "<scenario name>"`. Let's activate one of our scenarios: | ||
### POST `/parrot/scenario` | ||
``` | ||
Sets the currently active scenario. | ||
POST http://localhost:3001/parrot/scenario | ||
Content-Type: application/json | ||
### GET `/parrot/scenarios` | ||
{ | ||
"scenario": "has one ship" | ||
} | ||
Responds with an array of scenario objects. | ||
``` | ||
We can verify that the active scenario is now `has one ship` by simply submitting a GET request to the same URL: http://localhost:3001/parrot/scenario. | ||
Now that `"has one ship"` is the active scenario, navigating to http://localhost:3001/ship_log will return `[{ name: 'The Jolly Roger', captain: 'Captain Hook' }]`. | ||
Try setting the active scenario to `has more ships` and see if you get the expected response in our scenarios! | ||
### Inspect scenarios | ||
If you'd like to see exactly how the scenarios are parsed and view more details as to what the expected response will be, you can send a GET request to http://localhost:3001/parrot/scenarios, which for us would return: | ||
```js | ||
[ | ||
{ | ||
name: 'has one ship', | ||
mocks: [ | ||
{ | ||
request: { | ||
path: '/ship_log', | ||
method: 'GET', | ||
}, | ||
response: { | ||
status: 200, | ||
body: [ | ||
{ | ||
name: 'The Jolly Roger', | ||
captain: 'Captain Hook', | ||
}, | ||
], | ||
}, | ||
}, | ||
], | ||
}, | ||
{ | ||
name: 'has more ships', | ||
mocks: [ | ||
{ | ||
request: { | ||
path: '/ship_log', | ||
method: 'GET', | ||
}, | ||
response: { | ||
status: 200, | ||
body: [ | ||
{ | ||
name: 'The Jolly Roger', | ||
captain: 'Captain Hook', | ||
}, | ||
{ | ||
name: 'The Black Pearl', | ||
captain: 'Jack Sparrow', | ||
}, | ||
{ | ||
name: 'Flying Dutchman', | ||
captain: 'Davy Jones', | ||
}, | ||
{ | ||
name: 'The Wanderer', | ||
captain: 'Captain Ron', | ||
}, | ||
], | ||
}, | ||
}, | ||
], | ||
}, | ||
{ | ||
name: 'has a server error', | ||
mocks: [ | ||
{ | ||
request: { | ||
path: '/ship_log', | ||
method: 'GET', | ||
}, | ||
response: { | ||
status: 500, | ||
}, | ||
}, | ||
], | ||
}, | ||
]; | ||
``` | ||
## Using Scenarios | ||
For ease of use, you may want to check out [the Parrot Devtool Chrome Plugin](https://chrome.google.com/webstore/detail/parrot-devtools/jckchajdleibnohnphddbiglgpjpbffn), which will provide an easy to use interface for interacting with the endpoints above. |
New author
Supply chain riskA new npm collaborator published a version of the package for the first time. New collaborators are usually benign additions to a project, but do indicate a change to the security surface area of a package.
Found 1 instance in 1 package
21104
3
172
4
95
1
+ Added@babel/runtime@7.26.9(transitive)
+ Addedparrot-core@4.1.1(transitive)
+ Addedregenerator-runtime@0.14.1(transitive)
- Removedbabel-runtime@^6.0.0
- Removedbabel-runtime@6.26.0(transitive)
- Removedcore-js@2.6.12(transitive)
- Removedparrot-core@3.1.0(transitive)
- Removedregenerator-runtime@0.11.1(transitive)
Updatedparrot-core@^4.0.1