can-diff/deep/deep
Take a difference of nested maps or lists.
diffDeep(destination, source)
Find the differences between two objects or lists, including nested maps or lists.
import {diff} from "can";
diff.deep({inner: {}}, {inner: {a:'foo'}})
//-> [{
// key: 'inner.a',
// type: 'add',
// value: 'foo'
// }]
patches = diff.deep({inner: []}, {inner: ['a']});
//-> [{
// key: 'inner',
// type: "splice",
// index: 0,
// deleteCount: 0,
// insert: ['a']
// }]
Parameters
- destination
{Object}:The object that will be updated.
- source
{Object}:The object used to update
destination.
Returns
{Array<Patches>}:
An array of patches objects. All patch objects will have a key property, even
"splice" type patch objects. The key is the property that was changed. A dot (.) in the key signifies
that the key was part of a nested property.
Use
mergeDeep is useful when dealing with nested data sources. It will make sure
that the right nested objects get updated.
For example, say a Todo and its nested User type are defined as follows:
const User = DefineMap.extend("User",{
id: "number",
name: "string"
});
const Todo = DefineMap.extend("Todo",{
id: {identity: true},
name: "string",
complete: "boolean",
assignedTo: [User]
});
If a todo like the following:
var justin = new User({id: 20, name: "Justin"}),
ramiya = new User({id: 21, name: "Ramiya"});
var todo = new Todo({
id: 1,
name: "mow lawn",
complete: false,
assignedTo: [justin, ramiya]
});
is updated with data like:
import {diff} from "diff";
diff.mergeDeep(todo, {
id: 1,
name: "mow lawn",
complete: true,
assignedTo: [{
id: 21, name: "Ramiya Meyer"
}]
})
NOTICE: The
todo.assignedToarray removes the Justin todo and updates the Ramiya todo.
Without specifying the identity property of User, the justin instance's id and name will be
updated (this is what updateDeep would do):
justin.id //-> 21
justin.name //-> "Ramiya Meyer"
However, if the User object's identity property is specified as follows:
const User = DefineMap.extend("User",{
id: {identity: true, type: "number"},
name: "string"
});
When the update happens, the ramiya instance will be updated correctly:
ramiya.id //-> 21
ramiya.name //-> "Ramiya Meyer"