Проект Programmers.kz и школа hotPen3D2D предлагает Вам курсы по веб-дизайну, веб-программированию и компьютерной графике. Подробности здесь.

 
Информация к новости

Освоение Ajax: Часть 8. Использование XML в запросах и ответах

Категория: WEB-программирование / AJAX / Уроки Ajax

Источник: www.ibm.com

Уровень сложности: средний

Брэт Маклафлин, автор и редактор, O'Reilly Media Inc.

28.01.2008

В предыдущей статье этой серии вы узнали, как Ajax-приложение может отправлять запросы на сервер в виде XML. Настоящая статья фокусирует ваше внимание на зачастую более правильной идее: возвращать клиенту ответы в XML-формате.

На самом деле мне не очень нравится писать статьи, в которых, в основном описывается то, что вам не надо делать. По большей части это достаточно глупый способ написания. Я объясняю что-то в первой половине статьи только затем, чтобы во второй половине объяснять, насколько плохо использовать те приемы, которым вы только что научились. Так, в большей степени, было в статье в предыдущем месяце (если вы ее пропустили, смотрите Ресурсы), в которой рассказывалось, как использовать XML в качестве формата данных для запросов Ajax-приложения.

Надеюсь, нынешняя статья окупит время, потраченное на изучение XML-запросов. Помимо того, что есть несколько причин, чтобы использовать XML в качестве формата передачи данных в приложениях Ajax, есть также множество поводов, из-за которых вы, возможно, захотите, чтобы сервер отсылал клиенту данные в XML. Поэтому все, что вы выучили об XML в предыдущей статье, пригодится в этой.

Сервер не может много сказать (иногда)

Прежде чем вы погрузитесь в технические детали получения XML-ответа от сервера, вам нужно понять, чем же так хороша идея отправки ответа от сервера клиенту в виде XML (и насколько это отличается от того, когда клиент посылает серверу XML-запрос).

Клиент говорит парами "имя/значение"

Как вы помните из предыдущей статьи, клиенту не нужно использовать XML в большинстве случаев, потому что он может посылать запросы, используя пары "имя/значение". То есть вы могли бы послать, например, такое имя: name=Jennifer. Можно скомпоновать эти значения, просто добавляя между парами амперсанд (&), например: name=Jennifer&job=president. Используя простой текст и эти пары – "имя/значение", клиент легко может посылать серверу запросы с многочисленными значениями. Очень редко появляется необходимость дополнительного структурирования, которое предоставляет XML.

Фактически, почти все причины, по которым может понадобиться посылать XML серверу, можно распределить на две основные категории:

  • Сервер принимает только XML-запросы. В этих случаях у вас просто нет выбора. Знания из предыдущих статей дают все инструменты, которые необходимы для отправки таких видов запросов.
  • Вы вызываете удаленный API, который принимает только XML или SOAP-запросы. На самом деле, это частный случай предыдущего пункта, но о нем стоит упомянуть отдельно. Если вы хотите использовать API из Google или Amazon в асинхронном запросе, есть несколько различных решений. Мы обсудим их, как и несколько примеров создания запросов для такого типа API, в следующей статье.

Серверы не могут отправлять пары "имя/значение" (стандартным образом)

Когда вы отсылаете пары «имя/значение», Web-браузер, посылающий запросы и отвечающая на этот запрос платформа, на которой размещается программа-сервер, объединяются, чтобы превратить эти пары в данные, с которыми программа-сервер может работать. Практически каждая технология серверной части – от сервлетов Java до PHP или Perl, или Ruby on Rails – предоставляет широкий спектр средств для получения значений на основе имени. Поэтому получение аттрибута name – задача тривиальная.

Но ситуация меняется, когда направление передачи данных меняется на обратное. Если сервер отвечает приложению строкой name=Jennifer&job=president, у клиента нет стандартизированного, простого способа разбить ее на пары «имя/значение» и затем разбить каждую пару на имя и значение. Вам придется разбивать возвращенные данные вручную. Если сервер вернет ответ, сразу составленный из пар «имя/значение», то будет ненамного проще (а может быть даже сложнее) его интерпретировать, чем любой ответ с элементами, разделенными точкой с запятой, или символами конвейеризации "|", или же любыми другими нестандартными знаками форматирования.

