Index: /applications/editors/josm/plugins/reltoolbox/.classpath
===================================================================
--- /applications/editors/josm/plugins/reltoolbox/.classpath	(revision 36279)
+++ /applications/editors/josm/plugins/reltoolbox/.classpath	(revision 36280)
@@ -2,6 +2,12 @@
 <classpath>
 	<classpathentry kind="src" path="src"/>
-	<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-1.8"/>
+	<classpathentry kind="src" output="buildtest" path="test/unit">
+		<attributes>
+			<attribute name="test" value="true"/>
+		</attributes>
+	</classpathentry>
+	<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/>
 	<classpathentry combineaccessrules="false" kind="src" path="/JOSM"/>
+	<classpathentry kind="con" path="org.eclipse.jdt.junit.JUNIT_CONTAINER/4"/>
 	<classpathentry kind="output" path="build"/>
 </classpath>
Index: /applications/editors/josm/plugins/reltoolbox/.project
===================================================================
--- /applications/editors/josm/plugins/reltoolbox/.project	(revision 36279)
+++ /applications/editors/josm/plugins/reltoolbox/.project	(revision 36280)
@@ -25,4 +25,5 @@
 		<nature>org.eclipse.jdt.core.javanature</nature>
 		<nature>net.sf.eclipsecs.core.CheckstyleNature</nature>
+		<nature>org.apache.ivyde.eclipse.ivynature</nature>
 	</natures>
 </projectDescription>
Index: /applications/editors/josm/plugins/reltoolbox/src/relcontext/relationfix/MultipolygonFixer.java
===================================================================
--- /applications/editors/josm/plugins/reltoolbox/src/relcontext/relationfix/MultipolygonFixer.java	(revision 36279)
+++ /applications/editors/josm/plugins/reltoolbox/src/relcontext/relationfix/MultipolygonFixer.java	(revision 36280)
@@ -50,9 +50,8 @@
     public Command fixRelation(Relation rel) {
         List<RelationMember> members = fixMultipolygonRoles(rel.getMembers());
-        if (!members.equals(rel.getMembers())) {
-            final DataSet ds = Utils.firstNonNull(rel.getDataSet(), MainApplication.getLayerManager().getEditDataSet());
-            return new ChangeMembersCommand(ds, rel, members);
-        }
-        return null;
+        if (members.isEmpty() || members.equals(rel.getMembers())) 
+            return null;
+        final DataSet ds = Utils.firstNonNull(rel.getDataSet(), MainApplication.getLayerManager().getEditDataSet());
+        return new ChangeMembersCommand(ds, rel, members);
     }
 
Index: /applications/editors/josm/plugins/reltoolbox/test/unit/relcontext/relationfix/AssociatedStreetFixerTest.java
===================================================================
--- /applications/editors/josm/plugins/reltoolbox/test/unit/relcontext/relationfix/AssociatedStreetFixerTest.java	(revision 36279)
+++ /applications/editors/josm/plugins/reltoolbox/test/unit/relcontext/relationfix/AssociatedStreetFixerTest.java	(revision 36280)
@@ -45,4 +45,6 @@
                 new RelationMember("street", TestUtils.newWay("highway=residential name=FooBar", TestUtils.newNode(""), TestUtils.newNode(""))),
                 new RelationMember("house", TestUtils.newNode("")));
+        final DataSet ds = new DataSet();
+        ds.addPrimitiveRecursive(relation);
         return Stream.of(relation);
     }
Index: /applications/editors/josm/plugins/reltoolbox/test/unit/relcontext/relationfix/BoundaryFixerTest.java
===================================================================
--- /applications/editors/josm/plugins/reltoolbox/test/unit/relcontext/relationfix/BoundaryFixerTest.java	(revision 36279)
+++ /applications/editors/josm/plugins/reltoolbox/test/unit/relcontext/relationfix/BoundaryFixerTest.java	(revision 36280)
@@ -61,5 +61,5 @@
                 new RelationMember("outer", TestUtils.newWay("", TestUtils.newNode(""), TestUtils.newNode(""))));
         final Relation nodeRelation = TestUtils.newRelation("type=boundary boundary=administrative",
-                new RelationMember("admin_centre", TestUtils.newNode("")));
+                new RelationMember("admin_centre", TestUtils.newNode("place=city")));
         final Relation relationRelation = TestUtils.newRelation("type=boundary boundary=administrative",
                 new RelationMember("subarea", TestUtils.newRelation("")));
