Is there any implementation (or pattern) on how to handle the following extend cases? AFAIK there’s no way to do it straightforward neither in Angular or Underscore, is that right?
Otherwise here’s my implementation, but I’d like to know if there’s anything that has already been done, or in any case, know your feedback about my code, thanks!
http://jsbin.com/welcome/52916/edit
/**
Extends the target object with the properties in the source object, with the following special handling:
- it doesn't extend undefined properties, i.e.
target: { a: 10 }
source: { a: undefined }
result: { a: 10 }
- it does nested extends rather than overwriting sub-objects, i.e.
target: { b: { i: 'Hi' } }
source: { b: { j: 'Bye' } }
result: { b: { i: 'Hi', j: 'Bye' } }
*/
function extend( target, source ) {
_.each( _.keys( source ), function( k ) {
if (angular.isDefined( source[k] )) {
if (angular.isObject( source[k] )) {
extend( definedOr( target[k], {} ), source[k] );
}
else {
target[k] = source[k];
}
}
});
return target;
}
Yes, I guess, neither
_.extendnor_.defaultssolves your problem and my Angular-Fu is not good enough to comment there.But, It does look like
jQuery.extend(true, target, source)solves both your use-cases. Thetrue, in the method call does a deep-extend while theextendmethod already works with theundefinedcase you mentioned.If you need more control over resolving conflicts between source and target objects I have always found that
Object.merge(target, source, deep:boolean, resolve:boolean|function)to be more flexible. In case you are wondering that is a method from a library called Sugar.js.For the sake of completeness, the Sugar.js method can be used like given below for your particular use-case.
Hope that answered your question.