Анализ HTML-кода страницы, содержащейся в паре ключ-значение JSON, с помощью TFHpple в iOS

Я делаю собственное приложение iOS для проекта моей команды, используя его API. API имеет три основных метода: получение информации о профиле пользователя, его дневнике и таблице сертификатов. Последний метод возвращает мне данные JSON с HTML-кодом таблицы. Это выглядит так

{"html":"<table class=\"table term-marks\" cellspacing=\"0\" cellspadding=\"0\"> <thead> <tr> <td>\u041f\u0440\u0435\u0434\u043c\u0435\u0442<\/td> <td colspan=\"10\">\u041e\u0446\u0435\u043d\u043a\u0438<\/td><td width=\"60px\">\u0421\u0440\u0435\u0434\u043d\u0438\u0439 <br\/>\u0431\u0430\u043b\u043b<\/td> <td width=\"60px\">\u0421\u0440\u0435\u0434\u043d\u0438\u0439 <br\/>\u043f\u043e \u043a\u043b\u0430\u0441\u0441\u0443<\/td> <td width=\"60px\">\u0421\u0440\u0435\u0434\u043d\u0438\u0439 <br\/>\u043f\u043e \u043f\u0430\u0440\u0430\u043b\u043b\u0435\u043b\u0438<\/td><td width=\"60px\">\u0418\u0442\u043e\u0433\u043e\u0432\u0430\u044f \u043e\u0446\u0435\u043d\u043a\u0430<\/td> <\/tr> <\/thead> <tbody> <tr> <td>\u0410\u043d\u0433\u043b\u0438\u0439\u0441\u043a\u0438\u0439<\/td> <td>5<\/td> <td>5<\/td> <td>5<\/td> <td>4<\/td> <td>4<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td>4.60<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u0411\u0438\u043e\u043b\u043e\u0433\u0438\u044f<\/td> <td>3<\/td> <td>5<\/td> <td>5<\/td> <td>5<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td>4.50<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u0413\u0435\u043e\u0433\u0440\u0430\u0444\u0438\u044f<\/td> <td>5<\/td> <td>4<\/td> <td>3<\/td> <td>2<\/td> <td>3<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td>3.40<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u0418\u043d\u0444\u043e\u0440\u043c\u0430\u0442\u0438\u043a\u0430 \u0438 \u0418\u041a\u0422<\/td> <td>5<\/td> <td>5<\/td> <td>4<\/td> <td>5<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td>4.75<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u0418\u0441\u043a\u0443\u0441\u0441\u0442\u0432\u043e<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u0418\u0441\u0442\u043e\u0440\u0438\u044f<\/td> <td>5<\/td> <td>2<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td>3.50<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u041b\u0438\u0442\u0435\u0440\u0430\u0442\u0443\u0440\u0430<\/td> <td>4<\/td> <td>4<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td>4.00<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u041c\u0430\u0442\u0435\u043c\u0430\u0442\u0438\u043a\u0430<\/td> <td>4<\/td> <td>5<\/td> <td>3<\/td> <td>5<\/td> <td>4<\/td> <td>4<\/td> <td>5<\/td> <td>2<\/td> <td>3<\/td> <td>5<\/td> <td>4.00<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u041e\u0431\u0449\u0435\u0441\u0442\u0432\u043e\u0437\u043d\u0430\u043d\u0438\u0435<\/td> <td>4<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td>4.00<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u0420\u0443\u0441\u0441\u043a\u0438\u0439 \u044f\u0437\u044b\u043a<\/td> <td>5<\/td> <td>5<\/td> <td>4<\/td> <td>5<\/td> <td>5<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td>4.80<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u0422\u0430\u0442\u0430\u0440\u0441\u043a\u0430\u044f \u043b\u0438\u0442\u0435\u0440\u0430\u0442\u0443\u0440\u0430<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u0422\u0430\u0442\u0430\u0440\u0441\u043a\u0438\u0439 \u044f\u0437\u044b\u043a<\/td> <td>4<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td>4.00<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u0424\u0438\u0437\u0438\u043a\u0430<\/td> <td>3<\/td> <td>4<\/td> <td>5<\/td> <td>4<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td>4.00<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u0424\u0438\u0437\u0438\u0447\u0435\u0441\u043a\u0430\u044f \u043a\u0443\u043b\u044c\u0442\u0443\u0440\u0430<\/td> <td>5<\/td> <td>4<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td>4.50<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr> <td>\u0425\u0438\u043c\u0438\u044f<\/td> <td>4<\/td> <td>5<\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td><\/td> <td>4.50<\/td><td><\/td> <td><\/td> <td><\/td> <\/tr> <tr><td colspan=\"11\"><strong>\u0418\u0422\u041e\u0413\u041e<\/strong><\/td><td>3.88<\/td> <td>0<\/td> <td>0<\/td> <td>-<\/td><\/tr> <\/tbody> <\/table>"}

Я попытался создать NSDictionary с этими данными JSON и получить оттуда NSData следующим образом:

NSData *htmlData = [[NSData alloc] init];
NSDictionary *jsonDictionary = [NSJSONSerialization JSONObjectWithData:responseData options:kNilOptions error:nil]; // responseData contains API response
htmlData = [jsonDictionary objectForKey:@"html"];
TFHpple *parser = [TFHpple hppleWithHTMLData:htmlData];
NSArray *tableRows = [mainParser searchWithXPathQuery:@"//tr/td"]

Но я получаю ту же ошибку, что и здесь. Но я не могу использовать решение оттуда, потому что у меня нет URL-адреса таблицы, у меня есть только ее html-код. Как я могу разобрать его?


person khabiroff    schedule 06.05.2014    source источник
comment
Нет необходимости выделять/инициировать htmlData; Вы просто перегружаете ЦП. Это не ваша проблема, конечно.   -  person Hermann Klecker    schedule 06.05.2014
comment
@HermannKlecker спасибо за совет! Мне всего 16 лет, и я новичок в программировании на Obj-C :) Сейчас попробую ваше решение.   -  person khabiroff    schedule 06.05.2014
comment
Добро пожаловать в мир программирования :)   -  person Hermann Klecker    schedule 06.05.2014


Ответы (1)


Вы получаете объект NSString от [jsonDictionary objectForKey:@"html"];

Независимо от того, как вы на самом деле объявили принимающую переменную, в данном случае NSData, ей будет присвоено то, что на самом деле возвращает метод. И это NSString в данном случае.

В общем, желательно сначала получить данные в переменной типа id, а затем проверить ее класс, используя isKindOfClass, а затем идти оттуда.

NSData *htmlData;
NSDictionary *jsonDictionary = [NSJSONSerialization JSONObjectWithData:responseData options:kNilOptions error:nil];
id nextElement = [jsonDictionary objectForKey:@"html"];
if (id isKindOfClass:[NSString class]) {
  htmlData = [(NSString*)id dataUsingEncoding:NSUTF8StringEncoding];
} else {
   // Deal with the error or cover other classes accordingly 
} 
TFHpple *parser = [TFHpple hppleWithHTMLData:htmlData];
NSArray *tableRows = [mainParser searchWithXPathQuery:@"//tr/td"]
person Hermann Klecker    schedule 06.05.2014