Home Reference Source Repository
import CollectionProperty from 'f.lux/src/collection/CollectionProperty.js'
public class | source

CollectionProperty

Extends:

Property → CollectionProperty

CollectionProperty provides a standard means for accessing remote data and was inspired by Backbone collections. The protocol for interacting with the data source is delegated to an endpoint so the same application logic can work with data from a RESTful api, graphql, local test data, or even an in-browser database like localforage. F.lux ships with support for two endpoints, RestEndpointProperty and PojoEndpointProperty.

F.lux ships with a example using collections in a todo application utilizing an in memory data source. The example uses a local data source to make setup dead simple while still demonstrating the basic features of creating and interacting with collections.

Basic operations

  • add(state, mergeOp)
  • all()
  • clear()</li> <li>create(model)</li> <li>destroy(id)</li> <li>fetch(filter, mergeOp)</li> <li>find(id)</li> <li>get(id)</li> <li>has(id)</li> <li>remove(id)`

Utility functions

  • entries()
  • every(iteratee, context)
  • filter(iteratee, context)
  • groupBy(callback, context)
  • keys()
  • map(iteratee, context)
  • reduce(iteratee, acc, context)
  • some(iteratee, context)
  • sortBy(...iteratee)
  • values()

Model access

Properties managed by a collection receive an f.lux accessor ($()) with additional capabilities related to the collection. The accessor class is $ShadowModelAccess.

  • collection() - gets the Collection managing this model
  • destroy() - permanently deletes the model from the collection using CollectionProperty#destroy
  • id() - gets the ID used by the data source for tracking the model
  • isWaiting() - is a network operation in progress associated with this model
  • isDirty() - has the model been modified since it was last saved/retrieved
  • isNew() - gets whether the model has yet to be written to the collection's endpoint
  • remove() - removes the model from the collection using CollectionProperty#remove
  • save() - save the model using CollectionProperty#save

Paging

The collection provides redimentary paging support for potentially large collections. The current implementation simply grows the collection size wtih each call to fetchNext() and does not make any efforts to remove previous models. (A likely future enhancement)

  • fetchNext() - gets the next group of models
  • isPaging() - gets if a paging request is outstanding (only one paging request per collection allowed at one time)
  • hasMorePages() - does the endpoint have additional models
  • nextOffset() - gets the offset for the next paging request
  • resetPaging() - resets the internal paging variables
  • setLimit() - change the number of models requested with each fetchNext() request

Endpoints

Collections represent a protocol independent means of managing persistent models that exist outside the application state. Endpoints implement the protocol connection to the data source. F.lux endpoints have been implemented for RESTful server apis, in-memory, GraphQL, Sqlite, and Couchbase. F.lux ships with support for RESTful servers and in-memory.

A simple, explicit example of creating a collection and assigning an endpoint:

const rootProperty = store.root();
const collection = new CollectionProperty(colType);
const ep = new RestEndpointProperty.createFor("http://some-url.com/an-api");

collection.setEndpoint(ep);

root._keyed.addProperty("aCollection", collection);

The Todo Collection Example demonstrates a more typical example of setting up a collection.

See:

Query filters

Collection models are retrieved in full using CollectionProperty#fetch that has the following signature:

fetch(filter=null, mergeOp=REPLACE_OPTION, replaceAll=true)

where:

  • filter - a query filter object or null for no endpoint filtering
  • mergeOp - one of DEFAULTS_OPTION, MERGE_OPTION, or REPLACE_OPTION and specifies how to combine an existing model with a matching ID with a newly retrieved model.
  • replaceAll - a boolean where true means replace the current colleciton models with the returned models.

The filter parameter is a specialized object generated by the endpoint method queryBuilder(). A query builder is specialized to the endpoint and expose the following methods:

  • equals(name, value)
  • gt(name, value)
  • gte(name, value)
  • lt(name, value)
  • lte(name, value)

An example of using a query builder is:

const qb = colleciton.endpoint.queryBuilder();

qb.equals("name", "fred");

collection.fetch(qb);

See:

Errors

Methods utilizing the collection endpoint are asynchronous and return a Promise. Errors generated during an endpoint operation reject using an Error with several specialized properties:

  • status - an HTTP status code for the error type
  • endpointError - the error object generated by the endpoint

Auto-checkpointing

The Property class supports checkpointing state that can be reset at a later time using Property#resetToCheckpoint. Collections support setting an 'auto-checkpoint' flag that will result in managed models automatically setting a checkpoint on change. This handy for situations like a 'Cancel' button on a form where all changes need to be undone. The checkpoints are automatically cleared when a model is saved.

  • isAutocheckpoint()
  • setAutocheckpoint(auto)

Middleware

A middleware operation is invoked before each asynchronous/network operation involving the endpoint. Middleware operations are functions with the following format

function middleware(collectionShadow, collectionProperty, op): Promise

Middleware functions must return a Promise and are invoked in the order registered. A function generating an error will terminate the middleware chain and the collection operation will not be performed.

  • CreateOp - invoked prior to create rquests
  • DestroyOp - invoked prior to destroy rquests
  • FetchOp - invoked prior to fetch rquests
  • FindOp - invoked prior to find rquests
  • UpdateOp - invoked prior to update rquests
  • `` -

Events

A colleciton is an Event Emitter and generates the following events:

  • ChangeEvent - collection changes
  • DeletedEvent - collection destroy() success
  • FetchedEvent - collection fetch() success
  • FoundEvent - collection find() success
  • ErrorEvent - error during an operation
  • SavedEvent - collection save() success

Events are can be utilized to handle authorization errors, offline support, logging, or debugging tools.

See:

Static Method Summary

Static Public Methods
public static

createClass(shadowType: Object | CollectionShadow, typeCallback: function(type: StateType), initialState: Object): ObjectProperty

Factory function for creating an CollectionProperty subclass.

public static

defineType(PropClass: CollectionShadow, ShadowType: Object | CollectionShadow, typeCallback: function(type: StateType), initialState: Object): *

Factory function for setting up the StateType type class variable with an appropriately configured intial state.

Constructor Summary

Public Constructor
public

constructor(stateType: *)

Member Summary

Public Members
public get

Gets the endpoint for accessing the remote data source.

public get

Gets the endpoint ID, which for RestEndpointProperty is its URL.

public
public get

size: *

Gets the number of models contained in the collection.

Method Summary

Public Methods
public

addModel(state: object, mergeOp: string): *

Synchronously adds a new model object to the collection.

public

addModels(models: array, mergeOp: string, syncOp: boolean)

Bulk adds multiple models.

public

clean(json: *): *

public

Removes the endpoint from the collection.

public

create(model: Object): Promise

Combines an CollectionProperty#add and CollectionProperty#save actions.

public

destroy(id: *): Promise

Permantently deletes the model with the endpoint and removes it from the collection.

public

extractId(model: *): *

Used by the private _shadow() method to get the id from the model JSON representation as returned by the subclass doXXX() apis.

public

fetch(filter: *, mergeOp: string, replaceAll: boolean, callback: *): Promise

Fetches all the models from the endpoint.

public

fetchNext(mergeOp: string): Promise

Fetches the next set of models from the endpoint.

public

find(id: *): Promise

Gets a model by ID.

public

getModel(id: *): Object

Gets a model by ID.

public
this method is experimental.

Gets an object capable of providing a persisted version of this collection.

public

hasModel(id: *): boolean

Gets if the collection contains a matching model.

public

hasMorePages(state: *): *

Gets if additional paging calls will return additional results.

public

Sets whether auto-checkpointing is enabled.

public

Gets if the collection is active (has a shadow) and an endpoint.

public

isFetching(): *

Gets if a fetching operation that will replace ALL models is in progress.

public

isNew(id: *): *

Gets if a model has never been persisted to the endpoint.

public

isNewModel(shadow: *): *

Gets if a model shadow state model represents a model that has never been persisted to the endpoint.

public

isPaging(state: *): *

Gets if a paging operation (CollectionProperty#fetchNext) call is in progress.

public
public

modelEntries(state: *): Array

Gets an iterator with [ID, model] paris.

public

modelKeys(state: *): Iterator

Gets an iterator containing each model IDs.

public

modelKeysArray(state: *): Array

Gets an array containing each model iDs.

public

modelValues(state: *): Iterator

Gets an iterator containing each f.lux shadow state model.

public

modelsArray(state: *): array

Gets the shadow models currently managed by the collection.

public

nextOffset(): *

Gets the offset for the next paging request.

public

remove(id: *)

Synchronously removes the model from the collection without performing an endpoint operation.

public

Removes all models from the collection and marks the collection as having not synched with the endpoint.

public

Resets all internal paging tracking variables but does not affect currently stored models.

public

save(id: *, mergeOp: string): Promise

Saves a model through the endpoint.

public

Sets whether auto-checkpointing should be enabled.

public

setEndpoint(endPoint: *)

public

setIdName(idName: *)

Sets the property name containing the model ID.

public

setLimit(limit: number)

Sets the number of models to request with each paging request.

public

setModels(models: array, syncOp: boolean)

Bulk replaces current models with an array of new models.

public
this method is experimental.

Sets an object capable of providing a persisted version of this collection.

public

use(op: *, mw: *)

Registers collection middleware operation.

Inherited Summary

From class Property
public
public
public
public

[_checkpoint]: {"data": *}

public

[_impl]: *

public
public

[_mixins]: *[]

public
public

[_pid]: *

public
public
public
public
public

Use this.$$() in shadow methods to get access to the property.

public

Gets if autoshadowing is enabled for this property.

public

Copies the current actual state for later reset using Property#resetToCheckpoint.

public

Clears an existing checkpoint created using Property#checkpoint.

public

create$(impl: *): Access

Creates the object to be assigned to the shadow.$ property.

public

Gets the path from root property using a dot (.) separator.

public

Gets the checkpoint state previously recorded using Property#checkpoint.

public

getInitialState(state: *): *

Gets the initial state for a property at the beginning of the property mounting process.

public

Gets if an existing checkpoint has be created using Property#checkpoint.

public

Gets the result from StateType#computeInitialState.

public

Gets if the property is currently shadowing an actual state property.

public

Gets if property is an actual isolated property managed by the store.

public

Gets if the property allows for assignment through the shadow state, ie todo.desc = "go skiing".

public

Gets if this is the shadow state root property.

public

The property name by which this property is referenced by the Property.parent.

public

nextState(): *

Gets what the actual state for this property will be after the Store updates all pending actions.

public

Gets the object containing or managing this property.

public

Gets the parent property.

public

Gets the parent's shadow property.

public

path(): []

Gets the Property#name components from the root property to this property.

public

pid(): number

Gets the unique f.lux ID for this property.

public

propertyChildInvalidated(childProperty: Property, sourceProperty: Property)

A child property or one of its descendents wil be changing state.

public

Invoked by the f.lux shadowing process after a property initially shadows a state property.

public

Invoked by the f.lux shadowing process after a property is reshadowed.

public

Invoked by the f.lux shadowing process just before a property initially shadows a state property.

public

Invoked by the f.lux shadowing process just before a property will be removed from the shadow state.

public

Replaces the current property state with a checkpoint state previously recorded using Property#checkpoint.

public

Gets the shadow state root property for the Store managing this property.

public

Gets the root shadow state for the Store managing this property.

public

Sets the auto shadow property flag.

public

setImplementationClass(ImplClass: *)

public

Explicitly sets an initial state that will be used if the state tree does not have a value for this property.

public

setReadonly(readonly: *)

Sets the readonly flag which will prevent an assignment from changing the value.

public

setShadowClass(ShadowClass: Shadow)

Sets the class to be used for the shadow api

public

shader(state: *): *

Gets the Shader instance for this property.

public

Returns the Shadow subclass used to virtualize the state property.

public

Gets the path from root property using a slash (/) separator.

public

state(): *

Gets the actual state being shadowed.

public

stateType(): *

Gets the StateType used for creating this property.

public

store(): *

Gets the {@Link Store} containing the application state.

public

touch()

Triggers a reshadow of the properties shadow state.

public

typeName(): *

Gets this property's StateType.typeName value.

public

update(callback: function)

Makes changes to the next proeprty state.

Static Public Methods

public static createClass(shadowType: Object | CollectionShadow, typeCallback: function(type: StateType), initialState: Object): ObjectProperty source

Factory function for creating an CollectionProperty subclass. The generated class will have the type StateType descriptor set upon return.

Example usage:

class SomeShadow extends CollectionShadow {
// definition here
}

export default CollectionProperty.createClass(SomeShadow, type => {
// configure type variable
});

Params:

NameTypeAttributeDescription
shadowType Object | CollectionShadow
  • optional
  • default: {}

Shadow subclass or object literal api definition. If object literal specified, each property and function is mapped onto a Shadow subclass.

typeCallback function(type: StateType)
  • optional

a callback function that will be passed the StateType spec for additional customization, such as setting autoshadow, initial state, or readonly.

initialState Object
  • optional

={} - the initial state for the new property.

Return:

ObjectProperty

newly defined ObjectProperty subclass.

public static defineType(PropClass: CollectionShadow, ShadowType: Object | CollectionShadow, typeCallback: function(type: StateType), initialState: Object): * source

Factory function for setting up the StateType type class variable with an appropriately configured intial state.

Example usage:

export default class TodosCollection extends CollectionProperty {
// implement property here
}

class TodosShadow extends CollectionShadow {
// implement shadow api here
}

ObjectProperty.defineType(TodosCollection, TodosShadow, type => {
// configure type variable
});

Params:

NameTypeAttributeDescription
PropClass CollectionShadow

CollectionShadow subclass

ShadowType Object | CollectionShadow
  • optional

Shadow` subclass or object literal api definition. If object literal specified, each property and function is mapped onto a Shadow subclass.

