decentralized-internet
Version:
An NPM library of programs to create decentralized web and distributed computing projects
1 lines • 2.43 kB
JavaScript
;const Hoek=require("@hapi/hoek"),internals={};module.exports=class{constructor(){this._items=[],this.nodes=[]}add(e,t){const s=[].concat((t=t||{}).before||[]),o=[].concat(t.after||[]),n=t.group||"?",r=t.sort||0;Hoek.assert(!s.includes(n),`Item cannot come before itself: ${n}`),Hoek.assert(!s.includes("?"),"Item cannot come before unassociated items"),Hoek.assert(!o.includes(n),`Item cannot come after itself: ${n}`),Hoek.assert(!o.includes("?"),"Item cannot come after unassociated items"),[].concat(e).forEach((e,t)=>{const c={seq:this._items.length,sort:r,before:s,after:o,group:n,node:e};this._items.push(c)});const c=this._sort();return Hoek.assert(!c,"item","?"!==n?`added into group ${n}`:"","created a dependencies error"),this.nodes}merge(e){e=[].concat(e);for(let t=0;t<e.length;++t){const s=e[t];if(s)for(let e=0;e<s._items.length;++e){const t=Object.assign({},s._items[e]);this._items.push(t)}}this._items.sort(internals.mergeSort);for(let e=0;e<this._items.length;++e)this._items[e].seq=e;const t=this._sort();return Hoek.assert(!t,"merge created a dependencies error"),this.nodes}_sort(){const e={},t=Object.create(null),s=Object.create(null);for(let o=0;o<this._items.length;++o){const n=this._items[o],r=n.seq,c=n.group;s[c]=s[c]||[],s[c].push(r),e[r]=n.before;const i=n.after;for(let e=0;e<i.length;++e)t[i[e]]=(t[i[e]]||[]).concat(r)}let o=Object.keys(e);for(let t=0;t<o.length;++t){const n=o[t],r=[],c=Object.keys(e[n]);for(let t=0;t<c.length;++t){const o=e[n][c[t]];s[o]=s[o]||[];for(let e=0;e<s[o].length;++e)r.push(s[o][e])}e[n]=r}const n=Object.keys(t);for(let o=0;o<n.length;++o){const r=n[o];if(s[r])for(let o=0;o<s[r].length;++o){const n=s[r][o];e[n]=e[n].concat(t[r])}}let r;const c={};o=Object.keys(e);for(let t=0;t<o.length;++t){const s=o[t];r=e[s];for(let e=0;e<r.length;++e)c[r[e]]=(c[r[e]]||[]).concat(s)}const i={},l=[];for(let e=0;e<this._items.length;++e){let t=e;if(c[e]){t=null;for(let e=0;e<this._items.length;++e){if(!0===i[e])continue;c[e]||(c[e]=[]);const s=c[e].length;let o=0;for(let t=0;t<s;++t)i[c[e][t]]&&++o;if(o===s){t=e;break}}}null!==t&&(i[t]=!0,l.push(t))}if(l.length!==this._items.length)return new Error("Invalid dependencies");const h={};for(let e=0;e<this._items.length;++e){const t=this._items[e];h[t.seq]=t}const a=[];this._items=l.map(e=>{const t=h[e];return a.push(t.node),t}),this.nodes=a}},internals.mergeSort=((e,t)=>e.sort===t.sort?0:e.sort<t.sort?-1:1);