From b71c98cfca9177eae2bce71c3e542c37bff9cb3a Mon Sep 17 00:00:00 2001 From: tyr Date: Fri, 10 Jan 2014 10:50:50 +0100 Subject: [PATCH] protect against relation loops, part 2. fixes #2096 --- js/id/core/tree.js | 8 ++++++-- test/spec/core/tree.js | 15 +++++++++++++++ 2 files changed, 21 insertions(+), 2 deletions(-) diff --git a/js/id/core/tree.js b/js/id/core/tree.js index bd42c607f..fde531e95 100644 --- a/js/id/core/tree.js +++ b/js/id/core/tree.js @@ -18,7 +18,11 @@ iD.Tree = function(head) { return rect; } - function updateParents(entity, insertions) { + function updateParents(entity, insertions, memo) { + if (memo && memo[entity.id]) return; + memo = memo || {}; + memo[entity.id] = true; + head.parentWays(entity).forEach(function(parent) { if (rectangles[parent.id]) { rtree.remove(rectangles[parent.id]); @@ -31,7 +35,7 @@ iD.Tree = function(head) { rtree.remove(rectangles[parent.id]); insertions.push(parent); } - updateParents(parent, insertions); + updateParents(parent, insertions, memo); }); } diff --git a/test/spec/core/tree.js b/test/spec/core/tree.js index 67c9888a0..a776ab67c 100644 --- a/test/spec/core/tree.js +++ b/test/spec/core/tree.js @@ -41,6 +41,21 @@ describe("iD.Tree", function() { expect(tree.intersects(iD.geo.Extent([0, 0], [2, 2]), g)).to.eql([]); expect(tree.intersects(iD.geo.Extent([0, 0], [11, 11]), g)).to.eql([node_]); }); + + it("does not error on self-referencing relations", function() { + var graph = iD.Graph(), + tree = iD.Tree(graph), + node = iD.Node({id: 'n', loc: [1, 1]}), + relation = iD.Relation(); + + relation = relation.addMember({id: node.id}); + relation = relation.addMember({id: relation.id}); + + graph.rebase([node, relation], [graph]); + tree.rebase([relation]); + + expect(tree.intersects(iD.geo.Extent([0, 0], [2, 2]), graph)).to.eql([relation]); + }); }); describe("#intersects", function() {