typeCallback function(type: StateType)
  • optional

a callback function that will be passed the StateType spec for additional customization, such as setting autoshadow, initial state, or readonly.

initialState Object
  • optional
  • default: {}

the initial state for the new property.

Return:

*

Public Constructors

public constructor(stateType: *) source

If a StateType is not passed to this constructor then one is located using StateType.from thus ensuring the f.lux shadowing process is defined for this property.

Override:

Property#constructor

Params:

NameTypeAttributeDescription
stateType *

Public Members

public get endpoint: Object: * source

Gets the endpoint for accessing the remote data source.

Return:

Object

public get endpointId: string: * source

Gets the endpoint ID, which for RestEndpointProperty is its URL.

Return:

string

public pagingTime: * source

public get size: * source

Gets the number of models contained in the collection.

Public Methods

public addModel(state: object, mergeOp: string): * source

Synchronously adds a new model object to the collection. Call model.$().save() to persist the newly added object.

Params:

NameTypeAttributeDescription
state object

the json model to add to the collection

mergeOp string
  • optional
  • default: REPLACE_OPTION

one of DEFAULTS_OPTION, MERGE_OPTION, or REPLACE_OPTION and specifies how to combine an existing model with a matching ID with a newly retrieved model.

Return:

*

the object's ID. And ID is assigned if the 'id' parameter was not set and it could not be found in the state parameter.

public addModels(models: array, mergeOp: string, syncOp: boolean) source

Bulk adds multiple models. Models must have an ID as it is assumed they have been previously saved.

Params:

NameTypeAttributeDescription
models array

array of model values

mergeOp string
  • optional
  • default: REPLACE_OPTION

one of DEFAULTS_OPTION, MERGE_OPTION, or REPLACE_OPTION and specifies how to combine an existing model with a matching ID with a newly retrieved model.

syncOp boolean
  • optional
  • default: true

sets the synced flag to true if this parameter is true

public clean(json: *): * source

Params:

NameTypeAttributeDescription
json *

Return:

*

public clearEndpoint() source

Removes the endpoint from the collection. This has the side-effect of clearing the mdoels.

public create(model: Object): Promise source

Combines an CollectionProperty#add and CollectionProperty#save actions.

Params:

NameTypeAttributeDescription
model Object

the json data

Return:

Promise

resolves with the f.lux shadow state for the new model

public destroy(id: *): Promise source

Permantently deletes the model with the endpoint and removes it from the collection.

Params:

NameTypeAttributeDescription
id *

the model ID to delete

Return:

Promise

resolves with the ID for the removed mdoel

public extractId(model: *): * source

Used by the private _shadow() method to get the id from the model JSON representation as returned by the subclass doXXX() apis. The default implementation simply returns the 'id' model property.

