JSFiddle - React, Tailwind, and code Playground
by Tomalak
HTML
<script src="//cdnjs.cloudflare.com/ajax/libs/linq.js/2.2.0.2/linq.min.js "></script>
<h3>Before</h3>
<pre id="before"></pre>
<hr>
<h3>After</h3>
<pre id="after"></pre>
JavaScript
// Enumerable, definition => Enumerable
function applyOrder(items, definition) {
var i, prop, prefix, suffix, orderFunc;
if (!items) return;
if (!definition) return items;
for (i = 0; i < definition.length; i++) {
// definition[i] is either "propertyName" or "propertyName DESC"
prop = (definition[i] + " ").split(" ");
prefix = i === 0 ? "OrderBy" : "ThenBy";
suffix = prop[1].toUpperCase() === "DESC" ? "Descending" : "";
orderFunc = prefix + suffix;
items = items[orderFunc]("$." + prop[0]);
}
return items;
}
// Enumerable, definition => Enumerable
function applyGroup(items, definition) {
if (!items) return;
if (!definition) return items;
items = applyOrder(items, definition.order);
if (!definition.group) return items;
return items.GroupBy("$." + definition.group, "", function (key, e) {
return {
group: definition.group,
key: key,
items: applyGroup(e, definition.then).ToArray()
};
});
}
// Array, definition => Array
function applyStructure(items, definition) {
if (!items) return;
if (!definition) return items;
return applyGroup(Enumerable.From(items), definition).ToArray();
}
// list of items
var companies = [{
country: "Mexico",
city: "México D.F.",
companyName: "Ana Trujillo ..."
}, {
country: "Mexico",
city: "México D.F.",
companyName: "Antonio Moreno ..."
}, {
country: "Mexico",
city: "México D.F.",
companyName: "Centro Comercial ..."
}, {
country: "USA",
city: "Charlotte",
companyName: "Bank of America"
}];
var result = applyStructure(companies, {
group: "country",
order: ["country"],
then: {
group: "city",
order: ["city"],
then: {
order: [
"companyName DESC"
/* note that you can add more order clauses per...