@@ -47,10 +47,10 @@ module.exports =
4747
4848 'use strict' ;
4949
50- var _createClass = ( function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ) ( ) ;
51-
5250 var _slicedToArray = ( function ( ) { function sliceIterator ( arr , i ) { var _arr = [ ] ; var _n = true ; var _d = false ; var _e = undefined ; try { for ( var _i = arr [ Symbol . iterator ] ( ) , _s ; ! ( _n = ( _s = _i . next ( ) ) . done ) ; _n = true ) { _arr . push ( _s . value ) ; if ( i && _arr . length === i ) break ; } } catch ( err ) { _d = true ; _e = err ; } finally { try { if ( ! _n && _i [ "return" ] ) _i [ "return" ] ( ) ; } finally { if ( _d ) throw _e ; } } return _arr ; } return function ( arr , i ) { if ( Array . isArray ( arr ) ) { return arr ; } else if ( Symbol . iterator in Object ( arr ) ) { return sliceIterator ( arr , i ) ; } else { throw new TypeError ( "Invalid attempt to destructure non-iterable instance" ) ; } } ; } ) ( ) ;
5351
52+ var _createClass = ( function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ) ( ) ;
53+
5454 function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
5555
5656 function _defineProperty ( obj , key , value ) { if ( key in obj ) { Object . defineProperty ( obj , key , { value : value , enumerable : true , configurable : true , writable : true } ) ; } else { obj [ key ] = value ; } return obj ; }
@@ -68,66 +68,6 @@ module.exports =
6868 return resourceConfig . table || underscore ( resourceConfig . name ) ;
6969 }
7070
71- /**
72- * Lookup and apply table joins to query if field contains a `.`
73- * @param {string } field - Field defined in where filter
74- * @param {object } query - knex query to modify
75- * @param {object } resourceConfig - Resource of primary query/table
76- * @param {string[] } existingJoins - Array of fully qualitifed field names for
77- * any existing table joins for query
78- * @returns {string } - field updated to perspective of applied joins
79- */
80- function applyTableJoins ( field , query , resourceConfig , existingJoins ) {
81- if ( DSUtils . contains ( field , '.' ) ) {
82- ( function ( ) {
83- var parts = field . split ( '.' ) ;
84- var localResourceConfig = resourceConfig ;
85-
86- var relationPath = [ ] ;
87-
88- var _loop = function _loop ( ) {
89- var relationName = parts . shift ( ) ;
90- var relationResourceConfig = resourceConfig . getResource ( relationName ) ;
91- relationPath . push ( relationName ) ;
92-
93- if ( ! existingJoins . some ( function ( t ) {
94- return t === relationPath . join ( '.' ) ;
95- } ) ) {
96- var _localResourceConfig$ = localResourceConfig . relationList . filter ( function ( r ) {
97- return r . relation === relationName ;
98- } ) ;
99-
100- var _localResourceConfig$2 = _slicedToArray ( _localResourceConfig$ , 1 ) ;
101-
102- var relation = _localResourceConfig$2 [ 0 ] ;
103-
104- if ( relation ) {
105- var table = getTable ( localResourceConfig ) ;
106- var localId = table + '.' + relation . localKey ;
107-
108- var relationTable = getTable ( relationResourceConfig ) ;
109- var foreignId = relationTable + '.' + relationResourceConfig . idAttribute ;
110-
111- query . join ( relationTable , localId , foreignId ) ;
112- existingJoins . push ( relationPath . join ( '.' ) ) ;
113- } else {
114- // hopefully a qualified local column
115- }
116- }
117- localResourceConfig = relationResourceConfig ;
118- } ;
119-
120- while ( parts . length >= 2 ) {
121- _loop ( ) ;
122- }
123-
124- field = getTable ( localResourceConfig ) + '.' + parts [ 0 ] ;
125- } ) ( ) ;
126- }
127-
128- return field ;
129- }
130-
13171 function loadWithRelations ( items , resourceConfig , options ) {
13272 var _this = this ;
13373
@@ -198,12 +138,12 @@ module.exports =
198138
199139 if ( instance ) {
200140 var itemKeys = instance [ def . localKeys ] || [ ] ;
201- itemKeys = Array . isArray ( itemKeys ) ? itemKeys : DSUtils . keys ( itemKeys ) ;
141+ itemKeys = Array . isArray ( itemKeys ) ? itemKeys : Object . keys ( itemKeys ) ;
202142 localKeys = localKeys . concat ( itemKeys || [ ] ) ;
203143 } else {
204144 DSUtils . forEach ( items , function ( item ) {
205145 var itemKeys = item [ def . localKeys ] || [ ] ;
206- itemKeys = Array . isArray ( itemKeys ) ? itemKeys : DSUtils . keys ( itemKeys ) ;
146+ itemKeys = Array . isArray ( itemKeys ) ? itemKeys : Object . keys ( itemKeys ) ;
207147 localKeys = localKeys . concat ( itemKeys || [ ] ) ;
208148 } ) ;
209149 }
@@ -232,29 +172,35 @@ module.exports =
232172 } ) ( ) ;
233173 } else if ( def . type === 'belongsTo' || def . type === 'hasOne' && def . localKey ) {
234174 if ( instance ) {
235- task = _this . find ( resourceConfig . getResource ( relationName ) , DSUtils . get ( instance , def . localKey ) , __options ) . then ( function ( relatedItem ) {
236- instance [ def . localField ] = relatedItem ;
237- return relatedItem ;
238- } ) ;
175+ var id = DSUtils . get ( instance , def . localKey ) ;
176+ if ( id ) {
177+ task = _this . find ( resourceConfig . getResource ( relationName ) , DSUtils . get ( instance , def . localKey ) , __options ) . then ( function ( relatedItem ) {
178+ instance [ def . localField ] = relatedItem ;
179+ return relatedItem ;
180+ } ) ;
181+ }
239182 } else {
240- task = _this . findAll ( resourceConfig . getResource ( relationName ) , {
241- where : _defineProperty ( { } , relationDef . idAttribute , {
242- 'in' : DSUtils . filter ( items . map ( function ( item ) {
243- return DSUtils . get ( item , def . localKey ) ;
244- } ) , function ( x ) {
245- return x ;
183+ var ids = DSUtils . filter ( items . map ( function ( item ) {
184+ return DSUtils . get ( item , def . localKey ) ;
185+ } ) , function ( x ) {
186+ return x ;
187+ } ) ;
188+ if ( ids . length ) {
189+ task = _this . findAll ( resourceConfig . getResource ( relationName ) , {
190+ where : _defineProperty ( { } , relationDef . idAttribute , {
191+ 'in' : ids
246192 } )
247- } )
248- } , __options ) . then ( function ( relatedItems ) {
249- DSUtils . forEach ( items , function ( item ) {
250- DSUtils . forEach ( relatedItems , function ( relatedItem ) {
251- if ( relatedItem [ relationDef . idAttribute ] === item [ def . localKey ] ) {
252- item [ def . localField ] = relatedItem ;
253- }
193+ } , __options ) . then ( function ( relatedItems ) {
194+ DSUtils . forEach ( items , function ( item ) {
195+ DSUtils . forEach ( relatedItems , function ( relatedItem ) {
196+ if ( relatedItem [ relationDef . idAttribute ] === item [ def . localKey ] ) {
197+ item [ def . localField ] = relatedItem ;
198+ }
199+ } ) ;
254200 } ) ;
201+ return relatedItems ;
255202 } ) ;
256- return relatedItems ;
257- } ) ;
203+ }
258204 }
259205 }
260206
@@ -290,7 +236,7 @@ module.exports =
290236 var query = options && options . transaction || this . query ;
291237 return query . select ( '*' ) . from ( getTable ( resourceConfig ) ) . where ( resourceConfig . idAttribute , toString ( id ) ) . then ( function ( rows ) {
292238 if ( ! rows . length ) {
293- return DSUtils . Promise . reject ( new Error ( 'Not Found!' ) ) ;
239+ return Promise . reject ( new Error ( 'Not Found!' ) ) ;
294240 } else {
295241 instance = rows [ 0 ] ;
296242 return loadWithRelations . call ( _this2 , instance , resourceConfig , options ) ;
@@ -380,7 +326,10 @@ module.exports =
380326 } , {
381327 key : 'filterQuery' ,
382328 value : function filterQuery ( resourceConfig , params , options ) {
329+ var _this7 = this ;
330+
383331 var table = getTable ( resourceConfig ) ;
332+ var joinedTables = [ ] ;
384333 var query = undefined ;
385334
386335 if ( params instanceof Object . getPrototypeOf ( this . query . client ) . QueryBuilder ) {
@@ -398,9 +347,7 @@ module.exports =
398347 params . orderBy = params . orderBy || params . sort ;
399348 params . skip = params . skip || params . offset ;
400349
401- var joinedTables = [ ] ;
402-
403- DSUtils . forEach ( DSUtils . keys ( params ) , function ( k ) {
350+ DSUtils . forEach ( Object . keys ( params ) , function ( k ) {
404351 var v = params [ k ] ;
405352 if ( ! DSUtils . contains ( reserved , k ) ) {
406353 if ( DSUtils . isObject ( v ) ) {
@@ -422,19 +369,82 @@ module.exports =
422369 } ;
423370 }
424371
425- DSUtils . forOwn ( criteria , function ( v , op ) {
426- // Apply table joins (if needed)
372+ var processRelationField = function processRelationField ( field ) {
373+ var parts = field . split ( '.' ) ;
374+ var localResourceConfig = resourceConfig ;
375+ var relationPath = [ ] ;
376+
377+ var _loop = function _loop ( ) {
378+ var relationName = parts . shift ( ) ;
379+
380+ var _localResourceConfig$ = localResourceConfig . relationList . filter ( function ( r ) {
381+ return r . relation === relationName || r . localField === relationName ;
382+ } ) ;
383+
384+ var _localResourceConfig$2 = _slicedToArray ( _localResourceConfig$ , 1 ) ;
385+
386+ var relation = _localResourceConfig$2 [ 0 ] ;
387+
388+ if ( relation ) {
389+ var relationResourceConfig = resourceConfig . getResource ( relation . relation ) ;
390+ relationPath . push ( relation . relation ) ;
391+
392+ if ( relation . type === 'belongsTo' || relation . type === 'hasOne' ) {
393+ // Apply table join for belongsTo/hasOne property (if not done already)
394+ if ( ! joinedTables . some ( function ( t ) {
395+ return t === relationPath . join ( '.' ) ;
396+ } ) ) {
397+ var _table = getTable ( localResourceConfig ) ;
398+ var localId = _table + '.' + relation . localKey ;
399+
400+ var relationTable = getTable ( relationResourceConfig ) ;
401+ var foreignId = relationTable + '.' + relationResourceConfig . idAttribute ;
402+
403+ query . join ( relationTable , localId , foreignId ) ;
404+ joinedTables . push ( relationPath . join ( '.' ) ) ;
405+ }
406+ } else if ( relation . type === 'hasMany' ) {
407+ var _existsParams ;
408+
409+ // Perform `WHERE EXISTS` subquery for hasMany property
410+ var _table2 = getTable ( localResourceConfig ) ;
411+ var localId = _table2 + '.' + localResourceConfig . idAttribute ;
412+
413+ var relationTable = getTable ( relationResourceConfig ) ;
414+ var foreignId = relationTable + '.' + relation . foreignKey ;
415+
416+ var existsParams = ( _existsParams = { } , _defineProperty ( _existsParams , foreignId , { '===' : knex . raw ( localId ) } ) , _defineProperty ( _existsParams , parts [ 0 ] , criteria ) , _existsParams ) ;
417+ query . whereExists ( _this7 . filterQuery ( relationResourceConfig , existsParams , options ) ) ;
418+ criteria = null ; // criteria handled by EXISTS subquery
419+ }
420+
421+ localResourceConfig = relationResourceConfig ;
422+ } else {
423+ // hopefully a qualified local column
424+ }
425+ } ;
426+
427+ while ( parts . length >= 2 ) {
428+ _loop ( ) ;
429+ }
430+
431+ return getTable ( localResourceConfig ) + '.' + parts [ 0 ] ;
432+ } ;
433+
434+ if ( DSUtils . contains ( field , '.' ) ) {
427435 if ( DSUtils . contains ( field , ',' ) ) {
428436 var splitFields = field . split ( ',' ) . map ( function ( c ) {
429437 return c . trim ( ) ;
430438 } ) ;
431439 field = splitFields . map ( function ( splitField ) {
432- return applyTableJoins ( splitField , query , resourceConfig , joinedTables ) ;
440+ return processRelationField ( splitField ) ;
433441 } ) . join ( ',' ) ;
434442 } else {
435- field = applyTableJoins ( field , query , resourceConfig , joinedTables ) ;
443+ field = processRelationField ( field , query , resourceConfig , joinedTables ) ;
436444 }
445+ }
437446
447+ DSUtils . forOwn ( criteria , function ( v , op ) {
438448 if ( op === '==' || op === '===' ) {
439449 if ( v === null ) {
440450 query = query . whereNull ( field ) ;
@@ -503,6 +513,8 @@ module.exports =
503513 }
504514 } else if ( op === 'like' ) {
505515 query = query . where ( field , 'like' , v ) ;
516+ } else if ( op === '|like' ) {
517+ query = query . orWhere ( field , 'like' , v ) ;
506518 } else if ( op === '|==' || op === '|===' ) {
507519 if ( v === null ) {
508520 query = query . orWhereNull ( field ) ;
0 commit comments