diff --git a/modules/util/index.js b/modules/util/index.js index b7d51e668..dde2a5614 100644 --- a/modules/util/index.js +++ b/modules/util/index.js @@ -37,6 +37,7 @@ export { utilRebind } from './rebind'; export { utilSetTransform } from './util'; export { utilSessionMutex } from './session_mutex'; export { utilStringQs } from './util'; +export { utilTagDiff } from './util'; export { utilTagText } from './util'; export { utilTiler } from './tiler'; export { utilTriggerEvent } from './trigger_event'; diff --git a/modules/util/util.js b/modules/util/util.js index 2dc9c9b03..ea8d477da 100644 --- a/modules/util/util.js +++ b/modules/util/util.js @@ -1,8 +1,10 @@ -import { t, textDirection } from './locale'; -import { utilDetect } from './detect'; import { remove as removeDiacritics } from 'diacritics'; import { fixRTLTextForSvg, rtlRegex } from './svg_paths_rtl_fix'; +import { t, textDirection } from './locale'; +import { utilArrayUnion } from './array'; +import { utilDetect } from './detect'; + export function utilTagText(entity) { var obj = (entity && entity.tags) || {}; @@ -12,6 +14,24 @@ export function utilTagText(entity) { } +export function utilTagDiff(oldTags, newTags) { + var tagDiff = []; + var keys = utilArrayUnion(Object.keys(oldTags), Object.keys(newTags)).sort(); + keys.forEach(function(k) { + var oldVal = oldTags[k]; + var newVal = newTags[k]; + + if (oldVal && (!newVal || newVal !== oldVal)) { + tagDiff.push('- ' + k + '=' + oldVal); + } + if (newVal && (!oldVal || newVal !== oldVal)) { + tagDiff.push('+ ' + k + '=' + newVal); + } + }); + return tagDiff; +} + + export function utilEntitySelector(ids) { return ids.length ? '.' + ids.join(',.') : 'nothing'; } diff --git a/modules/validations/outdated_tags.js b/modules/validations/outdated_tags.js index a17156a79..d73ed0b77 100644 --- a/modules/validations/outdated_tags.js +++ b/modules/validations/outdated_tags.js @@ -3,7 +3,7 @@ import { actionChangePreset } from '../actions/change_preset'; import { actionChangeTags } from '../actions/change_tags'; import { actionUpgradeTags } from '../actions/upgrade_tags'; import { osmIsOldMultipolygonOuterMember, osmOldMultipolygonOuterMemberOfRelation } from '../osm/multipolygon'; -import { utilArrayUnion, utilDisplayLabel } from '../util'; +import { utilDisplayLabel, utilTagDiff } from '../util'; import { validationIssue, validationIssueFix } from '../core/validation'; @@ -48,20 +48,7 @@ export function validationOutdatedTags() { } // determine diff - var keys = utilArrayUnion(Object.keys(oldTags), Object.keys(newTags)).sort(); - var tagDiff = []; - keys.forEach(function(k) { - var oldVal = oldTags[k]; - var newVal = newTags[k]; - - if (oldVal && (!newVal || newVal !== oldVal)) { - tagDiff.push('- ' + k + '=' + oldVal); - } - if (newVal && (!oldVal || newVal !== oldVal)) { - tagDiff.push('+ ' + k + '=' + newVal); - } - }); - + var tagDiff = utilTagDiff(oldTags, newTags); if (!tagDiff.length) return []; return [new validationIssue({ diff --git a/modules/validations/private_data.js b/modules/validations/private_data.js index 53adef44c..972e77dec 100644 --- a/modules/validations/private_data.js +++ b/modules/validations/private_data.js @@ -1,6 +1,6 @@ import { actionChangeTags } from '../actions/change_tags'; import { t } from '../util/locale'; -import { utilDisplayLabel } from '../util'; +import { utilDisplayLabel, utilTagDiff } from '../util'; import { validationIssue, validationIssueFix } from '../core/validation'; @@ -40,20 +40,17 @@ export function validationPrivateData() { var validation = function checkPrivateData(entity, context) { var tags = entity.tags; - var keepTags = {}; - var tagDiff = []; if (!tags.building || !privateBuildingValues[tags.building]) return []; + var keepTags = {}; for (var k in tags) { if (publicKeys[k]) return []; // probably a public feature - - if (personalTags[k]) { - tagDiff.push('- ' + k + '=' + tags[k]); - } else { + if (!personalTags[k]) { keepTags[k] = tags[k]; } } + var tagDiff = utilTagDiff(tags, keepTags); if (!tagDiff.length) return []; var fixID = tagDiff.length === 1 ? 'remove_tag' : 'remove_tags'; diff --git a/test/spec/util/util.js b/test/spec/util/util.js index be330efaf..3811273be 100644 --- a/test/spec/util/util.js +++ b/test/spec/util/util.js @@ -2,57 +2,68 @@ describe('iD.util', function() { describe('utilGetAllNodes', function() { it('gets all descendant nodes of a way', function() { - var a = iD.osmNode({ id: 'a' }), - b = iD.osmNode({ id: 'b' }), - w = iD.osmWay({ id: 'w', nodes: ['a','b','a'] }), - graph = iD.coreGraph([a, b, w]), - result = iD.utilGetAllNodes(['w'], graph); + var a = iD.osmNode({ id: 'a' }); + var b = iD.osmNode({ id: 'b' }); + var w = iD.osmWay({ id: 'w', nodes: ['a','b','a'] }); + var graph = iD.coreGraph([a, b, w]); + var result = iD.utilGetAllNodes(['w'], graph); expect(result).to.have.members([a, b]); expect(result).to.have.lengthOf(2); }); it('gets all descendant nodes of a relation', function() { - var a = iD.osmNode({ id: 'a' }), - b = iD.osmNode({ id: 'b' }), - c = iD.osmNode({ id: 'c' }), - w = iD.osmWay({ id: 'w', nodes: ['a','b','a'] }), - r = iD.osmRelation({ id: 'r', members: [{id: 'w'}, {id: 'c'}] }), - graph = iD.coreGraph([a, b, c, w, r]), - result = iD.utilGetAllNodes(['r'], graph); + var a = iD.osmNode({ id: 'a' }); + var b = iD.osmNode({ id: 'b' }); + var c = iD.osmNode({ id: 'c' }); + var w = iD.osmWay({ id: 'w', nodes: ['a','b','a'] }); + var r = iD.osmRelation({ id: 'r', members: [{id: 'w'}, {id: 'c'}] }); + var graph = iD.coreGraph([a, b, c, w, r]); + var result = iD.utilGetAllNodes(['r'], graph); expect(result).to.have.members([a, b, c]); expect(result).to.have.lengthOf(3); }); it('gets all descendant nodes of multiple ids', function() { - var a = iD.osmNode({ id: 'a' }), - b = iD.osmNode({ id: 'b' }), - c = iD.osmNode({ id: 'c' }), - d = iD.osmNode({ id: 'd' }), - e = iD.osmNode({ id: 'e' }), - w1 = iD.osmWay({ id: 'w1', nodes: ['a','b','a'] }), - w2 = iD.osmWay({ id: 'w2', nodes: ['c','b','a','c'] }), - r = iD.osmRelation({ id: 'r', members: [{id: 'w1'}, {id: 'd'}] }), - graph = iD.coreGraph([a, b, c, d, e, w1, w2, r]), - result = iD.utilGetAllNodes(['r', 'w2', 'e'], graph); + var a = iD.osmNode({ id: 'a' }); + var b = iD.osmNode({ id: 'b' }); + var c = iD.osmNode({ id: 'c' }); + var d = iD.osmNode({ id: 'd' }); + var e = iD.osmNode({ id: 'e' }); + var w1 = iD.osmWay({ id: 'w1', nodes: ['a','b','a'] }); + var w2 = iD.osmWay({ id: 'w2', nodes: ['c','b','a','c'] }); + var r = iD.osmRelation({ id: 'r', members: [{id: 'w1'}, {id: 'd'}] }); + var graph = iD.coreGraph([a, b, c, d, e, w1, w2, r]); + var result = iD.utilGetAllNodes(['r', 'w2', 'e'], graph); expect(result).to.have.members([a, b, c, d, e]); expect(result).to.have.lengthOf(5); }); it('handles recursive relations', function() { - var a = iD.osmNode({ id: 'a' }), - r1 = iD.osmRelation({ id: 'r1', members: [{id: 'r2'}] }), - r2 = iD.osmRelation({ id: 'r2', members: [{id: 'r1'}, {id: 'a'}] }), - graph = iD.coreGraph([a, r1, r2]), - result = iD.utilGetAllNodes(['r1'], graph); + var a = iD.osmNode({ id: 'a' }); + var r1 = iD.osmRelation({ id: 'r1', members: [{id: 'r2'}] }); + var r2 = iD.osmRelation({ id: 'r2', members: [{id: 'r1'}, {id: 'a'}] }); + var graph = iD.coreGraph([a, r1, r2]); + var result = iD.utilGetAllNodes(['r1'], graph); expect(result).to.have.members([a]); expect(result).to.have.lengthOf(1); }); }); + it('utilTagDiff', function() { + var oldTags = { a: 'one', b: 'two', c: 'three' }; + var newTags = { a: 'one', b: 'three', d: 'four' }; + var diff = iD.utilTagDiff(oldTags, newTags); + expect(diff).to.have.length(4); + expect(diff[0]).to.eql('- b=two'); // delete-modify + expect(diff[1]).to.eql('+ b=three'); // insert-modify + expect(diff[2]).to.eql('- c=three'); // delete + expect(diff[3]).to.eql('+ d=four'); // insert + }); + it('utilTagText', function() { expect(iD.utilTagText({})).to.eql(''); expect(iD.utilTagText({tags:{foo:'bar'}})).to.eql('foo=bar');