diff --git a/src/rewritable_units/element.rs b/src/rewritable_units/element.rs
index b3e13cf8..85bd1093 100644
--- a/src/rewritable_units/element.rs
+++ b/src/rewritable_units/element.rs
@@ -1439,7 +1439,11 @@ mod tests {
#[test]
fn parsed() {
test!(
- |_| {},
+ |el| {
+ assert_eq!(el.get_attribute("a1").unwrap(), "foo \" baré \" baz");
+ assert_eq!(el.get_attribute("a3").unwrap(), "foo/bar");
+ assert_eq!(el.get_attribute("a4").unwrap(), "");
+ },
r#""#
);
}
@@ -1523,6 +1527,26 @@ mod tests {
assert_eq!(output, r"");
}
+ #[test]
+ fn value_trailing_slash() {
+ let mut output = rewrite_element(b"", UTF_8, "img", |el| {
+ assert_eq!(el.get_attribute("path").unwrap(), "//");
+ el.set_attribute("slash", "/").unwrap();
+
+ assert!(!el.can_have_content());
+ });
+
+ assert_eq!(output, r#""#);
+
+ output = rewrite_element(b"", UTF_8, "img", |el| {
+ el.remove_attribute("path");
+
+ assert!(!el.can_have_content());
+ });
+
+ assert_eq!(output, r"");
+ }
+
#[test]
fn remove_non_existent_attr() {
test!(
@@ -1537,6 +1561,8 @@ mod tests {
fn without_attrs() {
test!(
|el| {
+ assert!(el.can_have_content());
+
for name in &["a1", "a2", "a3", "a4"] {
el.remove_attribute(name);
}
diff --git a/src/rewritable_units/mod.rs b/src/rewritable_units/mod.rs
index 069a3fda..33652866 100644
--- a/src/rewritable_units/mod.rs
+++ b/src/rewritable_units/mod.rs
@@ -137,7 +137,9 @@ mod test_utils {
|c: &[u8]| output.push(c),
);
- rewriter.write(html).unwrap();
+ for ch in html.chunks(15) {
+ rewriter.write(ch).unwrap();
+ }
rewriter.end().unwrap();
}
diff --git a/src/rewritable_units/tokens/capturer/text_decoder.rs b/src/rewritable_units/tokens/capturer/text_decoder.rs
index 1a81e3e3..33090179 100644
--- a/src/rewritable_units/tokens/capturer/text_decoder.rs
+++ b/src/rewritable_units/tokens/capturer/text_decoder.rs
@@ -29,7 +29,7 @@ impl TextDecoder {
encoding,
pending_text_streaming_decoder: None,
// TODO make adjustable
- text_buffer: String::from_utf8(vec![0u8; 1024]).unwrap(),
+ text_buffer: "\0".repeat(if cfg!(debug_assertions) { 12 } else { 1024 }),
last_text_type: TextType::Data,
}
}
diff --git a/src/rewritable_units/tokens/text_chunk.rs b/src/rewritable_units/tokens/text_chunk.rs
index d160f3f9..6afdc53f 100644
--- a/src/rewritable_units/tokens/text_chunk.rs
+++ b/src/rewritable_units/tokens/text_chunk.rs
@@ -413,15 +413,6 @@ mod tests {
};
}
- macro_rules! skip_eof_chunk {
- ($c:ident) => {
- if $c.last_in_text_node() {
- assert!($c.as_str().is_empty());
- return;
- }
- };
- }
-
#[test]
fn parsed() {
test!(|_| {}, HTML);
@@ -429,15 +420,20 @@ mod tests {
#[test]
fn with_prepends_and_appends() {
+ let mut first = true;
test!(
|c| {
- skip_eof_chunk!(c);
- c.before("", ContentType::Text);
- c.before("Hey
", ContentType::Html);
- c.before("", ContentType::Html);
- c.after("", ContentType::Html);
- c.after("", ContentType::Html);
- c.after("", ContentType::Text);
+ let is_first = std::mem::replace(&mut first, c.last_in_text_node());
+ if is_first {
+ c.before("", ContentType::Text);
+ c.before("Hey
", ContentType::Html);
+ c.before("", ContentType::Html);
+ }
+ if c.last_in_text_node() {
+ c.after("", ContentType::Html);
+ c.after("", ContentType::Html);
+ c.after("", ContentType::Text);
+ }
},
concat!(
"<span>Hey
",
@@ -452,17 +448,22 @@ mod tests {
#[test]
fn removed() {
+ let mut first = true;
test!(
|c| {
- skip_eof_chunk!(c);
+ let is_first = std::mem::replace(&mut first, c.last_in_text_node());
assert!(!c.removed());
c.remove();
assert!(c.removed());
- c.before("", ContentType::Html);
- c.after("", ContentType::Html);
+ if is_first {
+ c.before("", ContentType::Html);
+ }
+ if c.last_in_text_node() {
+ c.after("", ContentType::Html);
+ }
},
""
);
@@ -472,17 +473,20 @@ mod tests {
fn replaced_with_text() {
test!(
|c| {
- skip_eof_chunk!(c);
- c.before("", ContentType::Html);
- c.after("", ContentType::Html);
+ if c.last_in_text_node() {
+ c.before("", ContentType::Html);
+ c.after("", ContentType::Html);
- assert!(!c.removed());
+ assert!(!c.removed());
- c.replace("", ContentType::Html);
- c.replace("", ContentType::Html);
- c.replace("", ContentType::Text);
+ c.replace("", ContentType::Html);
+ c.replace("", ContentType::Html);
+ c.replace("", ContentType::Text);
- assert!(c.removed());
+ assert!(c.removed());
+ } else {
+ c.remove();
+ }
},
"<foo & bar>"
);
@@ -492,17 +496,20 @@ mod tests {
fn replaced_with_html() {
test!(
|c| {
- skip_eof_chunk!(c);
- c.before("", ContentType::Html);
- c.after("", ContentType::Html);
+ if c.last_in_text_node() {
+ c.before("", ContentType::Html);
+ c.after("", ContentType::Html);
- assert!(!c.removed());
+ assert!(!c.removed());
- c.replace("", ContentType::Html);
- c.replace("", ContentType::Html);
- c.replace("", ContentType::Html);
+ c.replace("", ContentType::Html);
+ c.replace("", ContentType::Html);
+ c.replace("", ContentType::Html);
- assert!(c.removed());
+ assert!(c.removed());
+ } else {
+ c.remove();
+ }
},
""
);