Filter non-AS2 compatible nodes from toString output, and add non-SWF tests for XML filtering.
This commit is contained in:
parent
ce1b958abb
commit
2c790f1d41
|
@ -199,7 +199,7 @@ pub fn xmlnode_to_string<'gc>(
|
|||
|
||||
if let Some(node) = this.as_xml_node() {
|
||||
let mut writer = Writer::new(Cursor::new(&mut result));
|
||||
node.write_node_to_event_writer(&mut writer);
|
||||
node.write_node_to_event_writer(&mut writer, &mut is_as2_compatible);
|
||||
}
|
||||
|
||||
Ok(String::from_utf8(result)
|
||||
|
@ -669,7 +669,7 @@ pub fn create_xml_proto<'gc>(
|
|||
if let Some(doctype) = node.document().doctype() {
|
||||
let mut result = Vec::new();
|
||||
let mut writer = Writer::new(Cursor::new(&mut result));
|
||||
if let Err(e) = doctype.write_node_to_event_writer(&mut writer) {
|
||||
if let Err(e) = doctype.write_node_to_event_writer(&mut writer, &mut |_| true) {
|
||||
log::warn!("Error occured when serializing DOCTYPE: {}", e);
|
||||
}
|
||||
|
||||
|
|
|
@ -2,7 +2,9 @@
|
|||
|
||||
use crate::xml;
|
||||
use crate::xml::{XMLDocument, XMLName};
|
||||
use quick_xml::Writer;
|
||||
use gc_arena::rootless_arena;
|
||||
use std::io::Cursor;
|
||||
|
||||
/// Tests very basic parsing of a single-element document.
|
||||
#[test]
|
||||
|
@ -70,3 +72,43 @@ fn double_ended_children() {
|
|||
assert!(roots.next_back().is_none());
|
||||
})
|
||||
}
|
||||
|
||||
/// Tests round-trip XML writing behavior.
|
||||
#[test]
|
||||
fn round_trip_tostring() {
|
||||
let test_string = "<test><!-- Comment -->This is a text node</test>";
|
||||
|
||||
rootless_arena(|mc| {
|
||||
let xml = XMLDocument::new(mc);
|
||||
xml.as_node()
|
||||
.replace_with_str(mc, test_string)
|
||||
.expect("Parsed document");
|
||||
|
||||
let mut buf = Vec::new();
|
||||
let mut writer = Writer::new(Cursor::new(&mut buf));
|
||||
xml.as_node().write_node_to_event_writer(&mut writer, &mut |_| true).expect("Successful toString");
|
||||
let result = String::from_utf8(buf).expect("Valid UTF-8");
|
||||
|
||||
assert_eq!(test_string, result);
|
||||
})
|
||||
}
|
||||
|
||||
/// Tests filtered XML writing behavior.
|
||||
#[test]
|
||||
fn round_trip_filtered_tostring() {
|
||||
let test_string = "<test><!-- Comment -->This is a text node</test>";
|
||||
|
||||
rootless_arena(|mc| {
|
||||
let xml = XMLDocument::new(mc);
|
||||
xml.as_node()
|
||||
.replace_with_str(mc, test_string)
|
||||
.expect("Parsed document");
|
||||
|
||||
let mut buf = Vec::new();
|
||||
let mut writer = Writer::new(Cursor::new(&mut buf));
|
||||
xml.as_node().write_node_to_event_writer(&mut writer, &mut |node| !node.is_comment()).expect("Successful toString");
|
||||
let result = String::from_utf8(buf).expect("Valid UTF-8");
|
||||
|
||||
assert_eq!("<test>This is a text node</test>", result);
|
||||
})
|
||||
}
|
|
@ -983,6 +983,15 @@ impl<'gc> XMLNode<'gc> {
|
|||
}
|
||||
}
|
||||
|
||||
/// Check if this XML node constitutes text.
|
||||
#[allow(dead_code)]
|
||||
pub fn is_comment(self) -> bool {
|
||||
match &*self.0.read() {
|
||||
XMLNodeData::Comment { .. } => true,
|
||||
_ => false,
|
||||
}
|
||||
}
|
||||
|
||||
/// Check if this XML node constitutes a DOCTYPE declaration
|
||||
pub fn is_doctype(self) -> bool {
|
||||
match &*self.0.read() {
|
||||
|
@ -1168,11 +1177,28 @@ impl<'gc> XMLNode<'gc> {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn write_node_to_event_writer<W>(self, writer: &mut Writer<W>) -> Result<(), Error>
|
||||
/// Write the contents of this node, including it's children, to the given
|
||||
/// writer.
|
||||
///
|
||||
/// The given filter function allows filtering specific children out of the
|
||||
/// resulting write stream. It will be called at least once for each node
|
||||
/// encountered in the tree (other than this one) if specified; only nodes
|
||||
/// that yield `true` shall be printed.
|
||||
pub fn write_node_to_event_writer<W, F>(self, writer: &mut Writer<W>, filter: &mut F) -> Result<(), Error>
|
||||
where
|
||||
W: Write,
|
||||
F: FnMut(XMLNode<'gc>) -> bool
|
||||
{
|
||||
let children_len = self.children_len();
|
||||
let mut children = Vec::new();
|
||||
if let Some(my_children) = self.children() {
|
||||
for child in my_children {
|
||||
if filter(child) {
|
||||
children.push(child)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
let children_len = children.len();
|
||||
|
||||
match &*self.0.read() {
|
||||
XMLNodeData::DocumentRoot { .. } => Ok(0),
|
||||
|
@ -1214,10 +1240,8 @@ impl<'gc> XMLNode<'gc> {
|
|||
)),
|
||||
}?;
|
||||
|
||||
if let Some(children) = self.children() {
|
||||
for child in children {
|
||||
child.write_node_to_event_writer(writer)?;
|
||||
}
|
||||
child.write_node_to_event_writer(writer, filter)?;
|
||||
}
|
||||
|
||||
match &*self.0.read() {
|
||||
|
|
Loading…
Reference in New Issue