Skip to content

Commit

Permalink
[GEOS-8725] Class java.util.Map is not whitelisted for XML parsing
Browse files Browse the repository at this point in the history
  • Loading branch information
aaime committed Apr 30, 2018
1 parent 729db59 commit 9ce2b66
Show file tree
Hide file tree
Showing 2 changed files with 52 additions and 9 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -484,12 +484,15 @@ protected void init(XStream xs) {
xs.registerConverter(new KeywordInfoConverter());
xs.registerConverter(new SettingsInfoConverter());
// this should have been a metadata map too, but was not registered as such and got a plain
// map converter. Switched to TolerantMapConverter to make it work when plugins get removed and
// leave configuration that cannot be parsed anymore in there
xs.registerLocalConverter( impl(SettingsInfo.class), "metadata", new TolerantMapConverter(xs.getMapper(), MetadataMap.class));
// map converter. Switched to SettingsTolerantMapConverter to make it work when plugins get
// removed and leave configuration that cannot be parsed anymore in there
xs.registerLocalConverter(
impl(SettingsInfo.class),
"metadata",
new SettingsTolerantMapConverter(xs.getMapper(), MetadataMap.class));
xs.registerConverter(new MeasureConverter());
xs.registerConverter(new MultimapConverter(xs.getMapper()));

// register Virtual structure handling
registerBreifMapComplexType("virtualTable", VirtualTable.class);
registerBreifMapComplexType("coverageView", CoverageView.class);
Expand Down Expand Up @@ -957,13 +960,13 @@ void collectSuperclasses(Class clazz, List<Class> matches) {
}
}

class TolerantMapConverter extends MapConverter {
class SettingsTolerantMapConverter extends MapConverter {

public TolerantMapConverter(Mapper mapper) {
public SettingsTolerantMapConverter(Mapper mapper) {
super(mapper);
}

public TolerantMapConverter(Mapper mapper, Class type) {
public SettingsTolerantMapConverter(Mapper mapper, Class type) {
super(mapper, type);
}

Expand All @@ -972,6 +975,28 @@ public boolean canConvert(Class type) {
return super.canConvert(type);
}

@Override
public Object unmarshal(HierarchicalStreamReader reader, UnmarshallingContext context) {
reader.moveDown();
String nodeName = reader.getNodeName();
if (!"map".equals(nodeName)) {
throw new IllegalArgumentException("Expected <map> but found <" + nodeName + ">");
}
try {
return super.unmarshal(reader, context);
} finally {
reader.moveUp();
}
}

@Override
public void marshal(Object source, HierarchicalStreamWriter writer, MarshallingContext
context) {
writer.startNode("map");
super.marshal(source, writer, context);
writer.endNode();
}

protected void putCurrentEntryIntoMap(
HierarchicalStreamReader reader,
UnmarshallingContext context,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,8 @@
import java.util.List;
import java.util.Map;

import org.custommonkey.xmlunit.XMLUnit;
import org.geoserver.config.SettingsInfo;
import org.hamcrest.CoreMatchers;
import org.hamcrest.Matchers;
import si.uom.SI;
Expand Down Expand Up @@ -1334,6 +1336,7 @@ public void readSettingsMetadataInvalidEntry() throws Exception {
String xml = "<global>\n" +
" <settings>\n" +
" <metadata>\n" +
" <map>\n" +
" <entry>\n" +
" <string>key1</string>\n" +
" <string>value1</string>\n" +
Expand All @@ -1352,16 +1355,31 @@ public void readSettingsMetadataInvalidEntry() throws Exception {
" <string>key2</string>\n" +
" <string>value2</string>\n" +
" </entry>\n" +
" </map>\n" +
" </metadata>\n" +
" <localWorkspaceIncludesPrefix>false</localWorkspaceIncludesPrefix>\n" +
" <localWorkspaceIncludesPrefix>true</localWorkspaceIncludesPrefix>\n" +
" </settings>\n" +
"</global>\n";
GeoServerInfo gs = persister.load(new ByteArrayInputStream(xml.getBytes()),
GeoServerInfo.class);
MetadataMap metadata = gs.getSettings().getMetadata();
SettingsInfo settings = gs.getSettings();
MetadataMap metadata = settings.getMetadata();
assertEquals(2, metadata.size());
assertThat(metadata, hasEntry("key1", "value1"));
assertThat(metadata, hasEntry("key2", "value2"));
assertTrue(settings.isLocalWorkspaceIncludesPrefix());

// check it round trips the same way it came in, minus the bit we could not read
ByteArrayOutputStream bos = new ByteArrayOutputStream();
persister.save(gs, bos);
// System.out.println(new String(bos.toByteArray()));
Document doc = dom(new ByteArrayInputStream(bos.toByteArray()));
XMLAssert.assertXpathExists("//settings/metadata/map", doc);
XMLAssert.assertXpathEvaluatesTo("2", "count(//settings/metadata/map/entry)", doc);
XMLAssert.assertXpathEvaluatesTo("key1", "//settings/metadata/map/entry[1]/string[1]", doc);
XMLAssert.assertXpathEvaluatesTo("value1", "//settings/metadata/map/entry[1]/string[2]", doc);
XMLAssert.assertXpathEvaluatesTo("key2", "//settings/metadata/map/entry[2]/string[1]", doc);
XMLAssert.assertXpathEvaluatesTo("value2", "//settings/metadata/map/entry[2]/string[2]", doc);
}

@Test
Expand Down

0 comments on commit 9ce2b66

Please sign in to comment.