Params:

NameTypeAttributeDescription
model *

Return:

*

public fetch(filter: *, mergeOp: string, replaceAll: boolean, callback: *): Promise source

Fetches all the models from the endpoint.

Params:

NameTypeAttributeDescription
filter *
  • optional
  • default: null

filter object created using the endpoint.

mergeOp string
  • optional
  • default: REPLACE_OPTION

one of DEFAULTS_OPTION, MERGE_OPTION, or REPLACE_OPTION and specifies how to combine an existing model with a matching ID with a newly retrieved model.

replaceAll boolean
  • optional
  • default: true

set to true replace any current models by the ones returned by the endpoint.

callback *

invoked before retrieved models are process or in case of an error

Return:

Promise

resolves with the json models from the endpoint

public fetchNext(mergeOp: string): Promise source

Fetches the next set of models from the endpoint. This method differs from CollectionProperty#fetch by passing offset and limit filter criteria to the endpoint.

Params:

NameTypeAttributeDescription
mergeOp string
  • optional
  • default: REPLACE_OPTION

one of DEFAULTS_OPTION, MERGE_OPTION, or REPLACE_OPTION and specifies how to combine an existing model with a matching ID with a newly retrieved model.

Return:

Promise

resolves with a single argument of an array of model json objects as returned from the endpoint.

