[Entanglement] Add entanglement bundle
The entanglement bundle defines move, copy, and link actions, and exposes them as context menu actions. * The Move action moves an object from it's current parent to a new parent object. * The Copy action deep-copies an object to a new parent object. * The Link action links an object to a new parent object. These actions are implemented by three new services: moveService, copyService, and linkService. Mocks are provided for each service for easy testing of components that depend on them. Additionally, this bundle provides a DomainObjectFactory that simplifies the construction of mockDomainObjects for tests. These actions are exposed to the user as context menu options.
This commit is contained in:
79
platform/entanglement/src/services/CopyService.js
Normal file
79
platform/entanglement/src/services/CopyService.js
Normal file
@@ -0,0 +1,79 @@
|
||||
/*global define */
|
||||
|
||||
define(
|
||||
function () {
|
||||
"use strict";
|
||||
|
||||
function CopyService($q, creationService, policyService) {
|
||||
|
||||
/**
|
||||
* duplicateObject duplicates a `domainObject` into the composition
|
||||
* of `parent`, and then duplicates the composition of
|
||||
* `domainObject` into the new object.
|
||||
*
|
||||
* This function is a recursive deep copy.
|
||||
*
|
||||
* @param {DomainObject} domainObject - the domain object to
|
||||
* duplicate.
|
||||
* @param {DomainObject} parent - the parent domain object to
|
||||
* create the duplicate in.
|
||||
* @returns {Promise} A promise that is fulfilled when the
|
||||
* duplicate operation has completed.
|
||||
*/
|
||||
function duplicateObject(domainObject, parent) {
|
||||
var model = JSON.parse(JSON.stringify(domainObject.getModel()));
|
||||
if (domainObject.hasCapability('composition')) {
|
||||
model.composition = [];
|
||||
}
|
||||
|
||||
return creationService
|
||||
.createObject(model, parent)
|
||||
.then(function (newObject) {
|
||||
if (!domainObject.hasCapability('composition')) {
|
||||
return;
|
||||
}
|
||||
|
||||
return domainObject
|
||||
.useCapability('composition')
|
||||
.then(function (composees) {
|
||||
// Duplicate composition serially to prevent
|
||||
// write conflicts.
|
||||
return composees.reduce(function (promise, composee) {
|
||||
return promise.then(function () {
|
||||
return duplicateObject(composee, newObject);
|
||||
});
|
||||
}, $q.when(undefined));
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
return {
|
||||
/**
|
||||
* Returns true if `object` can be copied into
|
||||
* `parentCandidate`'s composition.
|
||||
*/
|
||||
validate: function (object, parentCandidate) {
|
||||
if (!parentCandidate || !parentCandidate.getId) {
|
||||
return false;
|
||||
}
|
||||
if (parentCandidate.getId() === object.getId()) {
|
||||
return false;
|
||||
}
|
||||
return policyService.allow(
|
||||
"composition",
|
||||
object.getCapability('type'),
|
||||
parentCandidate.getCapability('type')
|
||||
);
|
||||
},
|
||||
/**
|
||||
* Wrapper, @see {@link duplicateObject} for implementation.
|
||||
*/
|
||||
perform: function (object, parentObject) {
|
||||
return duplicateObject(object, parentObject);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
return CopyService;
|
||||
}
|
||||
);
|
||||
Reference in New Issue
Block a user