Your callback is breaking the contract: It doesn't return anything if catname is the same on the two objects you're comparing. And separate from breaking the contract, that's also why it's not working correctly.
This is a standard case of a multi-key sort, which you do by the first key, then the second key, etc. For instance, this sorts by catname (ascending) and, within catnames, by dish_sort_id (descending, as that seemed to be what your code did):
A.sort(function(a,b){
var rv = a.catname.localeCompare(b.catname);
if (rv == 0) {
// Same name, use the dish_sort_id
rv = b.dish_sort_id - a.dish_sort_id;
}
return rv;
});
Live example:
var name1 = randomName();
var name2 = randomName();
var A = [
{ catname: name2, dish_sort_id: randomNumber() },
{ catname: name1, dish_sort_id: randomNumber() },
{ catname: name1, dish_sort_id: randomNumber() },
{ catname: name2, dish_sort_id: randomNumber() },
{ catname: name2, dish_sort_id: randomNumber() },
{ catname: name1, dish_sort_id: randomNumber() }
];
show("Before", A);
A.sort(function(a,b){
var rv = a.catname.localeCompare(b.catname);
if (rv == 0) {
// Same name, use the dish_sort_id
rv = b.dish_sort_id - a.dish_sort_id;
}
return rv;
});
snippet.log("----");
show("After", A);
function show(label, a) {
snippet.log(label + ":");
A.forEach(function(entry) {
snippet.log(entry.catname + " - " + entry.dish_sort_id);
});
}
function randomName() {
var rv = "";
while (rv.length < 5) {
rv += String.fromCharCode(65 + Math.floor(Math.random() * 26));
}
return rv;
}
function randomNumber() {
return Math.floor(Math.random() * 10);
}
<!-- Script provides the `snippet` object, see http://meta.stackexchange.com/a/242144/134069 -->
<script src="http://tjcrowder.github.io/simple-snippets-console/snippet.js"></script>
aandbguaranteed to have equalcatnamefor all entries - why do you still compare them? And if they are not - where is the correspondingreturnfor such a case?undefinedin case if they are different? Are you aware thatArray.prototype.sort()callback MUST return one of{-1, 0, 1}?a.catname == b.catnamecomparison is not true?