How to access XML element names from XmlEvent

217

Solution 1

I advise you to avoid working with XML data. You should convert the XML data to JSON as possible as early. From this point of view, you can use the xml2json package.

  final myTransformer = Xml2Json();

  // Parse a simple XML string

  myTransformer.parse(xmlString);

  var jsonData = myTransformer.toParker();

Solution 2

First of all, only XmlTextEvent (and XmlCDATAEvent) contain text. You can access the text by calling text on these events.

I don't quite understand what you want to do? events is an Iterable<XmlTextEvent> with all the text events. Then you filter and cast that Iterable<XmlTextEvent> with a Stream to the superclass XmlEvent, which doesn't do anything. Just printing events would do the same.

Note that the package has two approaches to event-based XML parsing: the synchronous one that you are using with Iterable<XmlEvent> parseEvents(String) and the asynchronous one that works on Dart Streams Stream<List<XmlEvent>> Stream.toXmlEvents(). They both use the same event infrastructure, but the second one has much richer tooling. See the examples in the tutorial.

Share:
217
The Orchestrator
Author by

The Orchestrator

Eager to learn, grow and evolve...

Updated on December 25, 2022

Comments

  • The Orchestrator
    The Orchestrator over 1 year

    I am trying to access specific XML tag names from an Iterable Stream of XML Events. Is there a way as I can only find a way to print the text of each XmlEvent irrespective of tag/element name? Below my code.

    Future<String> getDataFromXml() async {
      String xmlString = await DefaultAssetBundle.of(context)
          .loadString('assets/gpx/filename');
    
    var events = parseEvents(xmlString).whereType<XmlTextEvent>();
    
    Stream.fromIterable(events)
          .where((event) => event is XmlEvent)
          .cast<XmlEvent>()
          .forEach(print);
    

    I understand how to access the elements from a parsed XML document (which is not a stream), but not from a stream of XML events.

  • The Orchestrator
    The Orchestrator over 3 years
    Thank you @lukas-renggli - I do understand that these are all text events, that much was clear to me from the start. What wasn't clear to me was whether there is a way to access the tags of the events elements' tag names? It is now clear to me that the elements and their respective tags are disregarded.
  • The Orchestrator
    The Orchestrator over 3 years
    What I want to do is perform calculations/aggregations or whatever analytics I want to on the data targeting specific tags.
  • Lukas Renggli
    Lukas Renggli over 3 years
    Have a look at the last example in the linked tutorial section: If you annotate your event stream withParentEvents() you can access the XmlStartElementEvent as the parentEvent of each XmlTextEvent.
  • The Orchestrator
    The Orchestrator over 3 years
    Thank you @lukas-renggli - That is where things weren't clear to me and hence me asking the question I did. Do you perhaps have a coding example in more or less the format I have submitted my snippet in?
  • Lukas Renggli
    Lukas Renggli over 3 years
    Try something along the following lines to print the text within elements <tag>: await Stream.fromIterable([xmlString]).toXmlEvents().withParentEve‌​nts().where((event) => event.parentEvent?.name == 'tag').forEach(print).
  • The Orchestrator
    The Orchestrator over 3 years
    Thank you @Lukas Renggli - I will definitely do so....
  • The Orchestrator
    The Orchestrator over 3 years
    May I ask why you made this recommendation? The deeper I go it seems that both have their benefits. XML seems more secure. Your thoughts @Akif ?