diff --git a/Changelog.md b/Changelog.md index 0ba5a368..080d475b 100644 --- a/Changelog.md +++ b/Changelog.md @@ -14,11 +14,15 @@ ### Bug Fixes +- [#755]: Fix incorrect missing of trimming all-space text events when + `trim_text_start = false` and `trim_text_end = true`. + ### Misc Changes - [#650]: Change the type of `Event::PI` to a new dedicated `BytesPI` type. [#650]: https://github.com/tafia/quick-xml/issues/650 +[#755]: https://github.com/tafia/quick-xml/pull/755 ## 0.32.0 -- 2024-06-10 diff --git a/src/reader/mod.rs b/src/reader/mod.rs index 748f5a78..4f353c00 100644 --- a/src/reader/mod.rs +++ b/src/reader/mod.rs @@ -244,13 +244,21 @@ macro_rules! read_event_impl { } ReadTextResult::UpToMarkup(bytes) => { $self.state.state = ParseState::InsideMarkup; - // Return Text event with `bytes` content or Eof if bytes is empty - Ok($self.state.emit_text(bytes)) + // FIXME: Can produce an empty event if: + // - event contains only spaces + // - trim_text_start = false + // - trim_text_end = true + Ok(Event::Text($self.state.emit_text(bytes))) } ReadTextResult::UpToEof(bytes) => { $self.state.state = ParseState::Done; - // Return Text event with `bytes` content or Eof if bytes is empty - Ok($self.state.emit_text(bytes)) + // Trim bytes from end if required + let event = $self.state.emit_text(bytes); + if event.is_empty() { + Ok(Event::Eof) + } else { + Ok(Event::Text(event)) + } } ReadTextResult::Err(e) => Err(Error::Io(e.into())), } diff --git a/src/reader/state.rs b/src/reader/state.rs index 8b117789..bf56d242 100644 --- a/src/reader/state.rs +++ b/src/reader/state.rs @@ -52,15 +52,11 @@ pub(super) struct ReaderState { } impl ReaderState { - /// Trims end whitespaces from `bytes`, if required, and returns a [`Text`] - /// event or an [`Eof`] event, if text after trimming is empty. + /// Trims end whitespaces from `bytes`, if required, and returns a text event. /// /// # Parameters /// - `bytes`: data from the start of stream to the first `<` or from `>` to `<` - /// - /// [`Text`]: Event::Text - /// [`Eof`]: Event::Eof - pub fn emit_text<'b>(&mut self, bytes: &'b [u8]) -> Event<'b> { + pub fn emit_text<'b>(&mut self, bytes: &'b [u8]) -> BytesText<'b> { let mut content = bytes; if self.config.trim_text_end { @@ -68,15 +64,10 @@ impl ReaderState { let len = bytes .iter() .rposition(|&b| !is_whitespace(b)) - .map_or_else(|| bytes.len(), |p| p + 1); + .map_or(0, |p| p + 1); content = &bytes[..len]; } - - if content.is_empty() { - Event::Eof - } else { - Event::Text(BytesText::wrap(content, self.decoder())) - } + BytesText::wrap(content, self.decoder()) } /// reads `BytesElement` starting with a `!`,