public find(id: *): Promise source

Gets a model by ID. The method looks for a matching model in the collection. If one is not found then one is requested from the endpoint.

Params:

NameTypeAttributeDescription
id *

the model ID

Return:

Promise

reolves with the model or undefined if one is not found

public getModel(id: *): Object source

Gets a model by ID. The method looks for a matching model in the collection and never looks for one remotely through the endpoint.

Params:

NameTypeAttributeDescription
id *

the model ID

Return:

Object

the model or undefined if one is not found

public getOfflineState(): Object source

this method is experimental.

Gets an object capable of providing a persisted version of this collection.

Return:

Object

public hasModel(id: *): boolean source

Gets if the collection contains a matching model.

Params:

NameTypeAttributeDescription
id *

the model ID

Return:

boolean

public hasMorePages(state: *): * source

Gets if additional paging calls will return additional results.

Params:

NameTypeAttributeDescription
state *
  • optional

Return:

*

public isAutocheckpoint(): boolean source

Sets whether auto-checkpointing is enabled.

Return:

boolean

public isConnected(): * source

Gets if the collection is active (has a shadow) and an endpoint.

Return:

*

public isFetching(): * source

Gets if a fetching operation that will replace ALL models is in progress.

Return:

*

public isNew(id: *): * source

Gets if a model has never been persisted to the endpoint.

