@tangle/reduce
Advanced tools
Comparing version 3.0.1 to 3.1.0
65
index.js
@@ -10,3 +10,3 @@ const Graph = require('@tangle/graph') | ||
nodes = [], | ||
getTransformation = node => node, | ||
getTransformation = (node, distance) => node, | ||
getBacklinks = node => node.previous, | ||
@@ -19,5 +19,5 @@ isValid | ||
this.getT = (nodeId) => { | ||
this.getT = (nodeId, distance) => { | ||
return strategy.mapToPure( | ||
getTransformation(this.graph.getNode(nodeId)) | ||
getTransformation(this.graph.getNode(nodeId), distance) | ||
) | ||
@@ -34,3 +34,3 @@ } | ||
resolve () { | ||
if (this._state) return this._resolvedState | ||
if (this._resolvedState) return this._resolvedState | ||
@@ -40,6 +40,6 @@ const { graph, strategy, getT, isValid } = this | ||
const queue = new Queue() | ||
// a queue made up of elements { nodeId, accT } | ||
// nodeId = the unique identifier for a node | ||
// accT = the accumulated (concat'd) Transformation up to and including the Transformation | ||
// described in node 'nodeId' | ||
// a queue made up of objects { nodeId, accT, d } representing position in graph: | ||
// - nodeId = the unique identifier for a node | ||
// - accT = the accumulated (concat'd) Transformation up to and including node `nodeId` | ||
// - d = distance from root, in a merge it increases to be longer than the longest path | ||
@@ -56,6 +56,8 @@ if (isValid) { | ||
// seed the queue with starting node(s) | ||
graph.rootNodeKeys.forEach(key => { | ||
queue.add({ | ||
nodeId: key, | ||
accT: getT(key) | ||
accT: getT(key, 0), | ||
d: 0 | ||
}) | ||
@@ -72,3 +74,3 @@ }) | ||
while (!queue.isEmpty()) { | ||
const { nodeId, accT } = queue.next() | ||
const { nodeId, accT, d } = queue.next() | ||
// accT is the accumulated Transformation so far | ||
@@ -95,10 +97,11 @@ // (NOT including Transformation stored in key though, that's what we're ) | ||
nodeId: nextId, | ||
accT: strategy.concat(accT, getT(nextId)) | ||
accT: strategy.concat(accT, getT(nextId, d + 1)), | ||
d: d + 1 | ||
}) | ||
// queue up the another node to explore from | ||
} else { | ||
tips.preMerge.set(nodeId, accT) | ||
tips.preMerge.set(nodeId, { accT, d }) | ||
const requiredKeys = graph.getBacklinks(nextId) | ||
const ready = requiredKeys.every(nodeId => tips.preMerge.has(nodeId)) | ||
const requiredNodeIds = graph.getBacklinks(nextId) | ||
const ready = requiredNodeIds.every(nodeId => tips.preMerge.has(nodeId)) | ||
// check tips.preMerge store to see if we now have the state needed to complete merge | ||
@@ -109,9 +112,15 @@ | ||
if (Object.keys(this.strategy._composition).length) { | ||
// this is for group tangle reducing where we using this machinary, | ||
// this is for group tangle reducing where we use this machinary, | ||
// but are not handling any transformations, so "merges" are safe | ||
console.warn('! WARNING ! - reducing merges safely is not yet fully working') | ||
} | ||
// const preMergeTransformations = requiredKeys.map(nodeId => tips.preMerge.get(nodeId)) | ||
const mergeTransformation = getT(nextId) | ||
const maxD = requiredNodeIds | ||
.map(nodeId => tips.preMerge.get(nodeId).d) | ||
.reduce((acc, d) => d > acc ? d : acc, 0) | ||
const mergeTransformation = getT(nextId, maxD + 1) | ||
// const preMergeTransformations = requiredNodeIds.map(nodeId => tips.preMerge.get(nodeId).accT) | ||
// ALGORITHM: | ||
@@ -125,8 +134,17 @@ // is there a conflict between tips (preMergeTransformations) ? | ||
// functions needed: | ||
// - [x] IsConflict(composition)(tips) | ||
// - [x] Concat(composition)(tips) | ||
// - [ ] IsConflict(composition)(tips) | ||
// - [ ] Concat(composition)(tips) | ||
// - [ ] IsValidMerge | ||
// | ||
// intended direction: | ||
// - build ComposeRule(composition), which has concat+merge methods | ||
// NOTE to detect a conflict I think we only want to be comparing the divergence in branches | ||
// e.g. | ||
// A ] | ||
// | ]--- common history, do not compare | ||
// B ] | ||
// / \ | ||
// C D ]--- divergent history, compare C + D for conflict | ||
// \ / | ||
// E | ||
// | ||
// | ||
@@ -136,3 +154,4 @@ queue.add({ | ||
// accT: nextT | ||
accT: mergeTransformation | ||
accT: mergeTransformation, | ||
d: maxD + 1 | ||
}) | ||
@@ -155,3 +174,5 @@ // this just treats merge like an overwrite (ignoring all transformations so far) | ||
this.graph.addNodes(nodes) | ||
// idea: preserve the more state from initial resolve and find a way to re-ignite the the resolving path | ||
// This is challenging because you don't know which new nodes attach where.... | ||
} | ||
} |
{ | ||
"name": "@tangle/reduce", | ||
"version": "3.0.1", | ||
"version": "3.1.0", | ||
"description": "reduce tangles into their current state", | ||
@@ -5,0 +5,0 @@ "main": "index.js", |
@@ -48,5 +48,5 @@ # @tangle/reduce | ||
const Reduce = require('@tangle/reduce') | ||
const Srategy = require('@tangle/strategy') | ||
const Strategy = require('@tangle/strategy') | ||
const strategy = Compose({ | ||
const strategy = new Strategy({ | ||
title: require('@tangle/simple-set')(), | ||
@@ -98,7 +98,2 @@ attendees: require('@tangle/overwrite')() | ||
- `opts.getTransformation = fn(node): Object` | ||
- fetch the part of the node which contains the transformation | ||
- default: `node => node` | ||
- NOTE - the strategy will automatically pick out properties defined in the strategy and ignore all others | ||
- `opts.getBacklinks = fn(node): Array` | ||
@@ -108,2 +103,9 @@ - fetch the part of the node which contains the backlinks to the nodes it followed in the tangle | ||
- `opts.getTransformation = fn(node, distance): Object` | ||
- fetch the part of the node which contains the transformation | ||
- `node` - raw node from which you are going to extract a transformation, `T` | ||
- `distance` - an integer describing how far the node is from the root (this is a monotonically increasing number so a merge nodes distance will always be 1 greater than the maximum of it's backlinks distances) | ||
- default: `(node, distance) => node` | ||
- NOTE - the strategy will automatically pick out properties defined in the strategy and ignore all others | ||
- `opts.isValid = fn(context, node): Boolean` | ||
@@ -110,0 +112,0 @@ - determine whether the next node `node` should be included in the tangle |
@@ -10,3 +10,4 @@ const test = require('tape') | ||
title: Overwrite(), | ||
authors: Set() | ||
authors: Set(), | ||
distance: Overwrite({ type: 'number' }) | ||
}) | ||
@@ -36,3 +37,9 @@ | ||
const getTransformation = node => node.mutations | ||
const getTransformation = (node, d) => { | ||
return { | ||
...node.mutations, | ||
distance: { set: d } | ||
} | ||
} | ||
t.deepEqual( | ||
@@ -43,3 +50,4 @@ new Reduce(strategy, { nodes: [A, B], getTransformation }).state, | ||
title: { set: 'my root message' }, | ||
authors: { luandro: 1 } | ||
authors: { luandro: 1 }, | ||
distance: { set: 1 } | ||
} | ||
@@ -50,3 +58,24 @@ }, | ||
// A (root) | ||
// | | ||
// B | ||
// | \ | ||
// C X | ||
// | | | ||
// D | | ||
// | / | ||
// E | ||
const C = { key: 'C', previous: ['B'] } | ||
const D = { key: 'D', previous: ['C'] } | ||
const X = { key: 'X', previous: ['B'] } | ||
const E = { key: 'E', previous: ['D', 'X'] } | ||
t.deepEqual( | ||
new Reduce(strategy, { nodes: [A, B, C, D, X, E], getTransformation }).state.E.distance, | ||
{ set: 4 }, | ||
'count works' | ||
) | ||
t.end() | ||
}) |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
25690
802
128