Atlassian ASAP authentication support (https://s2sauth.bitbucket.io/) (#565) (#566)

This commit is contained in:
Gerry Tan 2017-11-08 05:14:08 +11:00 committed by Gregory Schier
parent 9b9a033cd7
commit f67f220c6d
8 changed files with 451 additions and 38 deletions

View File

@ -147,6 +147,7 @@ export const AUTH_NTLM = 'ntlm';
export const AUTH_HAWK = 'hawk';
export const AUTH_AWS_IAM = 'iam';
export const AUTH_NETRC = 'netrc';
export const AUTH_ASAP = 'asap';
export const HAWK_ALGORITHM_SHA256 = 'sha256';
export const HAWK_ALGORITHM_SHA1 = 'sha1';
@ -160,7 +161,8 @@ const authTypesMap = {
[AUTH_OAUTH_2]: ['OAuth 2', 'OAuth 2.0'],
[AUTH_HAWK]: ['Hawk', 'Hawk'],
[AUTH_AWS_IAM]: ['AWS', 'AWS IAM v4'],
[AUTH_NETRC]: ['Netrc', 'Netrc File']
[AUTH_NETRC]: ['Netrc', 'Netrc File'],
[AUTH_ASAP]: ['ASAP', 'Atlassian ASAP']
};
export function getPreviewModeName (previewMode, useLong = false) {

View File

@ -1,6 +1,6 @@
// @flow
import type {BaseModel} from './index';
import {AUTH_BASIC, AUTH_DIGEST, AUTH_NONE, AUTH_NTLM, AUTH_OAUTH_1, AUTH_OAUTH_2, AUTH_HAWK, AUTH_AWS_IAM, AUTH_NETRC, CONTENT_TYPE_FILE, CONTENT_TYPE_FORM_DATA, CONTENT_TYPE_FORM_URLENCODED, CONTENT_TYPE_OTHER, getContentTypeFromHeaders, METHOD_GET, CONTENT_TYPE_GRAPHQL, CONTENT_TYPE_JSON, METHOD_POST, HAWK_ALGORITHM_SHA256} from '../common/constants';
import {AUTH_BASIC, AUTH_DIGEST, AUTH_NONE, AUTH_NTLM, AUTH_OAUTH_1, AUTH_OAUTH_2, AUTH_HAWK, AUTH_AWS_IAM, AUTH_NETRC, AUTH_ASAP, CONTENT_TYPE_FILE, CONTENT_TYPE_FORM_DATA, CONTENT_TYPE_FORM_URLENCODED, CONTENT_TYPE_OTHER, getContentTypeFromHeaders, METHOD_GET, CONTENT_TYPE_GRAPHQL, CONTENT_TYPE_JSON, METHOD_POST, HAWK_ALGORITHM_SHA256} from '../common/constants';
import * as db from '../common/database';
import {getContentTypeHeader} from '../common/misc';
import {buildFromParams, deconstructToParams} from '../common/querystring';
@ -137,6 +137,10 @@ export function newAuth (type: string, oldAuth: RequestAuthentication = {}): Req
case AUTH_HAWK:
return {type, algorithm: HAWK_ALGORITHM_SHA256};
// Atlassian ASAP
case AUTH_ASAP:
return {type, issuer: '', subject: '', audience: '', keyId: '', privateKey: ''};
// Types needing no defaults
default:
return {type};

View File

@ -1,9 +1,10 @@
// @flow
import {AUTH_BASIC, AUTH_BEARER, AUTH_HAWK, AUTH_OAUTH_1, AUTH_OAUTH_2} from '../common/constants';
import {AUTH_ASAP, AUTH_BASIC, AUTH_BEARER, AUTH_HAWK, AUTH_OAUTH_1, AUTH_OAUTH_2} from '../common/constants';
import {getBasicAuthHeader, getBearerAuthHeader} from '../common/misc';
import getOAuth2Token from './o-auth-2/get-token';
import getOAuth1Token from './o-auth-1/get-token';
import * as Hawk from 'hawk';
import jwtAuthentication from 'jwt-authentication';
import type {RequestAuthentication} from '../models/request';
type Header = {
@ -68,6 +69,33 @@ export async function getAuthHeader (
};
}
if (authentication.type === AUTH_ASAP) {
const {issuer, subject, audience, keyId, privateKey} = authentication;
const generator = jwtAuthentication.client.create();
const claims = {
iss: issuer,
sub: subject,
aud: audience
};
const options = {
privateKey,
kid: keyId
};
return new Promise((resolve, reject) => {
generator.generateAuthorizationHeader(claims, options, (error, headerValue) => {
if (error) {
reject(error);
} else {
resolve({
name: 'Authorization',
value: headerValue
});
}
});
});
}
return null;
}

View File

@ -6,7 +6,7 @@ import {trackEvent} from '../../../analytics';
import {showModal} from '../modals';
import AlertModal from '../modals/alert-modal';
import * as models from '../../../models';
import {AUTH_BASIC, AUTH_DIGEST, AUTH_BEARER, AUTH_NONE, AUTH_NTLM, AUTH_OAUTH_1, AUTH_OAUTH_2, AUTH_HAWK, AUTH_AWS_IAM, AUTH_NETRC, getAuthTypeName} from '../../../common/constants';
import {AUTH_BASIC, AUTH_DIGEST, AUTH_BEARER, AUTH_NONE, AUTH_NTLM, AUTH_OAUTH_1, AUTH_OAUTH_2, AUTH_HAWK, AUTH_AWS_IAM, AUTH_NETRC, AUTH_ASAP, getAuthTypeName} from '../../../common/constants';
@autobind
class AuthDropdown extends PureComponent {
@ -71,6 +71,7 @@ class AuthDropdown extends PureComponent {
{this.renderAuthType(AUTH_AWS_IAM)}
{this.renderAuthType(AUTH_NETRC)}
{this.renderAuthType(AUTH_HAWK)}
{this.renderAuthType(AUTH_ASAP)}
<DropdownDivider>Other</DropdownDivider>
{this.renderAuthType(AUTH_NONE, 'No Authentication')}
</Dropdown>

View File

@ -0,0 +1,155 @@
// @flow
import type {Request} from '../../../../models/request';
import * as React from 'react';
import autobind from 'autobind-decorator';
import OneLineEditor from '../../codemirror/one-line-editor';
import CodeEditor from '../../codemirror/code-editor';
import HelpTooltip from '../../help-tooltip';
type Props = {
request: Request,
handleRender: Function,
handleGetRenderContext: Function,
nunjucksPowerUserMode: boolean,
onChange: Function
};
@autobind
class AsapAuth extends React.PureComponent<Props> {
_handleChangeProperty (property: string, value: string | boolean): void {
const {request} = this.props;
const authentication = Object.assign({}, request.authentication, {[property]: value});
this.props.onChange(authentication);
}
renderAsapAuthenticationFields (): React.Node {
const asapIssuer = this.renderTextInput(
'Issuer (iss)',
'issuer',
'client-name',
(value) => this._handleChangeProperty('issuer', value)
);
const asapSubject = this.renderTextInput(
'Subject (sub)',
'subject',
'some-username',
(value) => this._handleChangeProperty('subject', value)
);
const asapAudience = this.renderTextInput(
'Audience (aud)',
'audience',
'resource-server-name',
(value) => this._handleChangeProperty('audience', value)
);
const asapKeyId = this.renderTextInput(
'Key ID (kid)',
'keyId',
'key-identifier',
(value) => this._handleChangeProperty('keyId', value)
);
const asapPrivateKey = this.renderPrivateKeyInput(
'Private Key',
'privateKey',
(value) => this._handleChangeProperty('privateKey', value)
);
return [asapIssuer, asapSubject, asapAudience, asapKeyId, asapPrivateKey];
}
renderTextInput (
label: string,
property: string,
placeholder: string,
onChange: Function
): React.Element<*> {
const { handleRender, handleGetRenderContext, request, nunjucksPowerUserMode } = this.props;
const id = label.replace(/ /g, '-');
return (
<tr key={id}>
<td className="pad-right no-wrap valign-middle">
<label htmlFor={id} className="label--small no-pad">
{label}
</label>
</td>
<td className="wide">
<div className="form-control form-control--underlined no-margin">
<OneLineEditor
id={id}
placeholder={placeholder}
onChange={onChange}
defaultValue={request.authentication[property] || ''}
nunjucksPowerUserMode={nunjucksPowerUserMode}
render={handleRender}
getRenderContext={handleGetRenderContext}
/>
</div>
</td>
</tr>
);
}
renderPrivateKeyInput (
label: string,
property: string,
onChange: Function
): React.Element<*> {
const { handleRender, handleGetRenderContext, request, nunjucksPowerUserMode } = this.props;
const id = label.replace(/ /g, '-');
const placeholderPrivateKey = '-----BEGIN RSA PRIVATE KEY-----\n' +
'MIIEpQIBAAKCAQEA39k9udklHnmkU0GtTLpnYtKk1l5txYmUD/cGI0bFd3HHOOLG\n' +
'mI0av55vMFEhxL7yrFrcL8pRKp0+pnOVStMDmbwsPE/pu9pf3uxD+m9/Flv89bUk\n' +
'mml+R3E8PwAYzkX0cr4yQTPN9PSSqy+d2+KrZ9QZmpc3tqltTbMVV93cxKCxfBrf\n' +
'jbiMIAVh7silDVY5+V46SJu8zY2kXOBBtlrE7/JoMiTURCkRjNIA8/sgSmRxBTdM\n' +
'313lKJM7NgxaGnREbP75U7ErfBvReJsf5p6h5+XXFirG7F2ntcqjUoR3M+opngp0\n' +
'CgffdGcsK7MmUUgAG7r05b0mljhI35t/0Y57MwIDAQABAoIBAQCH1rLohudJmROp\n' +
'Gl/qAewfQiiZlfATQavCDGuDGL1YAIme8a8GgApNYf2jWnidhiqJgRHBRor+yzFr\n' +
'cJV+wRTs/Szp6LXAgMmTkKMJ+9XXErUIUgwbl27Y3Rv/9ox1p5VRg+A=\n' +
'-----END RSA PRIVATE KEY-----';
return (
<tr key={id}>
<td className="pad-right pad-top-sm no-wrap valign-top">
<label htmlFor={id} className="label--small no-pad">
{label}
<HelpTooltip>Can also use single line data-uri format (e.g. obtained from asap-cli export-as-data-uri command), useful for saving as environment data</HelpTooltip>
</label>
</td>
<td className="wide">
<div className="form-control form-control--underlined form-control--tall no-margin">
<CodeEditor
id={id}
onChange={onChange}
defaultValue={request.authentication[property] || ''}
dynamicHeight={true}
hideLineNumbers={true}
lineWrapping={true}
placeholder={placeholderPrivateKey}
style={{height: 200}}
nunjucksPowerUserMode={nunjucksPowerUserMode}
render={handleRender}
getRenderContext={handleGetRenderContext}
/>
</div>
</td>
</tr>
);
}
render () {
const fields = this.renderAsapAuthenticationFields();
return (
<div className="pad">
<table>
<tbody>{fields}</tbody>
</table>
</div>
);
}
}
export default AsapAuth;

View File

@ -1,6 +1,6 @@
import React, {PureComponent} from 'react';
import PropTypes from 'prop-types';
import {AUTH_BASIC, AUTH_DIGEST, AUTH_BEARER, AUTH_NTLM, AUTH_OAUTH_1, AUTH_OAUTH_2, AUTH_AWS_IAM, AUTH_HAWK, AUTH_NETRC} from '../../../../common/constants';
import {AUTH_BASIC, AUTH_DIGEST, AUTH_BEARER, AUTH_NTLM, AUTH_OAUTH_1, AUTH_OAUTH_2, AUTH_AWS_IAM, AUTH_HAWK, AUTH_NETRC, AUTH_ASAP} from '../../../../common/constants';
import BasicAuth from './basic-auth';
import DigestAuth from './digest-auth';
import BearerAuth from './bearer-auth';
@ -10,6 +10,7 @@ import OAuth1Auth from './o-auth-1-auth';
import HawkAuth from './hawk-auth';
import AWSAuth from './aws-auth';
import NetrcAuth from './netrc-auth';
import AsapAuth from './asap-auth';
import autobind from 'autobind-decorator';
@autobind
@ -124,6 +125,16 @@ class AuthWrapper extends PureComponent {
return (
<NetrcAuth />
);
} else if (authentication.type === AUTH_ASAP) {
return (
<AsapAuth
request={request}
handleRender={handleRender}
handleGetRenderContext={handleGetRenderContext}
nunjucksPowerUserMode={nunjucksPowerUserMode}
onChange={onChange}
/>
);
} else {
return (
<div className="vertically-center text-center">

277
package-lock.json generated
View File

@ -4,12 +4,6 @@
"lockfileVersion": 1,
"requires": true,
"dependencies": {
"@types/node": {
"version": "7.0.46",
"resolved": "https://registry.npmjs.org/@types/node/-/node-7.0.46.tgz",
"integrity": "sha512-u+JAi1KtmaUoU/EHJkxoiuvzyo91FCE41Z9TZWWcOUU3P8oUdlDLdrGzCGWySPgbRMD17B0B+1aaJLYI9egQ6A==",
"dev": true
},
"7zip": {
"version": "0.0.6",
"resolved": "https://registry.npmjs.org/7zip/-/7zip-0.0.6.tgz",
@ -31,6 +25,22 @@
"dev": true,
"optional": true
},
"@types/node": {
"version": "7.0.46",
"resolved": "https://registry.npmjs.org/@types/node/-/node-7.0.46.tgz",
"integrity": "sha512-u+JAi1KtmaUoU/EHJkxoiuvzyo91FCE41Z9TZWWcOUU3P8oUdlDLdrGzCGWySPgbRMD17B0B+1aaJLYI9egQ6A==",
"dev": true
},
"JSONSelect": {
"version": "0.4.0",
"resolved": "https://registry.npmjs.org/JSONSelect/-/JSONSelect-0.4.0.tgz",
"integrity": "sha1-oI7cxn6z/L6Z7WMIVTRKDPKCu40="
},
"JSV": {
"version": "4.0.2",
"resolved": "https://registry.npmjs.org/JSV/-/JSV-4.0.2.tgz",
"integrity": "sha1-0Hf2glVx+CEy+d/67Vh7QCn+/1c="
},
"a-sync-waterfall": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/a-sync-waterfall/-/a-sync-waterfall-1.0.0.tgz",
@ -527,6 +537,14 @@
"resolved": "https://registry.npmjs.org/aws4/-/aws4-1.6.0.tgz",
"integrity": "sha1-g+9cqGCysy5KDe7e6MdxudtXRx4="
},
"axios": {
"version": "0.15.3",
"resolved": "https://registry.npmjs.org/axios/-/axios-0.15.3.tgz",
"integrity": "sha1-LJ1jiy4ZGgjqHWzJiOrda6W9wFM=",
"requires": {
"follow-redirects": "1.0.0"
}
},
"babel-cli": {
"version": "6.23.0",
"resolved": "https://registry.npmjs.org/babel-cli/-/babel-cli-6.23.0.tgz",
@ -1380,6 +1398,11 @@
"resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.2.0.tgz",
"integrity": "sha1-o5mS1yNYSBGYK+XikLtqU9hnAPE="
},
"base64url": {
"version": "2.0.0",
"resolved": "https://registry.npmjs.org/base64url/-/base64url-2.0.0.tgz",
"integrity": "sha1-6sFuA+oUOO/5Qj1puqNiYu0fcLs="
},
"batch": {
"version": "0.6.1",
"resolved": "https://registry.npmjs.org/batch/-/batch-0.6.1.tgz",
@ -1668,6 +1691,11 @@
"integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=",
"dev": true
},
"buffer-equal-constant-time": {
"version": "1.0.1",
"resolved": "https://registry.npmjs.org/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz",
"integrity": "sha1-+OcRMvf/5uAaXJaXpMbz5I1cyBk="
},
"buffer-shims": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/buffer-shims/-/buffer-shims-1.0.0.tgz",
@ -1756,6 +1784,14 @@
"resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz",
"integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw="
},
"catharsis": {
"version": "0.8.9",
"resolved": "https://registry.npmjs.org/catharsis/-/catharsis-0.8.9.tgz",
"integrity": "sha1-mMyJDKZS3S7w5ws3klMQ/56Q/Is=",
"requires": {
"underscore-contrib": "0.3.0"
}
},
"center-align": {
"version": "0.1.3",
"resolved": "https://registry.npmjs.org/center-align/-/center-align-0.1.3.tgz",
@ -2485,6 +2521,11 @@
}
}
},
"crypto": {
"version": "0.0.3",
"resolved": "https://registry.npmjs.org/crypto/-/crypto-0.0.3.tgz",
"integrity": "sha1-RwqBuGvkxe4XrMggeh9TFa4g27A="
},
"crypto-browserify": {
"version": "3.11.1",
"resolved": "https://registry.npmjs.org/crypto-browserify/-/crypto-browserify-3.11.1.tgz",
@ -2930,6 +2971,11 @@
"is-obj": "1.0.1"
}
},
"ducktype": {
"version": "1.1.0",
"resolved": "https://registry.npmjs.org/ducktype/-/ducktype-1.1.0.tgz",
"integrity": "sha1-owrBwDIJFrDCRl19HKj5Vo59kYg="
},
"duplexer": {
"version": "0.1.1",
"resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.1.tgz",
@ -2990,6 +3036,15 @@
"jsbn": "0.1.1"
}
},
"ecdsa-sig-formatter": {
"version": "1.0.9",
"resolved": "https://registry.npmjs.org/ecdsa-sig-formatter/-/ecdsa-sig-formatter-1.0.9.tgz",
"integrity": "sha1-S8kmJ07Dtau1AW5+HWCSGsJisqE=",
"requires": {
"base64url": "2.0.0",
"safe-buffer": "5.0.1"
}
},
"ee-first": {
"version": "1.1.1",
"resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz",
@ -4307,6 +4362,14 @@
"integrity": "sha512-jMImubdtZxLafc0EXZVCtOIJVknqGrruClPbol6kZ1oVQioMWu95iiKQMaSDJ78F4TjYuZCbqsdZ4LSI7TSsjA==",
"dev": true
},
"follow-redirects": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.0.0.tgz",
"integrity": "sha1-jjQpjL0uF28lTv/sdaHHjMhJ/Tc=",
"requires": {
"debug": "2.6.8"
}
},
"for-in": {
"version": "1.0.2",
"resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz",
@ -5113,10 +5176,6 @@
}
}
},
"string_decoder": {
"version": "0.10.31",
"bundled": true
},
"string-width": {
"version": "1.0.2",
"bundled": true,
@ -5126,6 +5185,10 @@
"strip-ansi": "3.0.1"
}
},
"string_decoder": {
"version": "0.10.31",
"bundled": true
},
"stringstream": {
"version": "0.0.5",
"bundled": true,
@ -6697,10 +6760,6 @@
}
}
},
"string_decoder": {
"version": "0.10.31",
"bundled": true
},
"string-width": {
"version": "1.0.2",
"bundled": true,
@ -6710,6 +6769,10 @@
"strip-ansi": "3.0.1"
}
},
"string_decoder": {
"version": "0.10.31",
"bundled": true
},
"stringstream": {
"version": "0.0.5",
"bundled": true
@ -7590,12 +7653,12 @@
"resolved": "https://registry.npmjs.org/jison/-/jison-0.4.13.tgz",
"integrity": "sha1-kEFwfWIkE2f1iDRTK58ZwsNvrHg=",
"requires": {
"JSONSelect": "0.4.0",
"cjson": "0.2.1",
"ebnf-parser": "0.1.10",
"escodegen": "0.0.21",
"esprima": "1.0.4",
"jison-lex": "0.2.1",
"JSONSelect": "0.4.0",
"lex-parser": "0.1.4",
"nomnom": "1.5.2"
},
@ -7690,11 +7753,63 @@
}
}
},
"js2xmlparser": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/js2xmlparser/-/js2xmlparser-3.0.0.tgz",
"integrity": "sha1-P7YOqgicVED5MZ9RdgzNB+JJlzM=",
"requires": {
"xmlcreate": "1.0.2"
}
},
"jsbn": {
"version": "0.1.1",
"resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz",
"integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM="
},
"jsdoc": {
"version": "3.5.5",
"resolved": "https://registry.npmjs.org/jsdoc/-/jsdoc-3.5.5.tgz",
"integrity": "sha512-6PxB65TAU4WO0Wzyr/4/YhlGovXl0EVYfpKbpSroSj0qBxT4/xod/l40Opkm38dRHRdQgdeY836M0uVnJQG7kg==",
"requires": {
"babylon": "7.0.0-beta.19",
"bluebird": "3.5.1",
"catharsis": "0.8.9",
"escape-string-regexp": "1.0.5",
"js2xmlparser": "3.0.0",
"klaw": "2.0.0",
"marked": "0.3.6",
"mkdirp": "0.5.1",
"requizzle": "0.2.1",
"strip-json-comments": "2.0.1",
"taffydb": "2.6.2",
"underscore": "1.8.3"
},
"dependencies": {
"babylon": {
"version": "7.0.0-beta.19",
"resolved": "https://registry.npmjs.org/babylon/-/babylon-7.0.0-beta.19.tgz",
"integrity": "sha512-Vg0C9s/REX6/WIXN37UKpv5ZhRi6A4pjHlpkE34+8/a6c2W1Q692n3hmc+SZG5lKRnaExLUbxtJ1SVT+KaCQ/A=="
},
"bluebird": {
"version": "3.5.1",
"resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.5.1.tgz",
"integrity": "sha512-MKiLiV+I1AA596t9w1sQJ8jkiSr5+ZKi0WKrYGUn6d1Fx+Ij4tIj+m2WMQSGczs5jZVxV339chE8iwk6F64wjA=="
},
"klaw": {
"version": "2.0.0",
"resolved": "https://registry.npmjs.org/klaw/-/klaw-2.0.0.tgz",
"integrity": "sha1-WcEo4Nxc5BAgEVEZTuucv4WGUPY=",
"requires": {
"graceful-fs": "4.1.11"
}
},
"underscore": {
"version": "1.8.3",
"resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz",
"integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI="
}
}
},
"jsdom": {
"version": "9.12.0",
"resolved": "https://registry.npmjs.org/jsdom/-/jsdom-9.12.0.tgz",
@ -7961,10 +8076,22 @@
"resolved": "https://registry.npmjs.org/jsonpointer/-/jsonpointer-4.0.1.tgz",
"integrity": "sha1-T9kss04OnbPInIYi7PUfm5eMbLk="
},
"JSONSelect": {
"version": "0.4.0",
"resolved": "https://registry.npmjs.org/JSONSelect/-/JSONSelect-0.4.0.tgz",
"integrity": "sha1-oI7cxn6z/L6Z7WMIVTRKDPKCu40="
"jsonwebtoken": {
"version": "5.7.0",
"resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-5.7.0.tgz",
"integrity": "sha1-HJD5qGzlt0j1+XnBK3BAK0r83bQ=",
"requires": {
"jws": "3.1.4",
"ms": "0.7.3",
"xtend": "4.0.1"
},
"dependencies": {
"ms": {
"version": "0.7.3",
"resolved": "https://registry.npmjs.org/ms/-/ms-0.7.3.tgz",
"integrity": "sha1-cIFVpeROM/X9D8U+gdDUCpG+H/8="
}
}
},
"jsprim": {
"version": "1.4.0",
@ -8009,11 +8136,6 @@
}
}
},
"JSV": {
"version": "4.0.2",
"resolved": "https://registry.npmjs.org/JSV/-/JSV-4.0.2.tgz",
"integrity": "sha1-0Hf2glVx+CEy+d/67Vh7QCn+/1c="
},
"jsx-ast-utils": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/jsx-ast-utils/-/jsx-ast-utils-2.0.1.tgz",
@ -8023,6 +8145,55 @@
"array-includes": "3.0.3"
}
},
"jwa": {
"version": "1.1.5",
"resolved": "https://registry.npmjs.org/jwa/-/jwa-1.1.5.tgz",
"integrity": "sha1-oFUs4CIHQs1S4VN3SjKQXDDnVuU=",
"requires": {
"base64url": "2.0.0",
"buffer-equal-constant-time": "1.0.1",
"ecdsa-sig-formatter": "1.0.9",
"safe-buffer": "5.0.1"
}
},
"jws": {
"version": "3.1.4",
"resolved": "https://registry.npmjs.org/jws/-/jws-3.1.4.tgz",
"integrity": "sha1-+ei5M46KhHJ31kRLFGT2GIDgUKI=",
"requires": {
"base64url": "2.0.0",
"jwa": "1.1.5",
"safe-buffer": "5.0.1"
}
},
"jwt-authentication": {
"version": "0.3.3",
"resolved": "https://registry.npmjs.org/jwt-authentication/-/jwt-authentication-0.3.3.tgz",
"integrity": "sha512-v76wJz9evqOAoDFHC7sWpOSY6701QwlH662yzOPOyHfTpNSWUD/c+rYtRr72jFO2XsVO1BDfD9YsdAuXfMf0JA==",
"requires": {
"axios": "0.15.3",
"crypto": "0.0.3",
"ducktype": "1.1.0",
"jsdoc": "3.5.5",
"jsonwebtoken": "5.7.0",
"lodash": "3.10.1",
"node-cache": "3.2.1",
"node-forge": "0.6.49",
"q": "1.5.0"
},
"dependencies": {
"lodash": {
"version": "3.10.1",
"resolved": "https://registry.npmjs.org/lodash/-/lodash-3.10.1.tgz",
"integrity": "sha1-W/Rejkm6QYnhfUgnid/RW9FAt7Y="
},
"node-forge": {
"version": "0.6.49",
"resolved": "https://registry.npmjs.org/node-forge/-/node-forge-0.6.49.tgz",
"integrity": "sha1-8e6V1ddGI5OP4Z1piqWibVTS9g8="
}
}
},
"kind-of": {
"version": "3.2.2",
"resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz",
@ -8749,6 +8920,22 @@
"integrity": "sha512-AbW35CPRE4vdieOse46V+16dKispLNv3PQwgqlcfg7GQeQHcLu3gvp3fbU2gTh7d8NfGjp5CJh+j4Hpyb0XzaA==",
"dev": true
},
"node-cache": {
"version": "3.2.1",
"resolved": "https://registry.npmjs.org/node-cache/-/node-cache-3.2.1.tgz",
"integrity": "sha1-p5WNMqikLZEZziWYZWfqLF+WZ3M=",
"requires": {
"clone": "1.0.2",
"lodash": "4.17.4"
},
"dependencies": {
"clone": {
"version": "1.0.2",
"resolved": "https://registry.npmjs.org/clone/-/clone-1.0.2.tgz",
"integrity": "sha1-Jgt6meux7f4kdTgXX3gyQ8sZ0Uk="
}
}
},
"node-emoji": {
"version": "1.5.1",
"resolved": "https://registry.npmjs.org/node-emoji/-/node-emoji-1.5.1.tgz",
@ -10214,8 +10401,7 @@
"q": {
"version": "1.5.0",
"resolved": "https://registry.npmjs.org/q/-/q-1.5.0.tgz",
"integrity": "sha1-3QG6ydBtMObyGa7LglPunr3DCPE=",
"dev": true
"integrity": "sha1-3QG6ydBtMObyGa7LglPunr3DCPE="
},
"qs": {
"version": "6.4.0",
@ -11000,6 +11186,14 @@
"integrity": "sha1-kl0mAdOaxIXgkc8NpcbmlNw9yv8=",
"dev": true
},
"requizzle": {
"version": "0.2.1",
"resolved": "https://registry.npmjs.org/requizzle/-/requizzle-0.2.1.tgz",
"integrity": "sha1-aUPDUwxNmn5G8c3dUcFY/GcM294=",
"requires": {
"underscore": "1.6.0"
}
},
"reselect": {
"version": "3.0.1",
"resolved": "https://registry.npmjs.org/reselect/-/reselect-3.0.1.tgz",
@ -11758,11 +11952,6 @@
"integrity": "sha1-J5siXfHVgrH1TmWt3UNS4Y+qBxM=",
"dev": true
},
"string_decoder": {
"version": "0.10.31",
"resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz",
"integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ="
},
"string-length": {
"version": "1.0.1",
"resolved": "https://registry.npmjs.org/string-length/-/string-length-1.0.1.tgz",
@ -11788,6 +11977,11 @@
"integrity": "sha1-aybpvTr8qnvjtCabUm3huCAArHg=",
"dev": true
},
"string_decoder": {
"version": "0.10.31",
"resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz",
"integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ="
},
"stringstream": {
"version": "0.0.5",
"resolved": "https://registry.npmjs.org/stringstream/-/stringstream-0.0.5.tgz",
@ -11828,8 +12022,7 @@
"strip-json-comments": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz",
"integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=",
"dev": true
"integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo="
},
"style-loader": {
"version": "0.13.2",
@ -11934,6 +12127,11 @@
}
}
},
"taffydb": {
"version": "2.6.2",
"resolved": "https://registry.npmjs.org/taffydb/-/taffydb-2.6.2.tgz",
"integrity": "sha1-fLy2S1oUG2ou/CxdLGe04VCyomg="
},
"tapable": {
"version": "0.2.8",
"resolved": "https://registry.npmjs.org/tapable/-/tapable-0.2.8.tgz",
@ -12321,6 +12519,14 @@
"resolved": "https://registry.npmjs.org/underscore/-/underscore-1.6.0.tgz",
"integrity": "sha1-izixDKze9jM3uLJOT/htRa6lKag="
},
"underscore-contrib": {
"version": "0.3.0",
"resolved": "https://registry.npmjs.org/underscore-contrib/-/underscore-contrib-0.3.0.tgz",
"integrity": "sha1-ZltmwkeD+PorGMn4y7Dix9SMJsc=",
"requires": {
"underscore": "1.6.0"
}
},
"uniq": {
"version": "1.0.1",
"resolved": "https://registry.npmjs.org/uniq/-/uniq-1.0.1.tgz",
@ -13453,6 +13659,11 @@
"integrity": "sha1-aSSGc0ELS6QuGmE2VR0pIjNap3M=",
"dev": true
},
"xmlcreate": {
"version": "1.0.2",
"resolved": "https://registry.npmjs.org/xmlcreate/-/xmlcreate-1.0.2.tgz",
"integrity": "sha1-+mv3YqYKQT+z3Y9LA8WyaSONMI8="
},
"xmldom": {
"version": "0.1.22",
"resolved": "https://registry.npmjs.org/xmldom/-/xmldom-0.1.22.tgz",

View File

@ -143,6 +143,7 @@
"insomnia-node-libcurl": "^1.2.3",
"jsonlint": "^1.6.2",
"jsonpath": "^0.2.12",
"jwt-authentication": "^0.3.3",
"marked": "^0.3.6",
"mime-types": "^2.1.14",
"mkdirp": "^0.5.1",