mirror of
https://github.com/Xahau/xahau.js.git
synced 2025-11-26 15:15:49 +00:00
[CHORE] limit identity to defined fields
This commit is contained in:
@@ -12,8 +12,6 @@ var BlobObj = function (url, id, key) {
|
|||||||
this.identity = new Identity(this);
|
this.identity = new Identity(this);
|
||||||
};
|
};
|
||||||
|
|
||||||
var identityRoot = '/identityVault';
|
|
||||||
|
|
||||||
// Blob operations
|
// Blob operations
|
||||||
// Do NOT change the mapping of existing ops
|
// Do NOT change the mapping of existing ops
|
||||||
BlobObj.ops = {
|
BlobObj.ops = {
|
||||||
@@ -40,6 +38,43 @@ for (var name in BlobObj.ops) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//Identity fields
|
||||||
|
var identityRoot = 'identityVault';
|
||||||
|
var identityFields = [
|
||||||
|
'name',
|
||||||
|
'entityType',
|
||||||
|
'email',
|
||||||
|
'phone',
|
||||||
|
'address',
|
||||||
|
'nationalID',
|
||||||
|
'birthday',
|
||||||
|
'birthplace'
|
||||||
|
];
|
||||||
|
|
||||||
|
var addressFields = [
|
||||||
|
'contact',
|
||||||
|
'line1',
|
||||||
|
'line2',
|
||||||
|
'city',
|
||||||
|
'region', //state/province/region
|
||||||
|
'postalCode',
|
||||||
|
'country'
|
||||||
|
];
|
||||||
|
|
||||||
|
var nationalIDFields = [
|
||||||
|
'number',
|
||||||
|
'type',
|
||||||
|
'country',
|
||||||
|
]
|
||||||
|
|
||||||
|
var idTypeFields = [
|
||||||
|
'ssn',
|
||||||
|
'taxID',
|
||||||
|
'passport',
|
||||||
|
'driversLicense',
|
||||||
|
'other'
|
||||||
|
]
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Initialize a new blob object
|
* Initialize a new blob object
|
||||||
* @param {function} fn - Callback function
|
* @param {function} fn - Callback function
|
||||||
@@ -499,7 +534,7 @@ function normalizeSubcommands(subcommands, compress) {
|
|||||||
* Identity class
|
* Identity class
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
var Identity = function(blob) {
|
var Identity = function (blob) {
|
||||||
var self = this;
|
var self = this;
|
||||||
self.blob = blob;
|
self.blob = blob;
|
||||||
|
|
||||||
@@ -507,7 +542,7 @@ var Identity = function(blob) {
|
|||||||
self.validate = function(fn) {
|
self.validate = function(fn) {
|
||||||
if (!self.blob) return fn(new Error("Identity must be associated with a blob"));
|
if (!self.blob) return fn(new Error("Identity must be associated with a blob"));
|
||||||
else if (!self.blob.data) return fn(new Error("Invalid Blob"));
|
else if (!self.blob.data) return fn(new Error("Invalid Blob"));
|
||||||
else if (!self.blob.data.identityVault) {
|
else if (!self.blob.data[identityRoot]) {
|
||||||
self.blob.set(identityRoot, {}, function(err, res){
|
self.blob.set(identityRoot, {}, function(err, res){
|
||||||
if (err) return fn(err);
|
if (err) return fn(err);
|
||||||
else return fn(null, true);
|
else return fn(null, true);
|
||||||
@@ -517,14 +552,50 @@ var Identity = function(blob) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* getFullAddress
|
||||||
|
* returns the address formed into a text string
|
||||||
|
* @param {string} key - Encryption key
|
||||||
|
*/
|
||||||
|
Identity.prototype.getFullAddress = function (key) {
|
||||||
|
if (!this.blob ||
|
||||||
|
!this.blob.data ||
|
||||||
|
!this.blob.data[identityRoot] ||
|
||||||
|
!this.blob.data[identityRoot].address) {
|
||||||
|
return "";
|
||||||
|
}
|
||||||
|
|
||||||
|
var address = this.get('address', key);
|
||||||
|
var text = "";
|
||||||
|
|
||||||
|
if (address.value.contact) text += address.value.contact;
|
||||||
|
if (address.value.line1) text += " " + address.value.line1;
|
||||||
|
if (address.value.line2) text += " " + address.value.line2;
|
||||||
|
if (address.value.city) text += " " + address.value.city;
|
||||||
|
if (address.value.region) text += " " + address.value.region;
|
||||||
|
if (address.value.postalCode) text += " " + address.value.postalCode;
|
||||||
|
if (address.value.country) text += " " + address.value.country;
|
||||||
|
return text;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* getAll
|
* getAll
|
||||||
* get and decrypt all identity fields
|
* get and decrypt all identity fields
|
||||||
* @param {string} key - Encryption key
|
* @param {string} key - Encryption key
|
||||||
* @param {function} fn - Callback function
|
* @param {function} fn - Callback function
|
||||||
*/
|
*/
|
||||||
Identity.prototype.getAll = function(key) {
|
Identity.prototype.getAll = function (key) {
|
||||||
|
|
||||||
|
if (!this.blob || !this.blob.data || !this.blob.data[identityRoot]) {
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
var result = {}, identity = this.blob.data[identityRoot];
|
||||||
|
for (var i in identity) {
|
||||||
|
result[i] = this.get(i, key);
|
||||||
|
}
|
||||||
|
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -534,54 +605,111 @@ Identity.prototype.getAll = function(key) {
|
|||||||
* @param {string} pointer - Field to retrieve
|
* @param {string} pointer - Field to retrieve
|
||||||
* @param {string} key - Encryption key
|
* @param {string} key - Encryption key
|
||||||
*/
|
*/
|
||||||
Identity.prototype.get = function(pointer, key) {
|
Identity.prototype.get = function (pointer, key) {
|
||||||
if (!this.blob || !this.blob.data || !this.blob.data.identityVault) {
|
if (!this.blob || !this.blob.data || !this.blob.data[identityRoot]) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
var data = this.blob.data.identityVault[pointer];
|
var data = this.blob.data[identityRoot][pointer];
|
||||||
if (data && data.encrypted) {
|
if (data && data.encrypted) {
|
||||||
|
return decrypt(key, data);
|
||||||
|
|
||||||
return {
|
|
||||||
encrypted : data.encrypted,
|
|
||||||
value : decrypt(key, data.value)
|
|
||||||
}
|
|
||||||
} else if (data) {
|
} else if (data) {
|
||||||
return data;
|
return data;
|
||||||
|
|
||||||
|
} else {
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
function decrypt (key, value) {
|
function decrypt (key, data) {
|
||||||
value = crypt.decrypt(key, value);
|
var value;
|
||||||
|
var result = {encrypted : true};
|
||||||
|
|
||||||
try {
|
try {
|
||||||
return JSON.parse(value);
|
value = crypt.decrypt(key, data.value);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
return value;
|
result.value = data.value;
|
||||||
|
result.error = e;
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
result.value = JSON.parse(value);
|
||||||
|
} catch (e) {
|
||||||
|
result.value = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* set
|
* set
|
||||||
* set and encrypt a single identity field
|
* set and encrypt a single identity field.
|
||||||
* @param {string} pointer - Field to set
|
* @param {string} pointer - Field to set
|
||||||
* @param {string} key - Encryption key
|
* @param {string} key - Encryption key
|
||||||
* @param {string} value - Unencrypted data
|
* @param {string} value - Unencrypted data
|
||||||
* @param {function} fn - Callback function
|
* @param {function} fn - Callback function
|
||||||
*/
|
*/
|
||||||
Identity.prototype.set = function(pointer, key, value, fn) {
|
Identity.prototype.set = function (pointer, key, value, fn) {
|
||||||
var self = this;
|
var self = this;
|
||||||
|
|
||||||
|
//check fields for validity
|
||||||
|
if (identityFields.indexOf(pointer) === -1) {
|
||||||
|
return fn(new Error("invalid identity field"));
|
||||||
|
|
||||||
|
//validate address fields
|
||||||
|
} else if (pointer === 'address') {
|
||||||
|
if (typeof value !== 'object') {
|
||||||
|
return fn(new Error("address must be an object"));
|
||||||
|
}
|
||||||
|
|
||||||
|
for (var addressField in value) {
|
||||||
|
if (addressFields.indexOf(addressField) === -1) {
|
||||||
|
return fn(new Error("invalid address field"));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//validate nationalID fields
|
||||||
|
} else if (pointer === 'nationalID') {
|
||||||
|
if (typeof value !== 'object') {
|
||||||
|
return fn(new Error("nationalID must be an object"));
|
||||||
|
}
|
||||||
|
|
||||||
|
for (var idField in value) {
|
||||||
|
if (nationalIDFields.indexOf(idField) === -1) {
|
||||||
|
return fn(new Error("invalid nationalID field"));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (idField === 'type') {
|
||||||
|
for (var idType in value.type) {
|
||||||
|
if (idTypeFields.indexOf(idType) === -1) {
|
||||||
|
return fn(new Error("invalid nationalID type"));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
this.validate(function(err, res){
|
this.validate(function(err, res){
|
||||||
if (err) return fn(err);
|
if (err) return fn(err);
|
||||||
|
|
||||||
|
//NOTE: currently we will overwrite if it already exists
|
||||||
|
//the other option would be to require decrypting with the
|
||||||
|
//existing key as a form of authorization
|
||||||
|
//var current = self.get(pointer, key);
|
||||||
|
//if (current && current.error) {
|
||||||
|
// return fn ? fn(current.error) : undefined;
|
||||||
|
//}
|
||||||
|
|
||||||
var data = {};
|
var data = {};
|
||||||
data[pointer] = {
|
data[pointer] = {
|
||||||
encrypted : key ? true : false,
|
encrypted : key ? true : false,
|
||||||
value : key ? encrypt(key, value) : value
|
value : key ? encrypt(key, value) : value
|
||||||
}
|
}
|
||||||
|
|
||||||
self.blob.extend(identityRoot, data, fn);
|
self.blob.extend("/" + identityRoot, data, fn);
|
||||||
});
|
});
|
||||||
|
|
||||||
function encrypt (key, value) {
|
function encrypt (key, value) {
|
||||||
@@ -601,6 +729,14 @@ Identity.prototype.set = function(pointer, key, value, fn) {
|
|||||||
*/
|
*/
|
||||||
Identity.prototype.unset = function (pointer, key, fn) {
|
Identity.prototype.unset = function (pointer, key, fn) {
|
||||||
|
|
||||||
|
//NOTE: this is rather useless since you can overwrite
|
||||||
|
//without an encryption key
|
||||||
|
var data = this.get(pointer, key);
|
||||||
|
if (data && data.error) {
|
||||||
|
return fn(data.error);
|
||||||
|
}
|
||||||
|
|
||||||
|
this.blob.unset("/" + identityRoot+"/" + pointer, fn);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -662,8 +798,7 @@ module.exports.verify = function (url, username, token, fn) {
|
|||||||
* @param {object} options.oldUserBlob
|
* @param {object} options.oldUserBlob
|
||||||
* @param {function} fn
|
* @param {function} fn
|
||||||
*/
|
*/
|
||||||
module.exports.create = function (options, fn)
|
module.exports.create = function (options, fn) {
|
||||||
{
|
|
||||||
|
|
||||||
var blob = new BlobObj(options.url, options.id, options.crypt);
|
var blob = new BlobObj(options.url, options.id, options.crypt);
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user