insomnia/packages/insomnia-app/app/network/o-auth-1/get-token.js

125 lines
3.5 KiB
JavaScript
Raw Normal View History

2017-11-06 20:44:55 +00:00
// @flow
2017-11-06 19:26:31 +00:00
/**
* Get an OAuth1Token object and also handle storing/saving/refreshing
* @returns {Promise.<void>}
*/
import crypto from 'crypto';
import OAuth1 from 'oauth-1.0a';
2018-04-18 18:20:49 +00:00
import {
SIGNATURE_METHOD_HMAC_SHA1,
SIGNATURE_METHOD_RSA_SHA1,
SIGNATURE_METHOD_PLAINTEXT,
SIGNATURE_METHOD_HMAC_SHA256,
2018-04-18 18:20:49 +00:00
} from './constants';
2018-06-25 17:42:50 +00:00
import type { OAuth1SignatureMethod } from './constants';
import type { RequestAuthentication, RequestBody } from '../../models/request';
import { CONTENT_TYPE_FORM_URLENCODED } from '../../common/constants';
2017-11-06 19:26:31 +00:00
2018-06-25 17:42:50 +00:00
function hashFunction(signatureMethod: OAuth1SignatureMethod) {
2017-11-06 19:26:31 +00:00
if (signatureMethod === SIGNATURE_METHOD_HMAC_SHA1) {
2018-06-25 17:42:50 +00:00
return function(baseString: string, key: string): string {
return crypto
.createHmac('sha1', key)
.update(baseString)
.digest('base64');
2017-11-06 19:26:31 +00:00
};
}
2018-04-18 18:20:49 +00:00
if (signatureMethod === SIGNATURE_METHOD_HMAC_SHA256) {
2018-06-25 17:42:50 +00:00
return function(baseString: string, key: string): string {
return crypto
.createHmac('sha256', key)
.update(baseString)
.digest('base64');
2018-04-18 18:20:49 +00:00
};
}
if (signatureMethod === SIGNATURE_METHOD_RSA_SHA1) {
2018-06-25 17:42:50 +00:00
return function(baseString: string, privatekey: string): string {
return crypto
.createSign('RSA-SHA1')
.update(baseString)
.sign(privatekey, 'base64');
};
}
2017-11-06 19:26:31 +00:00
if (signatureMethod === SIGNATURE_METHOD_PLAINTEXT) {
2018-06-25 17:42:50 +00:00
return function(baseString: string): string {
2017-11-06 19:26:31 +00:00
return baseString;
};
}
2017-11-06 20:44:55 +00:00
throw new Error(`Invalid signature method ${signatureMethod}`);
2017-11-06 19:26:31 +00:00
}
2018-06-25 17:42:50 +00:00
export default async function(
2017-11-06 20:44:55 +00:00
url: string,
method: string,
authentication: RequestAuthentication,
body: RequestBody | null = null,
2018-06-25 17:42:50 +00:00
): { [string]: string } {
2017-11-06 20:44:55 +00:00
const oauth = new OAuth1({
2017-11-06 19:26:31 +00:00
consumer: {
key: authentication.consumerKey,
secret: authentication.consumerSecret,
2017-11-06 19:26:31 +00:00
},
signature_method: authentication.signatureMethod,
version: authentication.version,
2017-11-06 21:43:00 +00:00
hash_function: hashFunction(authentication.signatureMethod),
realm: authentication.realm || null,
2017-11-06 19:26:31 +00:00
});
2017-11-06 20:44:55 +00:00
const requestData = {
2017-11-06 19:26:31 +00:00
url: url,
2017-11-06 21:43:00 +00:00
method: method,
includeBodyHash: false,
2017-11-06 21:43:00 +00:00
data: {
// These are conditionally filled in below
},
2017-11-06 19:26:31 +00:00
};
2017-11-06 21:43:00 +00:00
if (authentication.callback) {
requestData.data.oauth_callback = authentication.callback;
}
if (authentication.nonce) {
requestData.data.oauth_nonce = authentication.nonce;
}
if (authentication.timestamp) {
requestData.data.oauth_timestamp = authentication.timestamp;
}
2018-03-26 16:52:14 +00:00
if (authentication.verifier) {
requestData.data.oauth_verifier = authentication.verifier;
}
if (authentication.includeBodyHash && body && body.mimeType === CONTENT_TYPE_FORM_URLENCODED) {
requestData.includeBodyHash = true;
for (const p of body.params || []) {
requestData.data[p.name] = p.value;
}
}
2017-11-06 20:44:55 +00:00
let token = null;
if (authentication.tokenKey && authentication.tokenSecret) {
2018-06-25 17:42:50 +00:00
token = {
key: authentication.tokenKey,
secret: authentication.tokenSecret,
2018-06-25 17:42:50 +00:00
};
2017-11-06 20:44:55 +00:00
} else if (authentication.tokenKey) {
2018-06-25 17:42:50 +00:00
token = { key: authentication.tokenKey };
2017-11-06 20:44:55 +00:00
}
if (authentication.signatureMethod === SIGNATURE_METHOD_RSA_SHA1) {
2018-06-25 17:42:50 +00:00
token = { key: authentication.tokenKey, secret: authentication.privateKey };
// We override getSigningKey for RSA-SHA1 because we don't want ddo/oauth-1.0a to percentEncode the token
2018-06-25 17:42:50 +00:00
oauth.getSigningKey = function(tokenSecret) {
return tokenSecret || '';
};
}
2017-11-06 20:44:55 +00:00
const data = oauth.authorize(requestData, token);
return oauth.toHeader(data);
2017-11-06 19:26:31 +00:00
}