Index: /applications/editors/josm/plugins/reltoolbox/test/unit/relcontext/relationfix/RelationFixerTest.java
===================================================================
--- /applications/editors/josm/plugins/reltoolbox/test/unit/relcontext/relationfix/RelationFixerTest.java	(revision 36279)
+++ /applications/editors/josm/plugins/reltoolbox/test/unit/relcontext/relationfix/RelationFixerTest.java	(revision 36280)
@@ -6,4 +6,5 @@
 import static org.junit.jupiter.api.Assertions.assertFalse;
 import static org.junit.jupiter.api.Assertions.assertNotNull;
+import static org.junit.jupiter.api.Assertions.assertNull;
 import static org.junit.jupiter.api.Assertions.assertSame;
 import static org.junit.jupiter.api.Assertions.assertTrue;
@@ -15,7 +16,12 @@
 import org.junit.jupiter.params.ParameterizedTest;
 import org.junit.jupiter.params.provider.MethodSource;
+import org.openstreetmap.josm.TestUtils;
 import org.openstreetmap.josm.command.Command;
+import org.openstreetmap.josm.data.coor.LatLon;
 import org.openstreetmap.josm.data.osm.DataSet;
+import org.openstreetmap.josm.data.osm.Node;
 import org.openstreetmap.josm.data.osm.Relation;
+import org.openstreetmap.josm.data.osm.RelationMember;
+import org.openstreetmap.josm.data.osm.Way;
 import org.openstreetmap.josm.testutils.annotations.Projection;
 
