Skip to content

Commit

Permalink
fix #20 DataIntegrityProblemException: Deleted node referenced
Browse files Browse the repository at this point in the history
  • Loading branch information
Gubaer committed Oct 23, 2019
1 parent 1146175 commit 34e9819
Show file tree
Hide file tree
Showing 10 changed files with 504 additions and 37 deletions.
1 change: 0 additions & 1 deletion build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@ dependencies {
packIntoJar "org.apache.commons:commons-lang3:3.7"

implementation "javax.validation:validation-api:2.0.1.Final"

testImplementation "junit:junit:4.+"
testImplementation "org.codehaus.groovy:groovy-all:2.4.13"
testImplementation "org.hamcrest:hamcrest-library:1.3"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
import org.openstreetmap.josm.gui.layer.OsmDataLayer;

import javax.validation.constraints.NotNull;
import javax.validation.constraints.Null;
import java.awt.*;
import java.util.*;
import java.util.List;
Expand Down Expand Up @@ -459,24 +460,22 @@ protected Stream<Command> buildNodeDeleteCommands(
// of a merge operation

final WaySlice first = sources.get(0);
final Set<Way> ways = sources.stream().map(slice -> slice.getWay())
final Set<Way> ways = sources.stream().map(WaySlice::getWay)
.collect(Collectors.toSet());

return first.getNodes().stream()
.map(n -> {
// true, if the node n is only referenced by source ways
// in the merge operation
final boolean hasNoParents = n.getReferrers().stream()
.filter(p -> !ways.contains(p))
.count() == 0;
.allMatch(ways::contains);

if (hasNoParents && !n.isTagged()) {
return Optional.of(new DeleteCommand(n));
}
return Optional.<DeleteCommand>empty();
})
.filter(Optional::isPresent)
.map(o -> o.get());
.map(Optional::get);
}

/**
Expand All @@ -489,15 +488,21 @@ protected Stream<Command> buildNodeDeleteCommands(
public Command buildContourAlignCommand() {
final WaySlice dragSource = getDragSource();
final WaySlice dropTarget = getDropTarget();
return buildContourAlignCommand(dragSource, dropTarget);
}

public @Null Command buildContourAlignCommand(
@Null final WaySlice dragSource,
@Null final WaySlice dropTarget) {
if (dragSource == null || dropTarget == null) return null;

final List<WaySlice> waySlices =
dragSource.findAllEquivalentWaySlices()
.collect(Collectors.toList());
.collect(Collectors.toList());

List<Command> cmds = Stream.concat(
buildSourceChangeCommands(waySlices, dropTarget),
buildNodeDeleteCommands(waySlices)
final List<Command> cmds = Stream.concat(
buildSourceChangeCommands(waySlices, dropTarget),
buildNodeDeleteCommands(waySlices)
).collect(Collectors.toList());

return new SequenceCommand(tr("Merging Contour"), cmds);
Expand Down
Original file line number Diff line number Diff line change
@@ -1,16 +1,14 @@
package org.openstreetmap.josm.plugins.contourmerge;

import java.util.*;
import java.util.function.Function;
import java.util.stream.Stream;

import javax.validation.constraints.NotNull;

import lombok.EqualsAndHashCode;
import org.apache.commons.lang3.Validate;
import org.openstreetmap.josm.data.osm.Node;
import org.openstreetmap.josm.data.osm.Way;

import lombok.EqualsAndHashCode;
import javax.validation.constraints.NotNull;
import java.util.*;
import java.util.function.Function;
import java.util.stream.Stream;

/**
* <p>A <strong>WaySlice</strong> is a sub sequence of a ways sequence of
Expand Down Expand Up @@ -273,38 +271,73 @@ public WaySlice getOpositeSlice(){
* @param newNodes the new nodes. Ignored if null.
* @return the cloned way with the new nodes
*/
public Way replaceNodes(final List<Node> newNodes) {
final Way nw = new Way(w);
if (newNodes == null || newNodes.isEmpty()) return nw;
public Way replaceNodes(final List<Node> newNodes) {
final Way newWay = new Way(w);
final List<Node> updatedNodeList = new ArrayList<>();

if (!w.isClosed()) {
List<Node> oldNodes = new ArrayList<>(w.getNodes());
oldNodes.subList(start, end+1).clear();
oldNodes.addAll(start, newNodes);
nw.setNodes(oldNodes);
updatedNodeList.addAll(w.getNodes());
updatedNodeList.subList(start, end + 1).clear();
updatedNodeList.addAll(start, newNodes);
newWay.setNodes(updatedNodeList);
} else {
final List<Node> updatedNodeList = new ArrayList<>(w.getNodes());
// this is a slice of a closed way
updatedNodeList.addAll(w.getNodes());
if (inDirection) {
// because the slice is 'in direction' either of the start
// or the end node, neither of them, but not both, are
// included in the slice.
// first, we normalize the current situation
if (start == 0) {
updatedNodeList.remove(updatedNodeList.size()-1);
}
updatedNodeList.subList(start,end+1).clear();
updatedNodeList.addAll(start, newNodes);
if (start == 0) {
updatedNodeList.add(newNodes.get(0));
// jn -- n ........ n -- n -- ...-- jn
// <---- slice -->
// <-- cut&replace --> cut
//
// (jn - shared join node; n - arbitrary node)

// cut ...
updatedNodeList.subList(0, end+1).clear();
updatedNodeList.remove(updatedNodeList.size() - 1);
// ... and replace
updatedNodeList.addAll(0, newNodes);
} else if (end == w.getNodesCount() - 1) {
// jn -- n .... n -- ....... -- jn
// <---- slice -->
// cut <-- cut&replace -->
//
// (jn - shared join node; n - arbitrary node)

// cut ...
updatedNodeList.subList(start, end + 1).clear();
updatedNodeList.remove(0);
// ... and replace
updatedNodeList.addAll(newNodes);
} else {
// jn -- n -- n .... n -- -- jn
// <---- slice -->
// keep <-- cut&replace --> keep
//
// (jn - shared join node; n - arbitrary node)

// cut ...
updatedNodeList.subList(start, end + 1).clear();
// ... and replace
updatedNodeList.addAll(start, newNodes);
}
nw.setNodes(updatedNodeList);
// make sure the way is closed
updatedNodeList.add(updatedNodeList.get(0));
newWay.setNodes(updatedNodeList);
} else {
int upper = updatedNodeList.size()-1;
updatedNodeList.subList(end, upper+1).clear();
updatedNodeList.subList(0,start+1).clear();
updatedNodeList.subList(end, upper + 1).clear();
updatedNodeList.subList(0,start + 1).clear();
updatedNodeList.addAll(0, newNodes);
// make sure the new way is closed
updatedNodeList.add(newNodes.get(0));
nw.setNodes(updatedNodeList);
newWay.setNodes(updatedNodeList);
}
}
return nw;
return newWay;
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,8 @@ import org.junit.runners.Suite
@RunWith(Suite.class)
@Suite.SuiteClasses([
ContourMergeModelTest.class,
WaySliceTest.class
WaySliceTest.class,
DataIntegrityProblemTest01.class,
DataIntegrityProblemTest02.class
])
class AllUnitTests {}
Loading

0 comments on commit 34e9819

Please sign in to comment.