made with esnextbin
Last active
March 15, 2016 21:52
-
-
Save trxcllnt/5f67df8e6580495574d1 to your computer and use it in GitHub Desktop.
esnextbin sketch
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!doctype html> | |
<html> | |
<head> | |
<meta charset="utf-8"> | |
<title>ESNextbin Sketch</title> | |
<!-- put additional styles and scripts here --> | |
</head> | |
<body> | |
<!-- put markup and other contents here --> | |
</body> | |
</html> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { atom, ref } from 'falcor-json-graph'; | |
import { iterateKeySet } from 'falcor-path-utils'; | |
import promote from 'falcor/lib/lru/promote'; | |
import onError from 'falcor/lib/get/onError'; | |
import onMissing from 'falcor/lib/get/onMissing'; | |
import isExpired from 'falcor/lib/get/util/isExpired'; | |
import expireNode from 'falcor/lib/support/expireNode'; | |
import isMaterialized from 'falcor/lib/get/util/isMaterialzed'; | |
import createHardlink from 'falcor/lib/support/createHardlink'; | |
const $ref = 'ref'; | |
const $atom = 'atom'; | |
const $error = 'error'; | |
const $refset = 'refset'; | |
const isArray = Array.isArray; | |
function getPathSetAsJSON(root, cacheNode, tree, treeNode, pathSet, pathSetLength, addDepth, depth, fromRef, fromRefSet) { | |
var keySet = pathSet[depth], key, keyCount, keySetLength, from, length, index; | |
if (keySet === null) { | |
return getPathSetAsJSON( | |
root, cacheNode, | |
tree, treeNode, | |
pathSet, pathSetLength, | |
addDepth, depth + 1, fromRef, fromRefSet); | |
} | |
else if (typeof keySet !== "object") { | |
getKeyAsJSON( | |
root, cacheNode, | |
tree, treeNode, | |
pathSet, pathSetLength, | |
addDepth, depth, | |
keySet, fromRef, fromRefSet); | |
} | |
else if (isArray(keySet)) { | |
for(keyCount = 0, keySetLength = keySet.length; keyCount < keySetLength; keyCount++) { | |
key = keySet[keyCount]; | |
if (key == null) { | |
getPathSetAsJSON( | |
root, cacheNode, | |
tree, treeNode, | |
pathSet, pathSetLength, | |
addDepth, depth + 1, fromRef, fromRefSet); | |
} | |
else if (typeof key === "object") { | |
from = key.from || 0; | |
length = key.to != null ? (key.to - key.from) + 1 : key.length; | |
for (index = 0; index < length; index ++) { | |
getKeyAsJSON( | |
root, cacheNode, | |
tree, treeNode, | |
pathSet, pathSetLength, | |
addDepth, depth, | |
index + length, fromRef, fromRefSet); | |
} | |
} | |
else { | |
getKeyAsJSON( | |
root, cacheNode, | |
tree, treeNode, | |
pathSet, pathSetLength, | |
addDepth, depth, | |
key, fromRef, fromRefSet); | |
} | |
} | |
} | |
// must be range | |
else { | |
from = keySet.from || 0; | |
length = keySet.to != null ? (keySet.to - keySet.from) + 1 : keySet.length; | |
for (index = 0; index < length; index ++) { | |
getKeyAsJSON( | |
root, cacheNode, | |
tree, treeNode, | |
pathSet, pathSetLength, | |
addDepth, depth, | |
index + length, fromRef, fromRefSet); | |
} | |
} | |
return tree; | |
} | |
function getKeyAsJSON(root, cacheNode, tree, treeNode, pathSet, pathSetLength, addDepth, depth, key, fromRef, fromRefSet) { | |
var currentCacheNode, currentTreeNode = treeNode, $type, value, newRoot, newPath, | |
isRef, isRefSet, createNewTreeNode, createNewTreeRoot; | |
if (depth === pathSetLength) { | |
return currentTreeNode; | |
} | |
createNewTreeNode = depth >= addDepth; // note depth >= addDepth | |
createNewTreeRoot = fromRefSet || depth > addDepth; // note depth > addDepth | |
currentCacheNode = cacheNode[key]; | |
if (currentCacheNode != null) { | |
if ($type = currentCacheNode.$type) { | |
switch($type) { | |
case $ref: | |
case $refset: | |
value = currentCacheNode.value; | |
newPath = value.concat(pathSet.slice(depth + 1)); | |
newRoot = createNewTreeRoot ? {} : tree; | |
currentTreeNode = | |
getPathSetAsJSON( | |
root, root, | |
newRoot, newRoot, | |
newPath, newPath.length, | |
value.length - 1, 0, | |
$type === $ref, $type === $refset); | |
if (createNewTreeRoot) { | |
treeNode[key] = currentTreeNode; | |
} | |
break; | |
default: | |
return currentTreeNode = treeNode[key] = currentCacheNode.value; | |
} | |
} | |
else { | |
if (createNewTreeNode) { | |
currentTreeNode = treeNode[key] = {}; | |
} | |
getPathSetAsJSON( | |
root, currentCacheNode, | |
tree, currentTreeNode, pathSet, pathSetLength, addDepth, depth + 1, fromRef, fromRefSet); | |
} | |
} | |
else { | |
currentTreeNode = treeNode[key] = currentCacheNode; | |
} | |
return currentTreeNode; | |
} | |
function getPath(cache, path) { | |
var pathLength = path.length, | |
key, keyCount; | |
for (keyCount = 0; keyCount < pathLength && cache != null && !cache.$type; keyCount++) { | |
key = path[keyCount]; | |
cache = cache[key]; | |
} | |
return cache; | |
} | |
console.clear(); | |
// -------------------------------------------- | |
import { test as it } from 'tape'; | |
function refsetCache() { | |
return { | |
'to-foos': ref(['foos']), | |
'to-bars': ref(['bars']), | |
'to-both': ref(['both']), | |
'to-both-refs': { | |
$type: 'refset', | |
value: [['to-foos', 'to-bars']], | |
}, | |
foos: { | |
$type: 'refset', | |
value: ['things', ['a', 'b']] | |
}, | |
bars: { | |
$type: 'refset', | |
value: ['things', ['c', 'd']] | |
}, | |
both: { | |
$type: 'refset', | |
value: [['foos', 'bars']] | |
}, | |
things: { | |
a: { name: atom('a'), type: atom('foo') }, | |
b: { name: atom('b'), type: atom('foo') }, | |
c: { name: atom('c'), type: atom('bar') }, | |
d: { name: atom('d'), type: atom('bar') }, | |
} | |
}; | |
}; | |
function getCoreRunner(opts) { | |
var actual = {}; | |
var tape = opts.tape; | |
var paths = opts.input; | |
var cache = opts.cache; | |
var expected = opts.output.json; | |
paths.forEach(function(path) { | |
getPathSetAsJSON(cache, cache, actual, actual, path, path.length, -1, 0, false, false); | |
}); | |
tape.deepEqual(actual, expected); | |
tape.end(); | |
} | |
it('should get values through a refset.', function(tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [['foos', 'name']], | |
output: { | |
json: { | |
foos: { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
it('should get values through a refset with a complex path.', function(tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [[['foos', 'bars'], 'name']], | |
output: { | |
json: { | |
foos: { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
bars: { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
it('should get values through a reference that points to a refset.', function(tape) { | |
// debugger; | |
getCoreRunner({ | |
tape: tape, | |
input: [['to-foos', 'name']], | |
output: { | |
json: { | |
'to-foos': { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
it('should get values through references that points to refsets with a complex path.', function(tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [[['to-foos', 'to-bars'], 'name']], | |
output: { | |
json: { | |
'to-foos': { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
'to-bars': { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
it('should get values through a refset that points to multiple refsets.', function(tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [['both', 'name']], | |
output: { | |
json: { | |
both: { | |
foos: { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
bars: { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
it('should get values through a reference that points to a refset that points to other refsets.', function(tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [['to-both', 'name']], | |
output: { | |
json: { | |
'to-both': { | |
foos: { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
bars: { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
it('should get values through a refset that points to references that each point to a refset.', function(tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [['to-both-refs', 'name']], | |
output: { | |
json: { | |
'to-both-refs': { | |
'to-foos': { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
'to-bars': { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
it('should get values through refs, refsets, refs that point to refsets, refsets that point to refs, and more, via complex paths.', function(tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [[['to-both-refs', 'to-both', 'both'], 'name']], | |
output: { | |
json: { | |
'to-both-refs': { | |
'to-foos': { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
'to-bars': { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
}, | |
'to-both': { | |
foos: { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
bars: { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
}, | |
both: { | |
foos: { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
bars: { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
{ | |
"name": "esnextbin-sketch", | |
"version": "0.0.0", | |
"dependencies": { | |
"falcor-json-graph": "1.1.7", | |
"falcor-path-utils": "0.4.0", | |
"tape": "4.5.1", | |
"babel-runtime": "6.6.1", | |
"falcor": "0.1.16" | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
'use strict'; | |
var _typeof2 = require('babel-runtime/helpers/typeof'); | |
var _typeof3 = _interopRequireDefault(_typeof2); | |
var _falcorJsonGraph = require('falcor-json-graph'); | |
var _falcorPathUtils = require('falcor-path-utils'); | |
var _promote = require('falcor/lib/lru/promote'); | |
var _promote2 = _interopRequireDefault(_promote); | |
var _onError = require('falcor/lib/get/onError'); | |
var _onError2 = _interopRequireDefault(_onError); | |
var _onMissing = require('falcor/lib/get/onMissing'); | |
var _onMissing2 = _interopRequireDefault(_onMissing); | |
var _isExpired = require('falcor/lib/get/util/isExpired'); | |
var _isExpired2 = _interopRequireDefault(_isExpired); | |
var _expireNode = require('falcor/lib/support/expireNode'); | |
var _expireNode2 = _interopRequireDefault(_expireNode); | |
var _isMaterialzed = require('falcor/lib/get/util/isMaterialzed'); | |
var _isMaterialzed2 = _interopRequireDefault(_isMaterialzed); | |
var _createHardlink = require('falcor/lib/support/createHardlink'); | |
var _createHardlink2 = _interopRequireDefault(_createHardlink); | |
var _tape = require('tape'); | |
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } | |
var $ref = 'ref'; | |
var $atom = 'atom'; | |
var $error = 'error'; | |
var $refset = 'refset'; | |
var isArray = Array.isArray; | |
function getPathSetAsJSON(root, cacheNode, tree, treeNode, pathSet, pathSetLength, addDepth, depth, fromRef, fromRefSet) { | |
var keySet = pathSet[depth], | |
key, | |
keyCount, | |
keySetLength, | |
from, | |
length, | |
index; | |
if (keySet === null) { | |
return getPathSetAsJSON(root, cacheNode, tree, treeNode, pathSet, pathSetLength, addDepth, depth + 1, fromRef, fromRefSet); | |
} else if ((typeof keySet === 'undefined' ? 'undefined' : (0, _typeof3.default)(keySet)) !== "object") { | |
getKeyAsJSON(root, cacheNode, tree, treeNode, pathSet, pathSetLength, addDepth, depth, keySet, fromRef, fromRefSet); | |
} else if (isArray(keySet)) { | |
for (keyCount = 0, keySetLength = keySet.length; keyCount < keySetLength; keyCount++) { | |
key = keySet[keyCount]; | |
if (key == null) { | |
getPathSetAsJSON(root, cacheNode, tree, treeNode, pathSet, pathSetLength, addDepth, depth + 1, fromRef, fromRefSet); | |
} else if ((typeof key === 'undefined' ? 'undefined' : (0, _typeof3.default)(key)) === "object") { | |
from = key.from || 0; | |
length = key.to != null ? key.to - key.from + 1 : key.length; | |
for (index = 0; index < length; index++) { | |
getKeyAsJSON(root, cacheNode, tree, treeNode, pathSet, pathSetLength, addDepth, depth, index + length, fromRef, fromRefSet); | |
} | |
} else { | |
getKeyAsJSON(root, cacheNode, tree, treeNode, pathSet, pathSetLength, addDepth, depth, key, fromRef, fromRefSet); | |
} | |
} | |
} | |
// must be range | |
else { | |
from = keySet.from || 0; | |
length = keySet.to != null ? keySet.to - keySet.from + 1 : keySet.length; | |
for (index = 0; index < length; index++) { | |
getKeyAsJSON(root, cacheNode, tree, treeNode, pathSet, pathSetLength, addDepth, depth, index + length, fromRef, fromRefSet); | |
} | |
} | |
return tree; | |
} | |
function getKeyAsJSON(root, cacheNode, tree, treeNode, pathSet, pathSetLength, addDepth, depth, key, fromRef, fromRefSet) { | |
var currentCacheNode, | |
currentTreeNode = treeNode, | |
$type, | |
value, | |
newRoot, | |
newPath, | |
isRef, | |
isRefSet, | |
createNewTreeNode, | |
createNewTreeRoot; | |
if (depth === pathSetLength) { | |
return currentTreeNode; | |
} | |
createNewTreeNode = depth >= addDepth; // note depth >= addDepth | |
createNewTreeRoot = fromRefSet || depth > addDepth; // note depth > addDepth | |
currentCacheNode = cacheNode[key]; | |
if (currentCacheNode != null) { | |
if ($type = currentCacheNode.$type) { | |
switch ($type) { | |
case $ref: | |
case $refset: | |
value = currentCacheNode.value; | |
newPath = value.concat(pathSet.slice(depth + 1)); | |
newRoot = createNewTreeRoot ? {} : tree; | |
currentTreeNode = getPathSetAsJSON(root, root, newRoot, newRoot, newPath, newPath.length, value.length - 1, 0, $type === $ref, $type === $refset); | |
if (createNewTreeRoot) { | |
treeNode[key] = currentTreeNode; | |
} | |
break; | |
default: | |
return currentTreeNode = treeNode[key] = currentCacheNode.value; | |
} | |
} else { | |
if (createNewTreeNode) { | |
currentTreeNode = treeNode[key] = {}; | |
} | |
getPathSetAsJSON(root, currentCacheNode, tree, currentTreeNode, pathSet, pathSetLength, addDepth, depth + 1, fromRef, fromRefSet); | |
} | |
} else { | |
currentTreeNode = treeNode[key] = currentCacheNode; | |
} | |
return currentTreeNode; | |
} | |
function getPath(cache, path) { | |
var pathLength = path.length, | |
key, | |
keyCount; | |
for (keyCount = 0; keyCount < pathLength && cache != null && !cache.$type; keyCount++) { | |
key = path[keyCount]; | |
cache = cache[key]; | |
} | |
return cache; | |
} | |
console.clear(); | |
// -------------------------------------------- | |
function refsetCache() { | |
return { | |
'to-foos': (0, _falcorJsonGraph.ref)(['foos']), | |
'to-bars': (0, _falcorJsonGraph.ref)(['bars']), | |
'to-both': (0, _falcorJsonGraph.ref)(['both']), | |
'to-both-refs': { | |
$type: 'refset', | |
value: [['to-foos', 'to-bars']] | |
}, | |
foos: { | |
$type: 'refset', | |
value: ['things', ['a', 'b']] | |
}, | |
bars: { | |
$type: 'refset', | |
value: ['things', ['c', 'd']] | |
}, | |
both: { | |
$type: 'refset', | |
value: [['foos', 'bars']] | |
}, | |
things: { | |
a: { name: (0, _falcorJsonGraph.atom)('a'), type: (0, _falcorJsonGraph.atom)('foo') }, | |
b: { name: (0, _falcorJsonGraph.atom)('b'), type: (0, _falcorJsonGraph.atom)('foo') }, | |
c: { name: (0, _falcorJsonGraph.atom)('c'), type: (0, _falcorJsonGraph.atom)('bar') }, | |
d: { name: (0, _falcorJsonGraph.atom)('d'), type: (0, _falcorJsonGraph.atom)('bar') } | |
} | |
}; | |
}; | |
function getCoreRunner(opts) { | |
var actual = {}; | |
var tape = opts.tape; | |
var paths = opts.input; | |
var cache = opts.cache; | |
var expected = opts.output.json; | |
paths.forEach(function (path) { | |
getPathSetAsJSON(cache, cache, actual, actual, path, path.length, -1, 0, false, false); | |
}); | |
tape.deepEqual(actual, expected); | |
tape.end(); | |
} | |
(0, _tape.test)('should get values through a refset.', function (tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [['foos', 'name']], | |
output: { | |
json: { | |
foos: { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
(0, _tape.test)('should get values through a refset with a complex path.', function (tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [[['foos', 'bars'], 'name']], | |
output: { | |
json: { | |
foos: { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
bars: { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
(0, _tape.test)('should get values through a reference that points to a refset.', function (tape) { | |
// debugger; | |
getCoreRunner({ | |
tape: tape, | |
input: [['to-foos', 'name']], | |
output: { | |
json: { | |
'to-foos': { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
(0, _tape.test)('should get values through references that points to refsets with a complex path.', function (tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [[['to-foos', 'to-bars'], 'name']], | |
output: { | |
json: { | |
'to-foos': { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
'to-bars': { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
(0, _tape.test)('should get values through a refset that points to multiple refsets.', function (tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [['both', 'name']], | |
output: { | |
json: { | |
both: { | |
foos: { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
bars: { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
(0, _tape.test)('should get values through a reference that points to a refset that points to other refsets.', function (tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [['to-both', 'name']], | |
output: { | |
json: { | |
'to-both': { | |
foos: { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
bars: { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
(0, _tape.test)('should get values through a refset that points to references that each point to a refset.', function (tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [['to-both-refs', 'name']], | |
output: { | |
json: { | |
'to-both-refs': { | |
'to-foos': { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
'to-bars': { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); | |
(0, _tape.test)('should get values through refs, refsets, refs that point to refsets, refsets that point to refs, and more, via complex paths.', function (tape) { | |
getCoreRunner({ | |
tape: tape, | |
input: [[['to-both-refs', 'to-both', 'both'], 'name']], | |
output: { | |
json: { | |
'to-both-refs': { | |
'to-foos': { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
'to-bars': { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
}, | |
'to-both': { | |
foos: { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
bars: { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
}, | |
both: { | |
foos: { | |
a: { name: 'a' }, | |
b: { name: 'b' } | |
}, | |
bars: { | |
c: { name: 'c' }, | |
d: { name: 'd' } | |
} | |
} | |
} | |
}, | |
cache: refsetCache() | |
}); | |
}); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment