Merge pull request #136 from pierissimo/feat-connector-getproperty-definition-nested
Connector.getPropertyDefinition for nested properties
This commit is contained in:
commit
9e63fc3448
|
@ -135,8 +135,40 @@ Connector.prototype.getConnectorSpecificSettings = function(modelName) {
|
||||||
* @returns {Object} Property definition
|
* @returns {Object} Property definition
|
||||||
*/
|
*/
|
||||||
Connector.prototype.getPropertyDefinition = function(modelName, propName) {
|
Connector.prototype.getPropertyDefinition = function(modelName, propName) {
|
||||||
var model = this.getModelDefinition(modelName);
|
const model = this.getModelDefinition(modelName);
|
||||||
return model && model.properties[propName];
|
return Connector.getNestedPropertyDefinition(
|
||||||
|
model.model.definition,
|
||||||
|
propName.split('.')
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Helper function to get nested property definition
|
||||||
|
* @param {Object} definition Model name
|
||||||
|
* @param {Array} propPath
|
||||||
|
* @returns {Object} Property definition
|
||||||
|
*/
|
||||||
|
Connector.getNestedPropertyDefinition = function(definition, propPath) {
|
||||||
|
const properties = definition.properties || {};
|
||||||
|
const prop = properties[propPath[0]];
|
||||||
|
const isPropUndefined = typeof prop === 'undefined';
|
||||||
|
const isArray = !isPropUndefined && Array.isArray(prop.type);
|
||||||
|
const isFunction = !isPropUndefined && !isArray && typeof prop.type === 'function';
|
||||||
|
|
||||||
|
if (isPropUndefined || (propPath.length > 1 && (isArray && prop.type.length === 0))) {
|
||||||
|
throw new Error(g.f('Invalid property path'));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (propPath.length === 1) return prop;
|
||||||
|
|
||||||
|
const nextDefinition =
|
||||||
|
(isArray && prop.type[0].definition) ||
|
||||||
|
(isFunction && prop.type.definition);
|
||||||
|
|
||||||
|
return Connector.getNestedPropertyDefinition(
|
||||||
|
nextDefinition,
|
||||||
|
propPath.slice(1)
|
||||||
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -0,0 +1,107 @@
|
||||||
|
// Copyright IBM Corp. 2016. All Rights Reserved.
|
||||||
|
// Node module: loopback-connector
|
||||||
|
// This file is licensed under the MIT License.
|
||||||
|
// License text available at https://opensource.org/licenses/MIT
|
||||||
|
|
||||||
|
'use strict';
|
||||||
|
|
||||||
|
const expect = require('chai').expect;
|
||||||
|
const {ModelBuilder} = require('loopback-datasource-juggler');
|
||||||
|
const Connector = require('../lib/connector');
|
||||||
|
|
||||||
|
describe('Connector', () => {
|
||||||
|
describe('getPropertyDefinition()', () => {
|
||||||
|
let connector, builder;
|
||||||
|
|
||||||
|
beforeEach(() => {
|
||||||
|
connector = new Connector('MyConnector');
|
||||||
|
builder = new ModelBuilder();
|
||||||
|
|
||||||
|
const MyModel = builder.define('MyModel', {
|
||||||
|
firstname: String,
|
||||||
|
phoneList: [
|
||||||
|
{
|
||||||
|
number: Number,
|
||||||
|
label: {
|
||||||
|
title: String,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
],
|
||||||
|
address: {
|
||||||
|
line1: String,
|
||||||
|
},
|
||||||
|
someProp: {
|
||||||
|
innerArray: [
|
||||||
|
{
|
||||||
|
date: Date,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
connector.define({
|
||||||
|
model: MyModel,
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('supports retrieving first level properties definitions', () => {
|
||||||
|
const propDefinition1 = connector.getPropertyDefinition(
|
||||||
|
'MyModel',
|
||||||
|
'phoneList'
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(propDefinition1.type).to.be.an('array');
|
||||||
|
|
||||||
|
const propDefinition2 = connector.getPropertyDefinition(
|
||||||
|
'MyModel',
|
||||||
|
'firstname'
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(propDefinition2.type).to.be.equal(String);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('supports first level nested array property definitions', () => {
|
||||||
|
const propDefinition = connector.getPropertyDefinition(
|
||||||
|
'MyModel',
|
||||||
|
'phoneList.number'
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(propDefinition.type).to.equal(Number);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('supports second level nested array property definitions', () => {
|
||||||
|
const propDefinition = connector.getPropertyDefinition(
|
||||||
|
'MyModel',
|
||||||
|
'phoneList.label.title'
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(propDefinition.type).to.equal(String);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('supports nested property definitions on objects', () => {
|
||||||
|
const propDefinition = connector.getPropertyDefinition(
|
||||||
|
'MyModel',
|
||||||
|
'address.line1'
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(propDefinition.type).to.equal(String);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('supports nested property definitions on array within object', () => {
|
||||||
|
const propDefinition = connector.getPropertyDefinition(
|
||||||
|
'MyModel',
|
||||||
|
'someProp.innerArray.date'
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(propDefinition.type).to.equal(Date);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail for non-existing properties', () => {
|
||||||
|
expect(() =>
|
||||||
|
connector.getPropertyDefinition(
|
||||||
|
'MyModel',
|
||||||
|
'non.existing.property'
|
||||||
|
)).to.throw(/Invalid property path/);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
Loading…
Reference in New Issue