jashkenas/backbone · error · Error
Cannot sort a set without a comparator
Error message
Cannot sort a set without a comparator
What it means
Backbone's Collection.sort() requires the collection to have a comparator, which defines the ordering of models. If this.comparator is falsy, Backbone deliberately throws this error instead of silently leaving the collection unsorted. The comparator can be a function or a string naming an attribute to sort by.
Source
Thrown at backbone.js:1045
// Return models with matching attributes. Useful for simple cases of
// `filter`.
where: function(attrs, first) {
return this[first ? 'find' : 'filter'](attrs);
},
// Return the first model with matching attributes. Useful for simple cases
// of `find`.
findWhere: function(attrs) {
return this.where(attrs, true);
},
// Force the collection to re-sort itself. You don't need to call this under
// normal circumstances, as the set will maintain sort order as each item
// is added.
sort: function(options) {
var comparator = this.comparator;
if (!comparator) throw new Error('Cannot sort a set without a comparator');
options || (options = {});
var length = comparator.length;
if (_.isFunction(comparator)) comparator = comparator.bind(this);
// Run sort based on type of `comparator`.
if (length === 1 || _.isString(comparator)) {
this.models = this.sortBy(comparator);
} else {
this.models.sort(comparator);
}
if (!options.silent) this.trigger('sort', this, options);
return this;
},
// Pluck an attribute from each model in the collection.
pluck: function(attr) {
return this.map(attr + '');View on GitHub (pinned to f229c75b19)
Solutions
- Define a comparator on the collection: 'comparator: "name"' (sort by attribute) or 'comparator: function(m){ return m.get("name"); }'.
- Pass a comparator at construction: new Backbone.Collection(models, {comparator: 'id'}).
- Use a string comparator naming a model attribute if a custom function isn't needed.
- Before sorting, guard: if (!collection.comparator) collection.comparator = 'name'; then call collection.sort().
- If ordering doesn't matter, remove the sort() call instead of sorting a comparator-less collection.
Example fix
// before
var c = new Backbone.Collection(models);
c.sort(); // throws: Cannot sort a set without a comparator
// after
var c = new Backbone.Collection(models, {comparator: 'name'});
c.sort(); // works Defensive patterns
Strategy: validation
Validate before calling
function canSort(collection) {
return typeof collection === 'object' && collection != null &&
(typeof collection.comparator === 'function' || typeof collection.comparator === 'string');
}
if (!canSort(myCollection)) myCollection.comparator = 'name';
myCollection.sort(); Type guard
function hasComparator(c) {
return c instanceof Backbone.Collection &&
(typeof c.comparator === 'function' || typeof c.comparator === 'string');
} Try / catch
try {
collection.sort();
} catch (e) {
if (e.message === 'Cannot sort a set without a comparator') {
collection.comparator = 'name';
collection.sort();
} else { throw e; }
} Prevention
- Always declare comparator as a property of the Collection definition, not set ad hoc.
- Prefer string comparators ('attrName') when a simple attribute sort suffices.
- Add a unit test that sorts every collection used in the app.
- When constructing collections dynamically, pass {comparator: ...} in options.
- Never rely on add()/fetch() to maintain order without a comparator present.
When it happens
Trigger: Calling collection.sort() on a Collection instance whose constructor options, 'comparator' property, or set() call never defined a comparator; also triggered internally by add/fetch with {sort:true} options on a comparator-less collection.
Common situations: Defining a comparator on the wrong object (e.g., on a plain object instead of the Collection class or prototype); building collections dynamically without a comparator then calling sort(); upgrading Backbone and relying on a comparator set via attributes rather than as a class property; copying collection code and omitting the comparator.
Related errors
AI-assisted analysis of jashkenas/backbone@f229c75b19 (2026-08-28).
Data as JSON: /api/errors/1e27622d34312c0a.
Report an issue: GitHub.