Issue #2985 Configuration replacement algorithm (#2987)

* Issue #2985 Configuration replacement algorithm

Signed-off-by: Jan Bartel <janb@webtide.com>
This commit is contained in:
Jan Bartel 2018-10-18 09:21:06 +11:00 committed by GitHub
parent 4c1a0f9138
commit 2bb8902286
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 170 additions and 10 deletions

View File

@ -143,7 +143,12 @@
<dependency>
<groupId>javax.xml.bind</groupId>
<artifactId>jaxb-api</artifactId>
<version>2.3.0</version>
<version>2.4.0-b180830.0359</version>
</dependency>
<dependency>
<groupId>javax.activation</groupId>
<artifactId>javax.activation-api</artifactId>
<version>1.2.0</version>
</dependency>
</dependencies>
</plugin>

View File

@ -427,19 +427,30 @@ public class Configurations extends AbstractList<Configuration> implements Dumpa
{
Configuration c=i.next();
if(c.getClass().getName().equals(replaces.getName())
|| c.replaces()!=null && c.replaces().getName().equals(replaces.getName()))
|| c.replaces()!=null && c.replaces().getName().equals(replaces.getName()))
{
i.set(configuration);
return;
i.remove();
break;
}
}
_configurations.add(configuration);
return;
}
if (!_configurations.stream().map(c->c.getClass().getName()).anyMatch(n->{return name.equals(n);}))
_configurations.add(configuration);
//check if any existing configurations replace the one we're adding
for (ListIterator<Configuration> i=_configurations.listIterator();i.hasNext();)
{
Configuration c=i.next();
Class<? extends Configuration> r = c.replaces();
if (r != null)
{
if (r.getName().equals(configuration.getClass().getName()))
return; //skip the addition, a replacement is already present
}
if (c.getClass().getName().equals(configuration.getClass().getName()))
return; //don't add same one twice
}
_configurations.add(configuration);
}
@Override

View File

@ -23,6 +23,8 @@ import org.junit.jupiter.api.Test;
import static java.util.stream.Collectors.toList;
import static org.eclipse.jetty.webapp.Configurations.getKnown;
import static org.hamcrest.Matchers.contains;
import static org.hamcrest.Matchers.equalTo;
import static org.hamcrest.Matchers.not;
import static org.hamcrest.MatcherAssert.assertThat;
public class ConfigurationsTest
@ -110,6 +112,131 @@ public class ConfigurationsTest
));
}
@Test
public void testDuplicates()
{
Configurations.cleanKnown();
Configurations.setKnown(
ConfigBar.class.getName(),
ConfigZ.class.getName()
);
Configurations configs = new Configurations(
ConfigBar.class.getName(),
ConfigZ.class.getName());
configs.add(ConfigZ.class.getName());
configs.sort();
assertThat(configs.stream().map(c->c.getClass().getName()).collect(toList()),
contains(ConfigBar.class.getName(), ConfigZ.class.getName()));
assertThat(configs.getConfigurations().size(), equalTo(2));
}
@Test
public void testReplacement()
{
Configurations.cleanKnown();
Configurations.setKnown(
ConfigBar.class.getName(),
ConfigZ.class.getName(),
ConfigY.class.getName(),
ConfigX.class.getName(),
ConfigTom.class.getName(),
ConfigDick.class.getName(),
ConfigHarry.class.getName(),
ConfigAdditionalHarry.class.getName(),
ConfigFoo.class.getName(),
ReplacementDick.class.getName()
);
Configurations configs = new Configurations(
ConfigBar.class.getName(),
ConfigZ.class.getName(),
ConfigY.class.getName(),
ConfigX.class.getName(),
ConfigTom.class.getName(),
ReplacementDick.class.getName(),
ConfigHarry.class.getName(),
ConfigAdditionalHarry.class.getName(),
ConfigFoo.class.getName()
);
//ReplacementDick is already in the list and thus ConfigDick should not be added
configs.add(ConfigDick.class.getName());
configs.sort();
assertThat(configs.stream().map(c->c.getClass().getName()).collect(toList()),
contains(
ConfigFoo.class.getName(),
ConfigBar.class.getName(),
ConfigX.class.getName(),
ConfigY.class.getName(),
ConfigZ.class.getName(),
ConfigTom.class.getName(),
ReplacementDick.class.getName(),
ConfigHarry.class.getName(),
ConfigAdditionalHarry.class.getName()
));
assertThat(configs.stream().map(c->c.getClass().getName()).collect(toList()),
not(contains(
ConfigDick.class.getName()
)));
}
@Test
public void testTransitiveReplacements () throws Exception
{
Configurations.cleanKnown();
Configurations.setKnown(
ConfigBar.class.getName(),
ConfigZ.class.getName(),
ConfigY.class.getName(),
ConfigX.class.getName(),
ConfigTom.class.getName(),
ConfigDick.class.getName(),
ConfigHarry.class.getName(),
ConfigAdditionalHarry.class.getName(),
ConfigFoo.class.getName(),
ReplacementDick.class.getName(),
AnotherReplacementDick.class.getName()
);
Configurations configs = new Configurations(
ConfigBar.class.getName(),
ConfigZ.class.getName(),
ConfigY.class.getName(),
ConfigX.class.getName(),
ConfigTom.class.getName(),
AnotherReplacementDick.class.getName(),
ConfigDick.class.getName(),
ConfigHarry.class.getName(),
ConfigAdditionalHarry.class.getName(),
ConfigFoo.class.getName()
);
configs.add(ReplacementDick.class.getName());
configs.sort();
assertThat(configs.stream().map(c->c.getClass().getName()).collect(toList()),
contains(
ConfigFoo.class.getName(),
ConfigBar.class.getName(),
ConfigX.class.getName(),
ConfigY.class.getName(),
ConfigZ.class.getName(),
ConfigTom.class.getName(),
AnotherReplacementDick.class.getName(),
ConfigHarry.class.getName(),
ConfigAdditionalHarry.class.getName()
));
assertThat(configs.stream().map(c->c.getClass().getName()).collect(toList()),
not(contains(
ReplacementDick.class.getName(),
ConfigDick.class.getName()
)));
}
public static class ConfigFoo extends AbstractConfiguration
{
@ -175,7 +302,24 @@ public class ConfigurationsTest
}
public static class ReplacementDick extends ConfigDick
{
@Override
public Class<? extends Configuration> replaces()
{
return ConfigDick.class;
}
}
public static class AnotherReplacementDick extends ReplacementDick
{
@Override
public Class<? extends Configuration> replaces()
{
return ReplacementDick.class;
}
}
}

View File

@ -212,7 +212,7 @@ public class MetaInfConfigurationTest
context.setClassLoader(loader);
config.findAndFilterContainerPaths(context);
List<Resource> containerResources = context.getMetaData().getContainerResources();
assertEquals(1, containerResources.size());
assertEquals(2, containerResources.size());
assertTrue(containerResources.get(0).toString().contains("jetty-util"));
}