Params:

NameTypeAttributeDescription
id *

Return:

*

public isNewModel(shadow: *): * source

Gets if a model shadow state model represents a model that has never been persisted to the endpoint.

Params:

NameTypeAttributeDescription
shadow *

Return:

*

public isPaging(state: *): * source

Gets if a paging operation (CollectionProperty#fetchNext) call is in progress.

Params:

NameTypeAttributeDescription
state *
  • optional

Return:

*

public makeId(): string source

Return:

string

public modelEntries(state: *): Array source

Gets an iterator with [ID, model] paris.

Params:

NameTypeAttributeDescription
state *

Return:

Array

public modelKeys(state: *): Iterator source

Gets an iterator containing each model IDs.

Params:

NameTypeAttributeDescription
state *
  • optional

Return:

Iterator

public modelKeysArray(state: *): Array source

Gets an array containing each model iDs.

Params:

NameTypeAttributeDescription
state *

Return:

Array

public modelValues(state: *): Iterator source

Gets an iterator containing each f.lux shadow state model.

Params:

NameTypeAttributeDescription
state *
  • optional

Return:

Iterator

public modelsArray(state: *): array source

Gets the shadow models currently managed by the collection.

Params:

NameTypeAttributeDescription
state *

Return:

array

all models being managed by the collection

public nextOffset(): * source

Gets the offset for the next paging request.

Return:

*

public remove(id: *) source

Synchronously removes the model from the collection without performing an endpoint operation.

Params:

NameTypeAttributeDescription
id *

the model id or cid

public removeAllModels() source

Removes all models from the collection and marks the collection as having not synched with the endpoint.

public resetPaging() source

Resets all internal paging tracking variables but does not affect currently stored models.

public save(id: *, mergeOp: string): Promise source

Saves a model through the endpoint.

Params:

NameTypeAttributeDescription
id *

the model id or cid

mergeOp string
  • optional
  • default: REPLACE_OPTION

one of DEFAULTS_OPTION, MERGE_OPTION, or REPLACE_OPTION and specifies how to combine an existing model with a matching ID with a newly retrieved model.

Return:

Promise

resolves to the f.lux shadow state for the saved model

public setAutocheckpoint(auto: boolean) source

Sets whether auto-checkpointing should be enabled.

Params:

NameTypeAttributeDescription
auto boolean

true to enable.

public setEndpoint(endPoint: *) source

Sets the CollectionProperty#endpoint.

Params:

NameTypeAttributeDescription
endPoint *

public setIdName(idName: *) source

Sets the property name containing the model ID. Default is id.

Params:

NameTypeAttributeDescription
idName *

public setLimit(limit: number) source

Sets the number of models to request with each paging request. The default paging size is 50.

Params:

NameTypeAttributeDescription
limit number

public setModels(models: array, syncOp: boolean) source

Bulk replaces current models with an array of new models.

Params:

NameTypeAttributeDescription
models array

array of model values

syncOp boolean
  • optional
  • default: true

sets the synced flag to true if this parameter is true

public setOfflineState(offline: Object) source

this method is experimental.

Sets an object capable of providing a persisted version of this collection. The object must minimally expose a single method with the form:

function restore()

Method sets the collection state for offline access. Typically invoked by application logic after a failed fetch() to the endpoint.

An object is used as the offline state management entity because it will normally perform other duties such as registering for ChangeEvent to persistently store collection state on changes and support deleting previous backups

Params:

NameTypeAttributeDescription
offline Object

the object containing the restore() function.

public use(op: *, mw: *) source

Registers collection middleware operation. A middleware operation is invoked before each asynchronous/ network operation. Middleware operations are functions with the following format:

function mwCallback(collectionShadow, collectionProperty)

Middleware functions must return a promise and are invoked in the order registered. A function generating an error will terminate the middleware chain and the collection operation will not be performed.

Params:

NameTypeAttributeDescription
op *
mw *