The data manager handles the beans and collections life cycle. It provides
an API to declare data classes, instantiate them, and synchronize the data
with the server. It relies on the data structure defined by the application
metadata.
** The data manager provides:**
- An interface to declare bean and collection classes from metadata
- Factory methods for creating instances of beans and bean collections
- Factory methods for creating instances of bean relations and relation
collections
- A custom implementation of
Backbone.sync
Data model metadata
The metadata is used to describe the data model. It contains information
about module fields and relationships.
From the following sample metadata, the data manager would declare two
classes: Opportunities and Contacts.
var metadata = {
modules: {
Opportunities: {
fields: {
name: { ... },
...
}
},
Contacts: { ... }
},
relationships: {
opportunities_contacts: { ... },
...
}
};
Working with beans
Declare bean classes from metadata payload.
declareModels
should be called at application start-up and whenever the
metadata changes:
const DataManager = require('data/data-manager');
DataManager.declareModels(metadata);
You may now create bean instances using factory methods.
var opportunity = DataManager.createBean(
'Opportunities',
{ name: 'Cool opportunity' }
);
// You can save a bean using the standard `Backbone.Model.save` method.
// The save method will use the data manager's sync method to communicate
// changes to the remote server.
opportunity.save();
// Create an empty collection of contacts.
var contacts = DataManager.createBeanCollection('Contacts');
// Fetch a list of contacts
contacts.fetch();
Working with relationships
var attrs = {
firstName: 'John',
lastName: 'Smith',
// relationship field
opportunityRole: 'Influencer'
}
// Create a new instance of a contact related to an existing opportunity
var contact = DataManager.createRelatedBean(opportunity, null, 'contacts', attrs);
// This will save the contact and create the relationship
contact.save(null, { relate: true });
// Create an instance of contact collection related to an existing opportunity
var contacts = DataManager.createRelatedCollection(opportunity, 'contacts');
// This will fetch related contacts
contacts.fetch({ relate: true });
Members
#
(inner) beanCollection :function
#
(inner) beanModel :function
Reference to the base bean model class constructor. Defaults to
Data/Bean.
#
(inner) mixedBeanCollection :function
Methods
#
(inner) canHaveMany(module, link) → {boolean}
Checks if a given module can have multiple relationships via a given
link.
Parameters:
Name |
Type |
Description |
module |
string
|
Name of the module to do the check for. |
link |
string
|
Relationship link name. |
Returns:
true
if the module's link is a
many
-type relationship, false
otherwise.
-
Type
-
boolean
#
(inner) createBean(module, attrsopt, optionsopt) → {Data/Bean}
Creates an instance of a bean. Example of usage:
// Create an account bean. The account's name property will be set to
// "Acme".
const DataManager = require('data/data-manager');
var account = DataManager.createBean('Accounts', { name: 'Acme' });
// Create a team set bean with a given ID
var teamSet = DataManager.createBean('TeamSets', { id: 'xyz' });
Parameters:
Name |
Type |
Attributes |
Description |
module |
string
|
|
The module name. |
attrs |
Object
|
<optional>
|
Initial values of bean attributes, which
will be set on the bean. |
options |
Object
|
<optional>
|
A hash of options. |
Returns:
A new instance of a bean.
-
Type
-
Data/Bean
#
(inner) createBeanCollection(module, modelsopt, optionsopt) → {Data/BeanCollection}
Creates instance of a bean collection. Example of usage:
const DataManager = require('data/data-manager');
// Creates an empty collection of account beans.
var accounts = DataManager.createBeanCollection('Accounts');
Parameters:
Name |
Type |
Attributes |
Description |
module |
string
|
|
The module name. |
models |
Array.<Data/Bean>
|
<optional>
|
Initial array or collection of models. |
options |
Object
|
<optional>
|
A hash of options. |
#
(inner) createMixedBeanCollection(modelsopt, optionsopt) → {Data/MixedBeanCollection}
Creates a collection of beans of different modules.
Parameters:
Name |
Type |
Attributes |
Description |
models |
Array
|
Data/BeanCollection
|
<optional>
|
A list of models to
populate the new collection with. |
options |
Object
|
<optional>
|
A hash of options. |
Creates an instance of related Data/Bean or updates an
existing bean with link information.
// Create a new contact related to the given opportunity.
const DataManager = require('data/data-manager');
var contact = DataManager.createRelatedBean(opportunity, '1', 'contacts', {
'first_name': 'John',
'last_name': 'Smith',
'contact_role': 'Decision Maker'
});
contact.save(null, { relate: true });
Parameters:
Name |
Type |
Attributes |
Description |
bean1 |
Data/Bean
|
|
Instance of the first bean. |
beanOrId2 |
Data/Bean
|
string
|
|
Instance or ID of the second
bean. A new instance is created if this parameter is null . |
link |
string
|
|
Relationship link name. |
attrs |
Object
|
<optional>
|
Bean attributes hash. |
Returns:
A new instance of the related bean or existing
bean instance updated with relationship link information.
-
Type
-
Data/Bean
Creates a new instance of related bean collection.
// Create contacts collection for an existing opportunity.
const DataManager = require('data/data-manager');
var contacts = DataManager.createRelatedCollection(opportunity, 'contacts');
contacts.fetch({ relate: true });
The newly created collection is cached in the given bean instance.
Parameters:
Name |
Type |
Attributes |
Description |
bean |
Data/Bean
|
|
Bean to link the related beans to. |
link |
string
|
|
Relationship link name. |
models |
Array
|
Data/BeanCollection
|
<optional>
|
An array of related beans to
populate the newly created collection with. |
#
(inner) declareCollectionClass(moduleName, platform, collectionControlleropt) → {function}
Declares bean collection class for a given module.
Parameters:
Name |
Type |
Attributes |
Description |
moduleName |
string
|
|
The module name. |
platform |
string
|
|
The platform name. |
collectionController |
Object
|
<optional>
|
The controller. |
#
(inner) declareModel(moduleName, module, platform, modelControlleropt, collectionControlleropt)
Declares bean model and collection classes for a given module and caches
them.
Parameters:
Name |
Type |
Attributes |
Description |
moduleName |
string
|
|
Module name. |
module |
Object
|
|
Module metadata object. |
platform |
string
|
|
The platform name. |
modelController |
Object
|
<optional>
|
The bean controller to declare. |
collectionController |
Object
|
<optional>
|
The collection controller to declare. |
#
(inner) declareModelClass(moduleName, module, platform, modelControlleropt) → {function}
Declares the bean model class for a given module.
Parameters:
Name |
Type |
Attributes |
Description |
moduleName |
string
|
|
The module name. |
module |
string
|
|
The module metadata. |
platform |
string
|
|
The platform name. |
modelController |
Object
|
<optional>
|
The model controller. |
#
(inner) declareModels(modulesopt)
Declares bean models and collections classes for each module definition.
Data manager uses Core.MetadataManager#getModules method to get
metadata if modules
parameter is not specified.
Parameters:
Name |
Type |
Attributes |
Description |
modules |
Object
|
<optional>
|
metadata hash in which keys are module names
and values are module definitions. |
#
(inner) getBeanClass(module) → {Object}
Parameters:
Name |
Type |
Description |
module |
string
|
The module name to get the bean class from. |
Returns:
The bean class for the given module
, or
this.beanModel
if not found.
-
Type
-
Object
#
(inner) getCollectionClasses() → {Object}
Gets all collection classes.
Returns:
The hash of collection classes.
-
Type
-
Object
#
(inner) getEditableFields(model, fieldsopt) → {Object}
Parameters:
Name |
Type |
Attributes |
Description |
model |
Data/Bean
|
Data/BeanCollection
|
|
The bean or collection to
get fields from. |
fields |
Array
|
<optional>
|
Field names to be checked. |
#
(inner) getModelClasses() → {Object}
Returns:
The hash of bean classes.
-
Type
-
Object
#
(inner) getOppositeLink(module, link) → {string|boolean}
Given a module and a link field name, this method gets the link field
name of the other module of the relationship.
Parameters:
Name |
Type |
Description |
module |
string
|
The module name. |
link |
string
|
The link name for the given module. |
Returns:
oppositeLink The link field name of the other module
of the relationship. false
if not found.
-
Type
-
string
|
boolean
Gets related module name.
Parameters:
Name |
Type |
Description |
module |
string
|
Name of the parent module. |
link |
string
|
Relationship link name. |
Returns:
The name of the related module. false
if not
found.
-
Type
-
string
|
boolean
#
(inner) getRelateFields(parentModuleName, link) → {Array}
Gets fields of type relate
for a given link.
Example:
Assumptions:
- We have 2 modules
Accounts
and Cases
.
Accounts
has a link field named cases
, which represents a 1-to-many
relationship between the 2 modules: A case is linked to one account and
a account can be linked to many cases.
To retrieve the field that matches this relationship on the Cases side,
you can call:
var relateField = DataManager.getRelateField('Accounts', 'cases');
and you would get the definition of the Cases field that exposes the
parent Account bean.
Parameters:
Name |
Type |
Description |
parentModuleName |
string
|
Name of the module that has a link field
named link . |
link |
string
|
Link name. |
Returns:
Definitions of the relate
fields if found or empty
array if not found.
-
Type
-
Array
#
(inner) getRelationFields(module, link) → {Array|boolean}
Gets relationship fields for a complex relationship.
Some relationships may have relationship fields, that only makes sense in
the context of the relationship between 2 modules.
Use the the following, to get the relationships fields definition of a
relationship:
let relationshipFields = DataManager.getRelationFields('Opportunities', 'contacts');
Parameters:
Name |
Type |
Description |
module |
string
|
Name of the module that has a link field
called link . |
link |
string
|
Link name. |
Returns:
Relationship fields. false
if no fields are
found.
-
Type
-
Array
|
boolean
#
(inner) getRelationshipFields(parentModule, link) → {Array}
Gets relationship fields for a complex relationship.
Some relationships may have relationship fields, that only makes sense in
the context of the relationship between 2 modules.
Use the the following, to get the relationships fields definition of a
relationship:
let relationshipFields = DataManager.getRelationshipFields('Opportunities', 'contacts');
Parameters:
Name |
Type |
Description |
parentModule |
string
|
Name of the module that has a link field
called link . |
link |
string
|
Link name. |
#
(inner) getSyncAbortCallback(method, model, optionsopt) → {function}
Gets the abort
callback function for the sync #sync method.
Parameters:
Name |
Type |
Attributes |
Description |
method |
string
|
|
The CRUD method. |
model |
Data/Bean
|
Data/BeanCollection
|
|
The model/collection to
be synced/read. |
options |
Object
|
<optional>
|
A hash of options.
Properties
Name |
Type |
Attributes |
Description |
abort |
Object
|
<optional>
|
Custom abort callback
function to be executed. |
|
Fires:
- data:sync:abort globally and on the bean/collection, if the
sync request was aborted.event:
Returns:
The wrapped abort
callback function.
-
Type
-
function
#
(inner) getSyncCallbacks(method, model, optionsopt) → {Object}
Gets the sync
callback functions.
Parameters:
Name |
Type |
Attributes |
Description |
method |
string
|
|
The CRUD method. |
model |
Data/Bean
|
Data/BeanCollection
|
|
The bean/collection to
be synced/read. |
options |
Object
|
<optional>
|
A hash of options. |
Returns:
A hash containing the fallowing callback functions:
'success', 'error', 'complete', 'abort'.
-
Type
-
Object
#
(inner) getSyncCompleteCallback(method, model, optionsopt) → {function}
Gets the complete
callback function for the sync #sync method.
Parameters:
Name |
Type |
Attributes |
Description |
method |
string
|
|
The CRUD method. |
model |
Data/Bean
|
Data/BeanCollection
|
|
The bean/collection to
be synced/read. |
options |
Object
|
<optional>
|
A hash of options.
Properties
Name |
Type |
Attributes |
Description |
complete |
Object
|
<optional>
|
Custom complete callback
function to be executed. |
|
Fires:
- data:sync:complete globally and on the bean/collection,
once the sync call was complete.event:
Returns:
The wrapped complete
callback function.
-
Type
-
function
#
(inner) getSyncErrorCallback(method, model, optionsopt) → {function}
Gets the error
callback function for the sync #sync method.
Triggers the global data:sync:complete
event (registered on
SUGAR.App.events), as well as on the model
.
Executes the abort callback if we are aborting from a previous
collection fetch request.
Parameters:
Name |
Type |
Attributes |
Description |
method |
string
|
|
The CRUD method. |
model |
Data/Bean
|
Data/BeanCollection
|
|
The model/collection to
be synced/read. |
options |
Object
|
<optional>
|
A hash of options.
Properties
Name |
Type |
Attributes |
Description |
error |
Object
|
<optional>
|
Custom error callback function to be
executed. |
|
Fires:
- data:sync:error globally and on the bean, if the
sync call returned an error.event:
Returns:
The wrapped error
callback function.
-
Type
-
function
#
(inner) getSyncSuccessCallback(method, model, optionsopt) → {function}
Gets the success
callback function for the #sync method.
Parameters:
Name |
Type |
Attributes |
Description |
method |
string
|
|
The CRUD method. |
model |
Data/Bean
|
Data/BeanCollection
|
|
The bean/collection to
be synced/read. |
options |
Object
|
<optional>
|
A hash of options. |
Fires:
- data:sync:success globally and on the bean, once the
sync call is made and is successful.event:
Returns:
The success
callback function.
-
Type
-
function
#
(inner) init()
Initializes the data manager.
#
(inner) mergeModel(name, moduleopt)
Merges a model with its metadata.
Parameters:
Name |
Type |
Attributes |
Description |
name |
string
|
|
The module name. |
module |
Object
|
<optional>
|
The module metadata. |
#
(inner) parseOptionsForSync(method, model, optionsopt) → {Object}
Builds and returns the options to pass to the sync
request.
Parameters:
Name |
Type |
Attributes |
Description |
method |
string
|
|
The CRUD method. |
model |
Data/Bean
|
Data/BeanCollection
|
|
The bean/collection to
be synced/read. |
options |
Object
|
<optional>
|
A hash of options. |
#
(inner) reset(moduleopt)
Resets class declarations.
Parameters:
Name |
Type |
Attributes |
Description |
module |
string
|
<optional>
|
The module name from which to remove the bean
and collection class. If not specified, resets bean and collection
classes of all modules. |
#
(inner) resetCollection(moduleopt)
Resets collection class declarations.
Parameters:
Name |
Type |
Attributes |
Description |
module |
string
|
<optional>
|
The module name from which to remove the
collection class. If not specified, resets collection classes of all
modules. |
#
(inner) resetModel(moduleopt)
Resets bean class declarations.
Parameters:
Name |
Type |
Attributes |
Description |
module |
string
|
<optional>
|
The module name from which to remove the bean
class. If not specified, resets bean classes of all modules. |
#
(inner) sync(method, model, optionsopt) → {Sugar.HttpRequest|boolean}
Custom implementation of Backbone.sync
pattern. Syncs models with
the remote server using SUGAR.Api.
Parameters:
Name |
Type |
Attributes |
Description |
method |
string
|
|
The CRUD method: 'create', 'read', 'update', or
'delete'. |
model |
Data/Bean
|
Data/BeanCollection
|
|
The bean/collection to
be synced/read. |
options |
Object
|
<optional>
|
A hash of options. |
Fires:
- data:sync:start globally and on the bean, before the
sync call is made.event:
Returns:
The sync request, or false
if you
attempted to load a linked context with no id on a linked bean.
-
Type
-
Sugar.HttpRequest
|
boolean
Events
#
data:sync:abort
Fires when the sync operation was aborted.
Four parameters are passed to the callback:
- operation name (
method
)
- reference to the model/collection
- options
- request SUGAR.Api.HttpRequest
const Events = require('core/events');
SUGAR.App.events.on('data:sync:abort', function(method, model, options, request) {
SUGAR.App.logger.debug('Operation aborted ' + method + ' on ' + model);
});
#
data:sync:abort
Fires on model when the sync operation ends.
Three parameters are passed to the callback:
- operation name (
method
)
- options
- request SUGAR.Api.HttpRequest
model.on('data:sync:abort', function(method, options, request) {
SUGAR.App.logger.debug('Operation aborted ' + method + ' on ' + model);
});
#
data:sync:complete
Fires when the sync operation ends.
Four parameters are passed to the callback:
- operation name (
method
)
- reference to the model/collection
- options
- request (SUGAR.Api.HttpRequest)
const Events = require('core/events');
Events.on('data:sync:complete', function(method, model, options, request) {
SUGAR.App.logger.debug("Finished operation " + method + " on " + model);
});
#
data:sync:complete
Fires on model when the sync operation ends.
Three parameters are passed to the callback:
- operation name (
method
)
- options
- request SUGAR.Api.HttpRequest
model.on('data:sync:complete', function(method, options, request) {
SUGAR.App.logger.debug('Finished operation ' + method + ' on ' + model);
});
#
data:sync:error
Fires when the sync operation ends unsuccessfully.
Four parameters are passed to the callback:
- operation name (
method
)
- reference to the model/collection
- options
- error (SUGAR.Api.HttpError)
const Events = require('core/events');
Events.on('data:sync:error', function(method, model, options, error) {
SUGAR.App.logger.debug('Operation failed ' + method + ' on ' + model);
});
#
data:sync:error
Fires on model when the sync operation ends unsuccessfully.
Three parameters are passed to the callback:
- operation name (
method
)
- options
- error SUGAR.Api.HttpError
model.on('data:sync:error', function(method, options, error) {
SUGAR.App.logger.debug('Operation failed:' + method + ' on ' + model);
});
#
data:sync:start
Fires when the sync operation starts.
Three parameters are passed to the callback:
- operation name (
method
)
- reference to the model/collection
- options
const Events = require('core/events');
Events.on('data:sync:start', function(method, model, options) {
SUGAR.App.logger.debug('Started operation ' + method + ' on ' + model);
});
#
data:sync:start
Fires on model when the sync operation starts.
Two parameters are passed to the callback:
- operation name (
method
)
- options
model.on('data:sync:start', function(method, options) {
SUGAR.App.logger.debug('Started operation ' + method + ' on ' + model);
});
#
data:sync:success
Fires when the sync operation ends successfully.
Four parameters are passed to the callback:
- operation name (
method
)
- reference to the model/collection
- options
- request (SUGAR.Api.HttpRequest)
const Events = require('core/events');
Events.on('data:sync:success', function(method, model, options, request) {
SUGAR.App.logger.debug('Finished operation ' + method + ' on ' + model);
});