How to parse main XML file using NSXMLParser?
I'm trying to figure out the NSXMLParser for my iPhone application, and while I usually understand how it works, I'm still a little confused about how to retrieve the values ââI want.
The XML output I am processing is very simple. This is true:
<start>
<status>300</status>
<record>
<title>The Title</title>
<content>Some content</content>
</record>
</start>
I need to do 3 things: Get the status value. Get content value from your first post. There may be an answer that suggests multiple "entry" items, so I only need to get the first one.
I cannot figure out how to do this. Most of all the examples I have seen involve creating a separate object to populate this data, and I don't see that this is needed for 2 values. Can anyone tell me how to pull these 2 pieces of data and for the first record only?
The first thing that happens when an NSXMLParser
XML tag is encountered is the delegate method is called parser:didStartElement:namespaceURI:qualifiedName:attributes:
; you will probably need to use a variable here elementName
. The XML parser then reads the characters in the tag and calls the parser:foundCharacters:
content. Finally called parser:didEndElement:namespaceURI:qualifiedName
.
The approach I have taken, as Apple uses in the SeismicXML example, is to use methods like this:
- In,
parser:didStartElement:namespaceURI:qualifiedName:attributes:
compare the element name string with a known value to see if you need a string. If so, then set the instance variable (aNSMutableString
; I'll call itcontentOfCurrentXMLProperty
) to an empty string. Otherwise, set it tonil
. - In
parser:foundCharacters:
add the found symbols tocontentOfCurrentXMLProperty
. - In,
parser:didEndElement:namespaceURI:qualifiedName
assign a valuecontentOfCurrentXMLProperty
to whatever corresponds to the corresponding variable.
See the SeismicXML example for more information.
A couple of things about your particular case: First, since the XML parser only returns strings, you need to convert the string to an integer (or whatever data type you use) for status
.
Second, since you only need the first value for record
, parser:didStartElement:...
I would set in BOOL
, which indicates that you have already seen the tag record
before and, if so, set contentOfCurrentXMLProperty
before nil
.
Keeping in mind that NSXMLParser is an event-based SAX-like parser, you must configure your parser, run it, and listen for key events.
Install the parser up:
NSXMLParser *parser = [[NSXMLParser alloc] initWithData:data];
[parser setDelegate:self];
[parser parse];
Cancel the following methods:
â parser:didStartElement:namespaceURI:qualifiedName:attributes:
â parser:didEndElement:namespaceURI:qualifiedName:
â parser:foundCharacters:
Your function should basically say:
- When you reach the next tag run:
-(void)parser: didStartElement:(NSString *) namespaceURI:(NSString *) qualifiedName:(NSString *) attributes:(NSDictionary *)
- If the name of this tag is "status":
[elementName isEqualToString:@"status"]
- Give me the tag line data:
- (void)parser:(NSXMLParser *) foundCharacters:(NSString *)
...
[<your statusValueHolder as NSMutableString> appendString:<foundCharacters' parameter>]
...
You can apply the same logic for a different case (search for the first run tag named "record", abort until the end of the tag named "record", etc.)
Take a look at this and try it at home: Make NSXMLParser your friend .. Also see the NSXMLParser API References for additional delegation methods for the NSXMLParser delegate.