alt

Дайте мне несколько пробелов!

В большинстве HTTP-запросов управляющая последовательность символов %20 используется для представления одного пробела. Поэтому строка "Live Together, Die Alone" будет пересылаться по HTTP как Live%20Together,%20Die%20Alone.

Тогда получается, что нет простого способа использовать обычный текст в ответах и заставлять клиента получать этот ответ и интерпретировать его стандартным образом, по крайней мере, когда он содержит сложные значения. Если ваш сервер просто отсылает обратно, скажем, число 42, то простой текст идеально подходит. Но что делать, если нужно отослать обратно последние рейтинги для телешоу Lost, Alias и Six Degree, причем все сразу? И хотя вы можете найти множество способов отправить ответ, используя обычный текст (см. несколько примеров в листинге 1), ни один из них не будет интерпретироваться без определенной работы на клиентской части, и ни один из них не стандартизирован.


Листинг 1. Ответ сервера для телерейтингов (различные версии)
                
show=Alias&ratings=6.5|show=Lost&ratings=14.2|show=Six%20Degrees&ratings=9.1
Alias=6.5&Lost=14.2&Six%20Degrees=9.1
Alias|6.5|Lost|14.2|Six%20Degrees|9.1

И хотя не слишком сложно понять, как разбить эти строки ответа, клиент должен проанализировать и разделить строку, основываясь на точках с запятой, знаках равенства, вертикальных чертах и амперсандах. Едва ли это хороший способ написать ясный код, который другие разработчики смогут легко понять и поддерживать.

Ввод XML

Когда вы поймете, что у сервера нет стандартного способа для ответа клиенту парами «имя/значение», необходимость использования XML станет достаточно очевидной. Когда посылаются данные на сервер, пары «имя/значение» – великолепный выбор, так как сервер может легко интерпретировать эти пары; то же самое верно и для возврата данных с использованием XML. Вы видели применение DOM для распознавания структуры XML в нескольких предыдущих статьях, а в следующей статье узнаете, как JSON предоставляет для этого еще один способ. И, что самое главное, вы можете рассматривать XML как простой текст и получать значения таким образом. Поэтому есть несколько путей получения XML-ответа от сервера, и с помощью достаточно стандартного кода вытащить данные и использовать их в клиенте.

Дополнительным бонусом можно считать простоту понимания XML. Большинство людей, умеющих программировать, легко поймут смысл данных в листинге 2.


Листинг 2. Ответ сервера для телерейтингов (в XML)
                
	
	
<ratings>
<show>
<title>Alias</title>
<rating>6.5</rating>
</show>
<show>
<title>Lost</title>
<rating>14.2</rating>
</show>
<show>
<title>Six Degrees</title>
<rating>9.1</rating>
</show>
</ratings>

В коде листинга 2 не нужно ломать голову насчет того, что означает определенная точка с запятой или апостроф.


alt
alt
В начало


Получение XML от сервера

Так как эта серия статей фокусируется на клиентской стороне работы Ajax, то я не буду вдаваться в детали того, как может генерировать ответ в виде XML серверная часть. Однако вам нужно знать о некоторых особенностях того, как клиент получает XML.

Во-первых, вы можете рассмотреть XML-ответ от сервера двумя основными способами:

  • Как простой текст, который просто оказался отформатированным как XML
  • Как XML-документ, представленный объектом DOM Document

Во-вторых, возьмем простой ответ XML от сервера для примера. В листинге 3 показаны те же данные, что были приведены выше (фактически, это тот же XML, как в листинге 2, повторенный для вашего удобства). В этом разделе я буду использовать данный пример XML.


Листинг 3. Примеры телерейтингов, отформатированные в XML
                
	
	