@@ -25,70 +31,97 @@
 @TestInstance(TestInstance.Lifecycle.PER_CLASS)
 interface RelationFixerTest {
-    /**
-     * Get the instance to use for checking
-     * @return The fixer instance
-     */
-    RelationFixer getInstance();
+	/**
+	 * Get the instance to use for checking
+	 * @return The fixer instance
+	 */
+	RelationFixer getInstance();
 
-    /**
-     * A relation that should be fixed by the fixer
-     * @return The bad relation
-     */
-    Stream<Relation> getBadRelations();
+	/**
+	 * A relation that should be fixed by the fixer
+	 * @return The bad relation
+	 */
+	Stream<Relation> getBadRelations();
 
-    /**
-     * A relation that should not be fixed by the fixer
-     * @return The good relation
-     */
-    Stream<Relation> getGoodRelations();
+	/**
+	 * A relation that should not be fixed by the fixer
+	 * @return The good relation
+	 */
+	Stream<Relation> getGoodRelations();
 
-    default Stream<Relation> getRelations() {
-        return Stream.concat(getBadRelations(), getGoodRelations());
-    }
+	default Stream<Relation> getRelations() {
+		return Stream.concat(getBadRelations(), getGoodRelations());
+	}
 
-    @ParameterizedTest
-    @MethodSource("getRelations")
-    default void testIsFixerApplicable(Relation relation) {
-        final RelationFixer fixer = getInstance();
-        assertTrue(fixer.isFixerApplicable(relation));
-    }
+	@ParameterizedTest
+	@MethodSource("getRelations")
+	default void testIsFixerApplicable(Relation relation) {
+		final RelationFixer fixer = getInstance();
+		assertTrue(fixer.isFixerApplicable(relation));
+	}
 
-    @Test
-    default void testIsFixerApplicableEmptyRelation() {
-        assertFalse(getInstance().isFixerApplicable(new Relation()));
-    }
+	@Test
+	default void testIsFixerApplicableEmptyRelation() {
+		assertFalse(getInstance().isFixerApplicable(new Relation()));
+	}
 
-    @ParameterizedTest
-    @MethodSource("getGoodRelations")
-    default void testGoodRelationMatches(Relation goodRelation) {
-        final RelationFixer fixer = getInstance();
-        assertTrue(fixer.isFixerApplicable(goodRelation));
-        assertFalse(fixer.isFixerApplicable(new Relation()));
-    }
+	@ParameterizedTest
+	@MethodSource("getGoodRelations")
+	default void testGoodRelationMatches(Relation goodRelation) {
+		final RelationFixer fixer = getInstance();
+		assertTrue(fixer.isFixerApplicable(goodRelation));
+		assertFalse(fixer.isFixerApplicable(new Relation()));
+	}
 
-    @ParameterizedTest
-    @MethodSource("getGoodRelations")
-    default void testIsRelationGoodGoodRelation(Relation goodRelation) {
-        assertTrue(getInstance().isRelationGood(goodRelation));
-    }
+	@ParameterizedTest
+	@MethodSource("getGoodRelations")
+	default void testIsRelationGoodGoodRelation(Relation goodRelation) {
+		assertTrue(getInstance().isRelationGood(goodRelation));
+	}
 
-    @ParameterizedTest
-    @MethodSource("getBadRelations")
-    default void testIsRelationGoodBadRelation(Relation badRelation) {
-        assertFalse(getInstance().isRelationGood(badRelation));
-    }
+	@ParameterizedTest
+	@MethodSource("getBadRelations")
+	default void testIsRelationGoodBadRelation(Relation badRelation) {
+		assertFalse(getInstance().isRelationGood(badRelation));
+	}
 
-    @MethodSource("getBadRelations")
-    @ParameterizedTest
-    @Projection
-    default void testFixBadRelation(Relation badRelation) {
-        final DataSet ds = badRelation.getDataSet();
-        final RelationFixer fixer = getInstance();
-        final Command command = fixer.fixRelation(badRelation);
-        assertNotNull(command);
-        assertDoesNotThrow(command::executeCommand);
-        final Relation relation = ds.getRelations().stream().filter(fixer::isFixerApplicable).findFirst().orElseThrow(AssertionError::new);
-        assertAll(relation.getMemberPrimitives().stream()
-                .map(member -> () -> assertSame(ds, member.getDataSet(), member + " does not have the same dataset as " + relation)));
-    }
+	@MethodSource("getBadRelations")
+	@ParameterizedTest
+	@Projection
+	default void testFixBadRelation(Relation badRelation) {
+		final DataSet ds = badRelation.getDataSet();
+		final RelationFixer fixer = getInstance();
+		final Command command = fixer.fixRelation(badRelation);
+		assertNotNull(command);
+		assertDoesNotThrow(command::executeCommand);
+		final Relation relation = ds.getRelations().stream().filter(fixer::isFixerApplicable).findFirst().orElseThrow(AssertionError::new);
+		assertAll(relation.getMemberPrimitives().stream()
+				.map(member -> () -> assertSame(ds, member.getDataSet(), member + " does not have the same dataset as " + relation)));
+	}
+
+	@ParameterizedTest
+	@MethodSource("getGoodRelations")
+	default void testGoodRelationNotFixed(Relation goodRelation) {
+		assertTrue(getInstance().isRelationGood(goodRelation));
+		final DataSet ds = goodRelation.getDataSet();
+		final RelationFixer fixer = getInstance();
+		final Command command = fixer.fixRelation(goodRelation);
+		assertNull(command);
+	}
+
+	@ParameterizedTest
+	@MethodSource("getGoodRelations")
+	default void testAddBadMember(Relation goodRelation) {
+		// regression test for #23715
+		final DataSet ds = goodRelation.getDataSet();
+		assertTrue(getInstance().isRelationGood(goodRelation));
+		Node n1 = new Node(new LatLon(2.0, 2.0));
+		Node n2 = new Node(new LatLon(2.0, 3.0));
+		Way w1 = TestUtils.newWay("", n1, n2);
+		ds.addPrimitiveRecursive(w1);
+		goodRelation.addMember(new RelationMember("", w1));
+		final RelationFixer fixer = getInstance();
+		final Command command = fixer.fixRelation(goodRelation);
+		assertNull(command);
+	}
+
 }
