| //! Contains `XmlEvent` datatype, instances of which are emitted by the parser. | 
 |  | 
 | use std::fmt; | 
 | use std::borrow::Cow; | 
 |  | 
 | use name::OwnedName; | 
 | use attribute::OwnedAttribute; | 
 | use common::XmlVersion; | 
 | use namespace::Namespace; | 
 |  | 
 | /// An element of an XML input stream. | 
 | /// | 
 | /// Items of this enum are emitted by `reader::EventReader`. They correspond to different | 
 | /// elements of an XML document. | 
 | #[derive(PartialEq, Clone)] | 
 | pub enum XmlEvent { | 
 |     /// Corresponds to XML document declaration. | 
 |     /// | 
 |     /// This event is always emitted before any other event. It is emitted | 
 |     /// even if the actual declaration is not present in the document. | 
 |     StartDocument { | 
 |         /// XML version. | 
 |         /// | 
 |         /// If XML declaration is not present, defaults to `Version10`. | 
 |         version: XmlVersion, | 
 |  | 
 |         /// XML document encoding. | 
 |         /// | 
 |         /// If XML declaration is not present or does not contain `encoding` attribute, | 
 |         /// defaults to `"UTF-8"`. This field is currently used for no other purpose than | 
 |         /// informational. | 
 |         encoding: String, | 
 |  | 
 |         /// XML standalone declaration. | 
 |         /// | 
 |         /// If XML document is not present or does not contain `standalone` attribute, | 
 |         /// defaults to `None`. This field is currently used for no other purpose than | 
 |         /// informational. | 
 |         standalone: Option<bool> | 
 |     }, | 
 |  | 
 |     /// Denotes to the end of the document stream. | 
 |     /// | 
 |     /// This event is always emitted after any other event (except `Error`). After it | 
 |     /// is emitted for the first time, it will always be emitted on next event pull attempts. | 
 |     EndDocument, | 
 |  | 
 |     /// Denotes an XML processing instruction. | 
 |     /// | 
 |     /// This event contains a processing instruction target (`name`) and opaque `data`. It | 
 |     /// is up to the application to process them. | 
 |     ProcessingInstruction { | 
 |         /// Processing instruction target. | 
 |         name: String, | 
 |  | 
 |         /// Processing instruction content. | 
 |         data: Option<String> | 
 |     }, | 
 |  | 
 |     /// Denotes a beginning of an XML element. | 
 |     /// | 
 |     /// This event is emitted after parsing opening tags or after parsing bodiless tags. In the | 
 |     /// latter case `EndElement` event immediately follows. | 
 |     StartElement { | 
 |         /// Qualified name of the element. | 
 |         name: OwnedName, | 
 |  | 
 |         /// A list of attributes associated with the element. | 
 |         /// | 
 |         /// Currently attributes are not checked for duplicates (TODO) | 
 |         attributes: Vec<OwnedAttribute>, | 
 |  | 
 |         /// Contents of the namespace mapping at this point of the document. | 
 |         namespace: Namespace, | 
 |     }, | 
 |  | 
 |     /// Denotes an end of an XML element. | 
 |     /// | 
 |     /// This event is emitted after parsing closing tags or after parsing bodiless tags. In the | 
 |     /// latter case it is emitted immediately after corresponding `StartElement` event. | 
 |     EndElement { | 
 |         /// Qualified name of the element. | 
 |         name: OwnedName | 
 |     }, | 
 |  | 
 |     /// Denotes CDATA content. | 
 |     /// | 
 |     /// This event contains unparsed data. No unescaping will be performed. | 
 |     /// | 
 |     /// It is possible to configure a parser to emit `Characters` event instead of `CData`. See | 
 |     /// `pull::ParserConfiguration` structure for more information. | 
 |     CData(String), | 
 |  | 
 |     /// Denotes a comment. | 
 |     /// | 
 |     /// It is possible to configure a parser to ignore comments, so this event will never be emitted. | 
 |     /// See `pull::ParserConfiguration` structure for more information. | 
 |     Comment(String), | 
 |  | 
 |     /// Denotes character data outside of tags. | 
 |     /// | 
 |     /// Contents of this event will always be unescaped, so no entities like `<` or `&` or `{` | 
 |     /// will appear in it. | 
 |     /// | 
 |     /// It is possible to configure a parser to trim leading and trailing whitespace for this event. | 
 |     /// See `pull::ParserConfiguration` structure for more information. | 
 |     Characters(String), | 
 |  | 
 |     /// Denotes a chunk of whitespace outside of tags. | 
 |     /// | 
 |     /// It is possible to configure a parser to emit `Characters` event instead of `Whitespace`. | 
 |     /// See `pull::ParserConfiguration` structure for more information. When combined with whitespace | 
 |     /// trimming, it will eliminate standalone whitespace from the event stream completely. | 
 |     Whitespace(String) | 
 | } | 
 |  | 
 | impl fmt::Debug for XmlEvent { | 
 |     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { | 
 |         match *self { | 
 |             XmlEvent::StartDocument { ref version, ref encoding, ref standalone } => | 
 |                 write!(f, "StartDocument({}, {}, {:?})", version, *encoding, *standalone), | 
 |             XmlEvent::EndDocument => | 
 |                 write!(f, "EndDocument"), | 
 |             XmlEvent::ProcessingInstruction { ref name, ref data } => | 
 |                 write!(f, "ProcessingInstruction({}{})", *name, match *data { | 
 |                     Some(ref data) => format!(", {}", data), | 
 |                     None       => String::new() | 
 |                 }), | 
 |             XmlEvent::StartElement { ref name, ref attributes, namespace: Namespace(ref namespace) } => | 
 |                 write!(f, "StartElement({}, {:?}{})", name, namespace, if attributes.is_empty() { | 
 |                     String::new() | 
 |                 } else { | 
 |                     let attributes: Vec<String> = attributes.iter().map( | 
 |                         |a| format!("{} -> {}", a.name, a.value) | 
 |                     ).collect(); | 
 |                     format!(", [{}]", attributes.join(", ")) | 
 |                 }), | 
 |             XmlEvent::EndElement { ref name } => | 
 |                 write!(f, "EndElement({})", name), | 
 |             XmlEvent::Comment(ref data) => | 
 |                 write!(f, "Comment({})", data), | 
 |             XmlEvent::CData(ref data) => | 
 |                 write!(f, "CData({})", data), | 
 |             XmlEvent::Characters(ref data) => | 
 |                 write!(f, "Characters({})", data), | 
 |             XmlEvent::Whitespace(ref data) => | 
 |                 write!(f, "Whitespace({})", data) | 
 |         } | 
 |     } | 
 | } | 
 |  | 
 | impl XmlEvent { | 
 |     /// Obtains a writer event from this reader event. | 
 |     /// | 
 |     /// This method is useful for streaming processing of XML documents where the output | 
 |     /// is also an XML document. With this method it is possible to process some events | 
 |     /// while passing other events through to the writer unchanged: | 
 |     /// | 
 |     /// ```rust | 
 |     /// use std::str; | 
 |     /// | 
 |     /// use xml::{EventReader, EventWriter}; | 
 |     /// use xml::reader::XmlEvent as ReaderEvent; | 
 |     /// use xml::writer::XmlEvent as WriterEvent; | 
 |     /// | 
 |     /// let mut input: &[u8] = b"<hello>world</hello>"; | 
 |     /// let mut output: Vec<u8> = Vec::new(); | 
 |     /// | 
 |     /// { | 
 |     ///     let mut reader = EventReader::new(&mut input); | 
 |     ///     let mut writer = EventWriter::new(&mut output); | 
 |     /// | 
 |     ///     for e in reader { | 
 |     ///         match e.unwrap() { | 
 |     ///             ReaderEvent::Characters(s) => | 
 |     ///                 writer.write(WriterEvent::characters(&s.to_uppercase())).unwrap(), | 
 |     ///             e => if let Some(e) = e.as_writer_event() { | 
 |     ///                 writer.write(e).unwrap() | 
 |     ///             } | 
 |     ///         } | 
 |     ///     } | 
 |     /// } | 
 |     /// | 
 |     /// assert_eq!( | 
 |     ///     str::from_utf8(&output).unwrap(), | 
 |     ///     r#"<?xml version="1.0" encoding="UTF-8"?><hello>WORLD</hello>"# | 
 |     /// ); | 
 |     /// ``` | 
 |     /// | 
 |     /// Note that this API may change or get additions in future to improve its ergonomics. | 
 |     pub fn as_writer_event<'a>(&'a self) -> Option<::writer::events::XmlEvent<'a>> { | 
 |         match *self { | 
 |             XmlEvent::StartDocument { version, ref encoding, standalone } => | 
 |                 Some(::writer::events::XmlEvent::StartDocument { | 
 |                     version: version, | 
 |                     encoding: Some(encoding), | 
 |                     standalone: standalone | 
 |                 }), | 
 |             XmlEvent::ProcessingInstruction { ref name, ref data } => | 
 |                 Some(::writer::events::XmlEvent::ProcessingInstruction { | 
 |                     name: name, | 
 |                     data: data.as_ref().map(|s| &s[..]) | 
 |                 }), | 
 |             XmlEvent::StartElement { ref name, ref attributes, ref namespace } => | 
 |                 Some(::writer::events::XmlEvent::StartElement { | 
 |                     name: name.borrow(), | 
 |                     attributes: attributes.iter().map(|a| a.borrow()).collect(), | 
 |                     namespace: Cow::Borrowed(namespace) | 
 |                 }), | 
 |             XmlEvent::EndElement { ref name } => | 
 |                 Some(::writer::events::XmlEvent::EndElement { name: Some(name.borrow()) }), | 
 |             XmlEvent::Comment(ref data) => Some(::writer::events::XmlEvent::Comment(data)), | 
 |             XmlEvent::CData(ref data) => Some(::writer::events::XmlEvent::CData(data)), | 
 |             XmlEvent::Characters(ref data) => Some(::writer::events::XmlEvent::Characters(data)), | 
 |             XmlEvent::Whitespace(ref data) => Some(::writer::events::XmlEvent::Characters(data)), | 
 |             _ => None | 
 |         } | 
 |     } | 
 | } |