Online Book Reader

Home Category

Cocoa Programming for Mac OS X - Aaron Hillegass [109]

By Root 781 0
(!data)

return nil;

NSLog(@"Received %ld bytes.", [data length]);

return nil;

}

@end

We will use the NSDateFormatter later in the parsing process. Before we get into XML parsing, however, let’s test our fetchClassesWithError: method. In RanchForecastAppDelegate.m:

#import "RanchForecastAppDelegate.h"

#import "ScheduleFetcher.h"

@implementation RanchForecastAppDelegate

@synthesize window;

- (void)applicationDidFinishLaunching:(NSNotification *)aNotification

{

ScheduleFetcher *fetcher = [[ScheduleFetcher alloc] init];

NSError *error = nil;

[fetcher fetchClassesWithError:&error];

}

Build and run your application. You should see a log message indicating that data was received. Resolve any problems before continuing. It may help to log the error, if an error is being set.

Add XML Parsing to ScheduleFetcher


Now we need to parse the XML data from the Web service. We will do this by using an instance of NSXMLParser. Modify fetchClassesWithError: to instantiate and run the parser:

- (NSArray *)fetchClassesWithError:(NSError **)outError

{

BOOL success;

NSURL *xmlURL = [NSURL URLWithString:

@"http://bignerdranch.com/xml/schedule"];

NSURLRequest *req = [NSURLRequest requestWithURL:xmlURL

cachePolicy:NSURLRequestReturnCacheDataElseLoad

timeoutInterval:30];

NSURLResponse *resp = nil;

NSData *data = [NSURLConnection sendSynchronousRequest:req

returningResponse:&resp

error:outError];

if (!data)

return nil;

[classes removeAllObjects];

NSXMLParser *parser;

parser = [[NSXMLParser alloc] initWithData:data];

[parser setDelegate:self];

success = [parser parse];

if (!success)

{

*outError = [parser parserError];

return nil;

}

NSArray *output = [classes copy];

return output;

}

Note that the parser’s delegate is set to self. As all the NSXMLParserDelegate protocol methods are optional, we need to add only the ones we are interested in. Add them now to ScheduleFetcher.m:

#pragma mark -

#pragma mark NSXMLParserDelegate Methods

- (void)parser:(NSXMLParser *)parser

didStartElement:(NSString *)elementName

namespaceURI:(NSString *)namespaceURI

qualifiedName:(NSString *)qName

attributes:(NSDictionary *)attributeDict

{

if ([elementName isEqual:@"class"])

{

currentFields = [[NSMutableDictionary alloc] init];

}

else if ([elementName isEqual:@"offering"])

{

[currentFields setObject:[attributeDict objectForKey:@"href"]

forKey:@"href"];

}

}

- (void)parser:(NSXMLParser *)parser

didEndElement:(NSString *)elementName

namespaceURI:(NSString *)namespaceURI

qualifiedName:(NSString *)qName

{

if ([elementName isEqual:@"class"])

{

ScheduledClass *currentClass = [[ScheduledClass alloc] init];

[currentClass setName:[currentFields

objectForKey:@"offering"]];

[currentClass setLocation:[currentFields

objectForKey:@"location"]];

[currentClass setHref:[currentFields

objectForKey:@"href"]];

NSString *beginString = [currentFields objectForKey:@"begin"];

NSDate *beginDate = [dateFormatter

dateFromString:beginString];

[currentClass setBegin:beginDate];

[classes addObject:currentClass];

currentClass = nil;

currentFields = nil;

}

else if (currentFields && currentString)

{

NSString *trimmed;

trimmed = [currentString stringByTrimmingCharactersInSet:

[NSCharacterSet whitespaceAndNewlineCharacterSet]];

[currentFields setObject:trimmed forKey:elementName];

}

currentString = nil;

}

- (void)parser:(NSXMLParser *)parser

foundCharacters:(NSString *)string

{

if (!currentString) {

currentString = [[NSMutableString alloc] init];

}

[currentString appendString:string];

}

As mentioned at the start of the chapter, when NSXMLParser’s parse method is called, it scans through the data provided, calling its delegate for each change in the structure of the XML data that it encounters. As is this case in this exercise, you will frequently be interested only in the start and end of elements, as well as the character data that occurs in between them.

The delegate is responsible for managing any state information during the parsing process.

Return Main Page Previous Page Next Page

®Online Book Reader