<ratings>
<show>
<title>Alias</title>
<rating>6.5</rating>
</show>
<show>
<title>Lost</title>
<rating>14.2</rating>
</show>
<show>
<title>Six Degrees</title>
<rating>9.1</rating>
</show>
</ratings>

Работа с XML как с обычным текстом

Простейший вариант работы с XML, по крайней мере в плане изучения новых техник программирования, это обращение с ним как с любым другим текстом, возвращенным с сервера. Другими словами, вы игнорируете формат данных и просто забираете ответ с сервера.

В этой ситуации вы используете свойство responseTest вашего объекта запроса, точно также как и в случае, когда сервер посылает вам не XML-форматированный ответ (см. листинг 4).


Листинг 4. Считаем XML обычным текстовым ответом с сервера
                
	
function updatePage() {
  if (request.readyState == 4) {
    if (request.status == 200) {
      var response = request.responseText;
      // получаем ответ с сервера в формате XML 
      alert(response);
    }
  }
}

alt

Просмотрите предыдущие статьи

Чтобы избежать большого количества повторяющегося кода, в последних статьях серии показываются только небольшие фрагменты кода, имеющие отношение к обсуждаемому предмету. Таким образом в листинге 4 показан только метод обратной связи в коде клиентской части Ajax-приложения. Если вам непонятно, каким образом встроить этот метод в контекст асинхронного приложения, обратитесь к нескольким первым статьям серии, в которых описываются основы Ajax-приложений. Смотрите ссылки на ранние статьи в разделе Ресурсы.

В этом фрагменте кода updatePage() – это обратный вызов, а request – это объект XMLHttpRequest. И в итоге вы помещаете ответ сервера в переменную response. Если бы вы вывели на экран значение этой переменной, то получили бы нечто похожее на листинг 5. (Замечу, что обычно код, представленный в листинге 5 – это одна длинная строчка; здесь он разбит на несколько строк для удобства.)


Листинг 5. Значение переменной response
                
<ratings><show><title>Alias</title><rating>6.5</rating>
</show><show><title>Lost</title><rating>14.2</rating></show><show>
<title>Six Degrees</title><rating>9.1</rating></show></ratings>

Очень важно отметить здесь, что в большинстве случаев серверы возвращают XML без пробелов и переходов на новую строку; они просто связывают все вместе, как в листинге 5. Конечно, для вашего приложения пробелы не имеют значения, поэтому это не является проблемой, просто немного усложняет чтение XML.

Здесь вы можете использовать функцию javascript split для того, чтобы разбить эти данные, и основные средства управления строкой, чтобы получить имена элементов и их значения. Конечно, это дополнительные усилия, и игнорирование того факта, что вы потратили много времени, изучая DOM ранее в этой серии статей. Поэтому я призываю вас запомнить, что вы можете использовать XML-ответ сервера при помощи responseText, но вам не стоит использовать этот подход для получения XML-данных, если можно использовать DOM, что вы и увидите далее.

Чтобы увидеть это в действии, посмотрите на листинг 6. Этот код похож на листинг 4, но, вместо того, чтобы использовать свойство responseText, обратная связь использует свойство responseXML. Это свойство, доступное в XMLHttpRequest, возвращает ответ сервера в форме DOM-документа.

Рассматриваем XML как XML

Хотя вы можете рассматривать ответ сервера в XML-формате, как и любой другой текстовый ответ, вовсе необязательно делать именно так. Во-первых, если вы честно прочли предыдущие статьи, вы знаете, как использовать DOM, javascript- дружественный API, с которыми вы можете управлять XML. Что еще лучше, javascript и объект XMLHttpRequest предоставляют свойство, которое превосходно подходит для получения XML-ответа от сервера, и его получения в форме объекта Document DOM.


Листинг 6. Рассмотрение XML как XML
                
function updatePage() {
  if (request.readyState == 4) {
    if (request.status == 200) {
      var xmlDoc = request.responseXML;
      // работаем с xmlDoc, используя DOM
    }
  }
}

Теперь у вас есть DOM Document, и вы можете работать с ним, как и с любым другим XML. Например, вы можете взять все элементы show, как в листинге 7.


Листинг 7. Выбор всех элементов show
                
function updatePage() {
  if (request.readyState == 4) {
    if (request.status == 200) {
      var xmlDoc = request.responseXML;
      var showElements = xmlDoc.getElementsByTagName("show");
    }
  }
}

Если вы уже знакомы с DOM, то вам и это будет знакомым. Вы можете использовать любые методы DOM, о которых вы уже узнали, и легко управлять XML, полученным от сервера.

Вы можете также, конечно, вставить нормальный код javascript. Например, вы можете написать цикл повторения по всем элементам show, как в листинге 8.


Листинг 8. Цикл по show-элементам
                
function updatePage() {
  if (request.readyState == 4) {
    if (request.status == 200) {
      var xmlDoc = request.responseXML;
      var showElements = xmlDoc.getElementsByTagName("show");
      for (var x=0; x<showElements.length; x++) {
        // Мы знаем, что первый потомок show - это title, а второй - rating
        var title = showElements[x].childNodes[0].value;
        var rating = showElements[x].childNodes[1].value;
        // Теперь делайте что хотите с show, title и ratings
      }
    }
  }
}

С помощью этого достаточно простого кода, мы рассмотрели XML как XML, а не просто неотформатированный текст, и немного использовали DOM и javascript для обработки ответа сервера. Еще более важно то, что мы работали со стандартизированным форматом – XML – вместо формата с разделяющими запятыми или парами "имя/значение" разделенными вертикальными чертами. Другими словами, мы использовали XML там, где это имело смысл, и избежали этого в других случаях, как, например, в отправке запроса на сервер.

XML на сервере: короткий пример

Хотя я практически не говорил о том, как генерировать XML на сервере, стоит рассмотреть короткий пример без подробных комментариев, просто чтобы вы могли придумать какие-то свои собственные способы того, что делать в такой ситуации. В листинге 9 показан простой PHP-сценарий, который выдает XML в ответ на запрос, предположительно от асинхронного клиента.

Это грубый подход, где сценарий PHP печатает XML-вывод вручную. Вы можете найти огромное разнообразие инструментов и API для PHP и большинства других языков серверной части, которые также позволяют вам генерировать XML-ответы. В любом случае этот пример дает вам представление о том, как выглядят сценарии серверной части, которые отвечают на запросы и генерируют ответ в виде XML.


Листинг 9. Сценарий PHP, который возвращает XML
                
<?php
// Подключаемся к базе данных MySQL 
$conn = @mysql_connect("mysql.myhost.com", "username", "secret-password");
if (!conn)
  die("Error connecting to database: " . mysql_error());
if (!mysql_select_db("television", $conn))
  die("Error selecting TV database: " . mysql_error());
// Получаем рейтинги со всех шоу в базе данных
$select = 'SELECT title, rating';
$from   = '  FROM ratings';
$queryResult = @mysql_query($select . $from);
if (!$queryResult)
  die("Error retrieving ratings for TV shows.');
// Даем знать клиенту, что возвращаем XML
header("Content-Type: text/xml");
echo "<?xml version=\"1.0\" encoding=\"utf-8\"?>";
echo "<ratings>";
while ($row = mysql_fetch_array($queryResult)) {
  $title = $row['title'];
  $rating = $row['rating'];
  echo "<show>
  echo "<title>" . $title . "</title>";
  echo "<rating>" . $rating . "</rating>";
  echo "</show>";
}
echo "</ratings>";
mysql_close($conn);
?>

Вы должны уметь выводить XML похожим образом с помощью вашего любимого языка серверной части. Статьи сайта IBM developerWorks помогут вам узнать, как генерировать XML-документ с помощью предпочитаемого вами языка (см. Ресурсы).


alt
alt
В начало


Другие варианты интерпретации XML

Кроме вариантов работы с XML в виде неформатированного текста или с помощью DOM, есть еще один очень популярный способ, о котором важно упомянуть. Это JSON (javascript Object Notation) – свободный текстовый формат, который входит в комплект с javascript. В этой статье не хватит места, чтобы рассказать о JSON, поэтому я вернусь к нему через несколько месяцев; возможно, вы услышите о нем, как только упомянете об XML или Ajax, так что теперь вы будете знать, о чем говорят ваши коллеги.

В общем, все, что вы можете делать с JSON, вы можете делать с DOM и наоборот; выбор подхода зависит от личных предпочтений и конкретного приложения. Теперь давайте остановимся на DOM и ознакомимся с ситуацией получения ответа сервера. Я посвящу пару статей обсуждению JSON, и тогда вы сможете сделать выбор между ним и DOM при использовании в своем приложении. Так что настройтесь: еще больше информации об XML ждет вас в следующих статьях.


alt
alt
В начало


Заключение

Я говорил об XML почти безостановочно, но все еще осветил только минимум вклада XML в работу с Ajax. В следующей статье я более подробно рассмотрю особые случаи, в которых вы должны отправлять XML (и вы узнаете, в каком из этих случаев надо также получать XML обратно). В частности, вы изучите Web-сервисы – как собственные, так и такие API, как Google – в свете работы с Ajax.

Ваше задание на ближайшее время – обдумать, в каких случаях есть смысл использовать XML в своем приложении. Часто, если ваше приложение хорошо работает, то XML не представляет из себя ничего, кроме модной технологии, которая добавит вам головной боли, и вы должны устоять перед соблазном использовать ее только затем, чтобы сказать «а я в своем приложении использую XML».

Если вы столкнулись с ситуацией, когда данные, которые вам отправляет сервер, ограничены, или они имеют странный формат с запятыми или вертикальными чертами в качестве разграничителей, то XML действительно может вам помочь. Пересмотрите работу сервера или измените его компоненты так, чтобы они возвращали ответы более стандартным образом – с помощью XML.

Более того, поймите, что чем больше вы узнаете о технологиях связанных с Ajax, тем более осторожным нужно быть в своих решениях. Конечно, интересно писать Web 2.0-приложения (и в следующих статьях я вернусь к пользовательскому интерфейсу и покажу вам еще более интересные вещи), но необходимо быть уверенным, что вы не добавляете модные технологии на работающую Web-страницу, просто чтобы впечатлить своих друзей. Я знаю, что вы можете написать хорошее приложение, так что не сидите и просто сделайте это. Когда вы закончите, возвращайтесь за следующей статьей и еще большим количеством информации по XML.



Ресурсы

Научиться

Получить продукты и технологии

Обсудить


Об авторе

alt

Photo of Brett McLaughlin

alt

Брэт Маклафлин работает с компьютерами со времен Logo (помните маленький треугольник?). За последние несколько лет он стал одним из наиболее известных авторов и программистов сообщества по технологиям Java и XML. Он работал в Nextel Communications над реализацией сложных корпоративных систем, в Lutris Technologies, фактически, над созданием сервера приложений, а с недавнего времени - в O'Reilly Media, Inc., где продолжает писать и редактировать книги по данной тематике. Его готовящаяся книга " Head Rush Ajax " рассматривает инновационный подход "Вперед головой" к изучению Ajax; она пишется совместно с известными соавторами Эриком и Бет Фримэн. Его недавняя книга " Java 5.0 Tiger: Заметки разработчика " является первой доступной книгой по новейшей технологии Java, а его классическая " Java и XML " остается одной из наиболее авторитетных работ по использованию технологий XML в языке программирования Java.

 

Данная статья опубликована с разрешения редколлегии IBM developerWorks Россия.

Уважаемый посетитель, Вы зашли на сайт как незарегистрированный пользователь.
Мы рекомендуем Вам зарегистрироваться либо войти на сайт под своим именем.
Информация
Посетители, находящиеся в группе Гости, не могут оставлять комментарии к данной публикации.