В большинстве примеров, продемонстрированных выше, ответ сервера на HTTP_ запрос интерпретировался как простой текст. Это вполне законно, и никто не мо_ жет заявить, что веб_серверы не могут возвращать документы с содержимым ти_ па «text/plain». Анализировать такой ответ из JavaScript_сценария можно с по_ мощью разнообразных строковых методов и делать с ним все, что потребуется.
Ответ сервера всегда можно интерпретировать как простой текст, даже если его содержимое имеет другой тип. Если сервер, например, возвращает HTML_доку_ мент, можно извлечь содержимое этого документа с помощью свойства respon_ seText и затем вставить его в какой_либо элемент документа с помощью свойства innerHTML.
506 Глава 20. Работа с протоколом HTTP
Однако существуют и другие способы обработки ответа, полученного от сервера. Как уже отмечалось в начале главы, если сервер отправляет ответ с содержимым типа «text/xml», можно получить преобразованное представление XML_доку_ мента из свойства responseXML. Значением этого свойства является DOM_объект Document, поэтому для работы с таким документом допускается использовать DOM_методы.
Однако следует заметить, что использование формата XML для передачи данных может оказаться далеко не лучшим выбором. Если сервер передает данные, ко_ торые будут обрабатываться на стороне клиента JavaScript_сценарием, весьма неэффективным будет сначала преобразовать эти данные в формат XML на сто_ роне сервера, затем с помощью объекта XMLHttpRequest преобразовать эти данные в DOM_дерево узлов, а потом в сценарии выполнять обход этого дерева для из_ влечения данных. Более короткий путь заключается в том, чтобы на стороне сер_ вера преобразовать данные в литералы объектов и массивов, а затем передать по_ лученный исходный текст на языке JavaScript веб_броузеру. После этого сцена_ рий сможет «проанализировать» ответ, просто передав его методу eval().
Преобразование данных в форму JavaScript_объектов известно под названием JSON (JavaScript Object Notation – нотация JavaScript_объектов).1 Вот примеры данных в форматах XML и JSON:
<!__ Формат XML __> <author>
<name>Wendell Berry</name> <books>
<book>The Unsettling of America</book> <book>What are People For?</book>
</books>
</author>
// Формат JSON
{
"name": "Wendell Berry",
"books": [
"The Unsettling of America", "What are People For?"
]
}
Функция HTTP.post(), приводившаяся в примере 20.5, вызывает функцию HTTP._getResponse(). Эта функция отыскивает заголовок Content_Type и с его помо_ щью определяет форму представления ответа. В примере 20.6 приводится реали_ зация HTTP_getResponse(), которая возвращает XML_документ в виде объекта Docu_ ment, интерпретирует с помощью eval() содержимое JavaScript_ или JSON_доку_ ментов, а документы любых других типов возвращает в виде обычного текста.
1 Подробнее узнать о JSON можно на сайте http://json.org. Идея принадлежит Дуг_ ласу Крокфорду (Douglas Crockford); на его веб_сайте можно найти ссылки на ути_ литы преобразования данных в/из формата JSON, написанные на различных языках программирования. Такой способ кодирования данных может оказаться полезным даже для тех, кто не пользуется JavaScript.
20.2. Примеры и утилиты с объектом XMLHttpRequest
Пример 20.6. HTTP._getResponse()
HTTP._getResponse = function(request) {
// Проверить тип содержимого, полученного от сервера switch(request.getResponseHeader("Content_Type")) { case "text/xml":
// Если это XML_документ, вернуть объект Document. return request.responseXML;
case "text/json":
case "text/javascript":
case "application/javascript": case "application/x_javascript":
// Если это JavaScript_код или документ в формате JSON, вызвать eval(),
// чтобы выполнить преобразование текста в JavaScript_значение.
// Обратите внимание: делать это следует только в том случае,
// если добропорядочность сервера не вызывает сомнений!
return eval(request.responseText); default:
// В противном случае интерпретировать ответ как простой текст
// и вернуть его как строку.
return request.responseText;
}
};
Не используйте метод eval() для обработки данных в формате JSON, как это де_ лается в примере 20.6, если не уверены в том, что сервер никогда не пришлет злонамеренный программный код вместо данных в формате JSON. Более без_ опасная альтернатива методу eval() – выполнить разбор объектов_литералов JavaScript «вручную», без вызова eval().