Merge pull request #1653 from mozilla/phil/auto-unbuffer
feat(server): auto-unbuffer binary data when crossing API boundaries refactor(server): unify the unbuffering functions to one place https://github.com/mozilla/fxa-auth-server/pull/1653 r=vbudhram
This commit is contained in:
Коммит
64b3a368bf
|
@ -2,7 +2,9 @@
|
|||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
var HEX = /^(?:[a-fA-F0-9]{2})+$/
|
||||
'use strict'
|
||||
|
||||
const HEX = /^(?:[a-fA-F0-9]{2})+$/
|
||||
|
||||
module.exports.ONES = Buffer('ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff', 'hex')
|
||||
|
||||
|
@ -32,14 +34,26 @@ module.exports.xorBuffers = function xorBuffers(buffer1, buffer2) {
|
|||
return result
|
||||
}
|
||||
|
||||
module.exports.unbuffer = function unbuffer(object, inplace) {
|
||||
var keys = Object.keys(object)
|
||||
var copy = inplace ? object : {}
|
||||
for (var i = 0; i < keys.length; i++) {
|
||||
var x = object[keys[i]]
|
||||
copy[keys[i]] = Buffer.isBuffer(x) ? x.toString('hex') : x
|
||||
module.exports.unbuffer = (object, inplace) => {
|
||||
return Object.keys(object).reduce((unbuffered, key) => {
|
||||
unbuffered[key] = unbufferDatum.call(object, key, object[key])
|
||||
return unbuffered
|
||||
}, inplace ? object : {})
|
||||
}
|
||||
|
||||
module.exports.unbufferDatum = unbufferDatum
|
||||
|
||||
// Invoked as the `replacer` in calls to JSON.stringify.
|
||||
// If you're going to call it elsewhere, `this` must be
|
||||
// set as it would be then.
|
||||
function unbufferDatum (key, value) {
|
||||
const unstringifiedValue = this[key]
|
||||
|
||||
if (Buffer.isBuffer(unstringifiedValue)) {
|
||||
return unstringifiedValue.toString('hex')
|
||||
}
|
||||
return copy
|
||||
|
||||
return value
|
||||
}
|
||||
|
||||
module.exports.bufferize = function bufferize(object, options) {
|
||||
|
|
125
lib/db.js
125
lib/db.js
|
@ -8,9 +8,7 @@ const P = require('./promise')
|
|||
const Pool = require('./pool')
|
||||
const userAgent = require('./userAgent')
|
||||
|
||||
const butil = require('./crypto/butil')
|
||||
const bufferize = butil.bufferize
|
||||
const unbuffer = butil.unbuffer
|
||||
const bufferize = require('./crypto/butil').bufferize
|
||||
const random = require('./crypto/random')
|
||||
|
||||
module.exports = function (
|
||||
|
@ -71,7 +69,7 @@ module.exports = function (
|
|||
data.normalizedEmail = data.email.toLowerCase()
|
||||
return this.pool.put(
|
||||
'/account/' + data.uid.toString('hex'),
|
||||
unbuffer(data)
|
||||
data
|
||||
)
|
||||
.then(
|
||||
function () {
|
||||
|
@ -93,22 +91,19 @@ module.exports = function (
|
|||
function (sessionToken) {
|
||||
return this.pool.put(
|
||||
'/sessionToken/' + sessionToken.id,
|
||||
unbuffer(
|
||||
{
|
||||
tokenId: sessionToken.tokenId,
|
||||
data: sessionToken.data,
|
||||
uid: sessionToken.uid,
|
||||
createdAt: sessionToken.createdAt,
|
||||
uaBrowser: sessionToken.uaBrowser,
|
||||
uaBrowserVersion: sessionToken.uaBrowserVersion,
|
||||
uaOS: sessionToken.uaOS,
|
||||
uaOSVersion: sessionToken.uaOSVersion,
|
||||
uaDeviceType: sessionToken.uaDeviceType,
|
||||
mustVerify: sessionToken.mustVerify,
|
||||
tokenVerificationId: sessionToken.tokenVerificationId
|
||||
},
|
||||
'inplace'
|
||||
)
|
||||
{
|
||||
tokenId: sessionToken.tokenId,
|
||||
data: sessionToken.data,
|
||||
uid: sessionToken.uid,
|
||||
createdAt: sessionToken.createdAt,
|
||||
uaBrowser: sessionToken.uaBrowser,
|
||||
uaBrowserVersion: sessionToken.uaBrowserVersion,
|
||||
uaOS: sessionToken.uaOS,
|
||||
uaOSVersion: sessionToken.uaOSVersion,
|
||||
uaDeviceType: sessionToken.uaDeviceType,
|
||||
mustVerify: sessionToken.mustVerify,
|
||||
tokenVerificationId: sessionToken.tokenVerificationId
|
||||
}
|
||||
)
|
||||
.then(
|
||||
function () {
|
||||
|
@ -126,17 +121,14 @@ module.exports = function (
|
|||
function (keyFetchToken) {
|
||||
return this.pool.put(
|
||||
'/keyFetchToken/' + keyFetchToken.id,
|
||||
unbuffer(
|
||||
{
|
||||
tokenId: keyFetchToken.tokenId,
|
||||
authKey: keyFetchToken.authKey,
|
||||
uid: keyFetchToken.uid,
|
||||
keyBundle: keyFetchToken.keyBundle,
|
||||
createdAt: keyFetchToken.createdAt,
|
||||
tokenVerificationId: keyFetchToken.tokenVerificationId
|
||||
},
|
||||
'inplace'
|
||||
)
|
||||
{
|
||||
tokenId: keyFetchToken.tokenId,
|
||||
authKey: keyFetchToken.authKey,
|
||||
uid: keyFetchToken.uid,
|
||||
keyBundle: keyFetchToken.keyBundle,
|
||||
createdAt: keyFetchToken.createdAt,
|
||||
tokenVerificationId: keyFetchToken.tokenVerificationId
|
||||
}
|
||||
)
|
||||
.then(
|
||||
function () {
|
||||
|
@ -154,17 +146,14 @@ module.exports = function (
|
|||
function (passwordForgotToken) {
|
||||
return this.pool.put(
|
||||
'/passwordForgotToken/' + passwordForgotToken.id,
|
||||
unbuffer(
|
||||
{
|
||||
tokenId: passwordForgotToken.tokenId,
|
||||
data: passwordForgotToken.data,
|
||||
uid: passwordForgotToken.uid,
|
||||
passCode: passwordForgotToken.passCode,
|
||||
createdAt: passwordForgotToken.createdAt,
|
||||
tries: passwordForgotToken.tries
|
||||
},
|
||||
'inplace'
|
||||
)
|
||||
{
|
||||
tokenId: passwordForgotToken.tokenId,
|
||||
data: passwordForgotToken.data,
|
||||
uid: passwordForgotToken.uid,
|
||||
passCode: passwordForgotToken.passCode,
|
||||
createdAt: passwordForgotToken.createdAt,
|
||||
tries: passwordForgotToken.tries
|
||||
}
|
||||
)
|
||||
.then(
|
||||
function () {
|
||||
|
@ -182,15 +171,12 @@ module.exports = function (
|
|||
function (passwordChangeToken) {
|
||||
return this.pool.put(
|
||||
'/passwordChangeToken/' + passwordChangeToken.id,
|
||||
unbuffer(
|
||||
{
|
||||
tokenId: passwordChangeToken.tokenId,
|
||||
data: passwordChangeToken.data,
|
||||
uid: passwordChangeToken.uid,
|
||||
createdAt: passwordChangeToken.createdAt
|
||||
},
|
||||
'inplace'
|
||||
)
|
||||
{
|
||||
tokenId: passwordChangeToken.tokenId,
|
||||
data: passwordChangeToken.data,
|
||||
uid: passwordChangeToken.uid,
|
||||
createdAt: passwordChangeToken.createdAt
|
||||
}
|
||||
)
|
||||
.then(
|
||||
function () {
|
||||
|
@ -527,7 +513,7 @@ module.exports = function (
|
|||
return this.pool.put(
|
||||
'/account/' + uid.toString('hex') +
|
||||
'/device/' + deviceInfo.id.toString('hex'),
|
||||
unbuffer({
|
||||
{
|
||||
sessionTokenId: sessionTokenId,
|
||||
createdAt: deviceInfo.createdAt,
|
||||
name: deviceInfo.name,
|
||||
|
@ -535,7 +521,7 @@ module.exports = function (
|
|||
callbackURL: deviceInfo.pushCallback,
|
||||
callbackPublicKey: deviceInfo.pushPublicKey,
|
||||
callbackAuthKey: deviceInfo.pushAuthKey
|
||||
})
|
||||
}
|
||||
)
|
||||
})
|
||||
.then(
|
||||
|
@ -572,14 +558,14 @@ module.exports = function (
|
|||
return this.pool.post(
|
||||
'/account/' + uid.toString('hex') +
|
||||
'/device/' + deviceInfo.id.toString('hex') + '/update',
|
||||
unbuffer({
|
||||
{
|
||||
sessionTokenId: sessionTokenId,
|
||||
name: deviceInfo.name,
|
||||
type: deviceInfo.type,
|
||||
callbackURL: deviceInfo.pushCallback,
|
||||
callbackPublicKey: deviceInfo.pushPublicKey,
|
||||
callbackAuthKey: deviceInfo.pushAuthKey
|
||||
})
|
||||
}
|
||||
)
|
||||
.then(
|
||||
function (result) {
|
||||
|
@ -687,7 +673,7 @@ module.exports = function (
|
|||
data.verifierSetAt = Date.now()
|
||||
return this.pool.post(
|
||||
'/account/' + accountResetToken.uid.toString('hex') + '/reset',
|
||||
unbuffer(data)
|
||||
data
|
||||
)
|
||||
}
|
||||
|
||||
|
@ -698,13 +684,9 @@ module.exports = function (
|
|||
|
||||
DB.prototype.verifyTokens = function (tokenVerificationId, accountData) {
|
||||
log.trace({ op: 'DB.verifyTokens', tokenVerificationId: tokenVerificationId })
|
||||
return this.pool.post('/tokens/' + tokenVerificationId.toString('hex') + '/verify',
|
||||
unbuffer(
|
||||
{
|
||||
uid: accountData.uid
|
||||
},
|
||||
'inplace'
|
||||
)
|
||||
return this.pool.post(
|
||||
'/tokens/' + tokenVerificationId.toString('hex') + '/verify',
|
||||
{ uid: accountData.uid }
|
||||
)
|
||||
.then(
|
||||
function (body) {
|
||||
|
@ -726,15 +708,12 @@ module.exports = function (
|
|||
function (accountResetToken) {
|
||||
return this.pool.post(
|
||||
'/passwordForgotToken/' + passwordForgotToken.id + '/verified',
|
||||
unbuffer(
|
||||
{
|
||||
tokenId: accountResetToken.tokenId,
|
||||
data: accountResetToken.data,
|
||||
uid: accountResetToken.uid,
|
||||
createdAt: accountResetToken.createdAt
|
||||
},
|
||||
'inplace'
|
||||
)
|
||||
{
|
||||
tokenId: accountResetToken.tokenId,
|
||||
data: accountResetToken.data,
|
||||
uid: accountResetToken.uid,
|
||||
createdAt: accountResetToken.createdAt
|
||||
}
|
||||
)
|
||||
.then(
|
||||
function () {
|
||||
|
@ -779,7 +758,7 @@ module.exports = function (
|
|||
securityEvent: event
|
||||
})
|
||||
|
||||
return this.pool.post('/securityEvents', unbuffer(event))
|
||||
return this.pool.post('/securityEvents', event)
|
||||
}
|
||||
|
||||
DB.prototype.securityEvents = function (params) {
|
||||
|
|
28
lib/log.js
28
lib/log.js
|
@ -4,23 +4,13 @@
|
|||
|
||||
'use strict'
|
||||
|
||||
var EventEmitter = require('events').EventEmitter
|
||||
var util = require('util')
|
||||
var mozlog = require('mozlog')
|
||||
var config = require('../config')
|
||||
var logConfig = config.get('log')
|
||||
var StatsDCollector = require('./metrics/statsd')
|
||||
|
||||
function unbuffer(object) {
|
||||
var keys = Object.keys(object)
|
||||
for (var i = 0; i < keys.length; i++) {
|
||||
var x = object[keys[i]]
|
||||
if (Buffer.isBuffer(x)) {
|
||||
object[keys[i]] = x.toString('hex')
|
||||
}
|
||||
}
|
||||
return object
|
||||
}
|
||||
const EventEmitter = require('events').EventEmitter
|
||||
const util = require('util')
|
||||
const mozlog = require('mozlog')
|
||||
const config = require('../config')
|
||||
const logConfig = config.get('log')
|
||||
const StatsDCollector = require('./metrics/statsd')
|
||||
const unbuffer = require('./crypto/butil').unbuffer
|
||||
|
||||
function Lug(options) {
|
||||
EventEmitter.call(this)
|
||||
|
@ -139,10 +129,10 @@ Lug.prototype.summary = function (request, response) {
|
|||
if (line.code >= 500) {
|
||||
line.trace = request.app.traced
|
||||
line.stack = response.stack
|
||||
this.error(unbuffer(line), response.message)
|
||||
this.error(unbuffer(line, true), response.message)
|
||||
}
|
||||
else {
|
||||
this.info(unbuffer(line))
|
||||
this.info(unbuffer(line, true))
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -2,8 +2,11 @@
|
|||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
var P = require('./promise')
|
||||
var Poolee = require('poolee')
|
||||
'use strict'
|
||||
|
||||
const P = require('./promise')
|
||||
const Poolee = require('poolee')
|
||||
const unbufferDatum = require('./crypto/butil').unbufferDatum
|
||||
|
||||
function parseUrl(url) {
|
||||
var match = /([a-zA-Z]+):\/\/(\S+)/.exec(url)
|
||||
|
@ -40,7 +43,7 @@ Pool.prototype.request = function (method, path, data) {
|
|||
headers: {
|
||||
'Content-Type': 'application/json'
|
||||
},
|
||||
data: data ? JSON.stringify(data) : undefined
|
||||
data: data ? JSON.stringify(data, unbufferDatum) : undefined
|
||||
},
|
||||
handleResponse
|
||||
)
|
||||
|
|
Загрузка…
Ссылка в новой задаче