Skip to content

Instantly share code, notes, and snippets.

@iros
Last active May 17, 2017 22:28
Show Gist options
  • Save iros/4689365 to your computer and use it in GitHub Desktop.
Save iros/4689365 to your computer and use it in GitHub Desktop.
Backbone.sync override to use in memory storage with deferred support
Backbone.sync = function(method, model, options) {
// we need to make sure we initialize a store, in this case
// we will just use a JS object.
var cache = {};
// The size will be primarily used to assign ids to newly
// created models. Each time a new model is created, the size
// will be incremented.
var size = 0;
// since we need to create a store for the models/collections
// we are actually going to invoke the outer function which will
// return this function below as the Backbone.sync that will
// actually be used.
return function(method, model, options) {
// create a new deferred object. standard sync returns the $.ajax
// request, which internally returns a deferred. It's important to
// do this so that people can chain on fetch using the standard .then/.fail
// syntax, rather than just the success/error callbacks.
var deferred = $.Deferred();
// when creating a new model...
if (method === "create") {
// first assign it an id. The server would traditionally do this.
model.id = size;
// store it in our cache
cache[model.id] = model;
// make sure we increment the number of models we now have.
size += 1;
// if a success callback was provided, execute it.
if (options.success) {
options.success(model, model.toJSON(), options);
}
// resolve the deferred.
deferred.resolve(model);
// we are updating a model
} else if (method === "update") {
// as long as the model actually exists in our store
if (cache[model.id]) {
// overwrite what is currently in the store with this model.
cache[model.id] = model;
// if a success callback was provided, execute it.
if (options.success) {
options.success(model, model.toJSON(), options);
}
deferred.resolve(model);
// if this model doesn't exist yet, we can't update it
} else {
if (options.error) {
options.error(model, "Model not found");
}
deferred.reject(model);
}
// if we're trying to read a model...
} else if (method === "read") {
// as long as it exists
if (cache[model.id]) {
// if a success callback was provided, execute it.
if (options.success) {
options.success(model, cache[model.id].toJSON(), options);
}
// resolve
deferred.resolve(model);
} else {
if (options.error) {
options.error(model, "Model not found");
}
deferred.reject(model);
}
// if we're deleting a model...
} else if (method === "delete") {
// first make sure it exists in the cache
if (cache[model.id]) {
// then remove it from the cache
delete cache[model.id];
// and trigger the success callback. Note we're passing an
// empty object as the second argument, because a deletion
// would result in an empty return from the server.
if (options.success) {
options.success(model, {}, options);
}
// resolve the deferred
deferred.resolve(model);
// otherwise, error that the model doesn't exist.
} else {
if (options.error) {
options.error(model, "Model not found");
}
deferred.reject(model);
}
}
return deferred.promise();
}
}();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment