Книга: Яндекс для всех

10.2.2. Как написать программу

10.2.2. Как написать программу

Создание запроса

Для написания программы вам не требуется скачивать с Яндекса никаких дополнительных модулей. Разве что примеры, позволяющие лучше разобраться со структурой запроса. Сформированный запрос отправляется вами на Яндекс, вы получаете ответ и формируете страницу результата. И форму запроса, и формат результирующей страницы вы создаете сами и вот здесь уже ни в чем не зависите от Яндекса. Единственное требование, чтобы при использовании сервиса на бесплатной основе информация об этом была выведена вверху каждой страницы результатов, а при платном использовании информация о Яндекс. XML может располагаться и внизу страницы.

Сервер XML-поиска Яндекса принимает поисковые запросы методом POST или методом GET по адресу http://xmlsearch.yandex.ru/xmlsearch/. Во входном потоке должен быть передан поисковый запрос в формате XML. Есть некоторые ограничения на формирование запроса и результатов: групп на странице не более 20, документов в группе не более 3, пассажей в документе не более 5, длина запроса в символах не более 150, число страниц при листании не более 100.

Поисковый запрос состоит из следующих элементов (табл. 10.4).



Два из перечисленных элементов имеют свою структуру. Это элементы сортировки и группировки.

Сортировка может выполняться по одному из двух доступных в Яндекс XML параметров — по релевантности запросу или по времени модификации. Но при этом следует учитывать еще одну особенность формирования результатов. Все они вначале подразделяются на три группы, соответствующие выполнению условий поиска: "совпадение фразы", "наличие всех слов", "отсутствие некоторых слов". И вот уже внутри этих групп происходит сортировка по релевантности или по времени модификации.

Группировка позволяет получать данные в сжатом виде. Например, если вы ищете сайты, подпадающие под определенные признаки, может оказаться полезным найти не сами сайты, а категории Яндекс. Каталога, в которых они находятся. Упорядочивание групп происходит по их лучшим представителям. Например, при сортировке по дате и одновременной группировке по сайтам в расчет принимается самый свежий документ сайта.

В отличие от сортировки, группировать результаты можно по нескольким признакам, для чего в запросе необходимо их все перечислить. На Яндексе поддерживается три варианта группировки:

? "плоский" способ — каждая группа состоит ровно из одного документа, используется по умолчанию, иначе называется группировкой по сайтам;

? "глубокий" способ — группировка выполняется по самому нижнему уровню иерархии или по сайтам. Еще ее называют иерархической группировкой по регионам каталога Яндекса;

? "широкий" способ — обеспечивает возможность группирования по категориям заданного уровня в нужной ветке иерархии; ветка задается при помощи номера узла. Также называется группировкой по тематическим рубрикам каталога.

Разобравшись с элементами запроса, можно попытаться его составить. Но прежде, чем запускать его в работу, сформированный XML-запрос следует проверить. Для этого можно воспользоваться либо формой на Яндексе http://xml.yandex.ru/request_example.xml, либо проверить согласно формальной схеме XML-запроса Яндекса (http://xml.yandex.ru/request.xs). С ее помощью при наличии XML-парсера, поддерживающего валидацию по схеме, вы сможете проверить корректность своих запросов (листинг 10.6).

Листинг 10.6. Пример запроса, размещенный на Яндексе для тестирования

<?xml version="1.0" encoding="windows-1251"?> <request>

<query>yandex</query> <groupings> <groupby attr="d" mode="deep" groups-on-page="10" docs-in-group="1" /> </groupings> </request>

Обработка результата поиска

В ответ на запрос Яндекс возвращает ответ, состоящий из элементов <request> и <response> (табл. 10.5).





Принятый ответ необходимо будет обработать вашей программой и вывести в виде страницы сайта.

Специальные возможности

Поиск по своему сайту

Мы уже говорили о том, что с помощью Яндекс. XML можно искать не только на Яндексе, но и на своем сайте. Сделать такой поиск можно следующим образом. Составьте запрос и дополните его расширенным условием поиска <<. Выглядеть это будет так:

{ваш запрос} << host="www.my_rsite.ru"

При этом есть несколько правил:

? группировка по сайту должна быть "плоской";

? специальные символы в запросе нужно менять на escape-последовательности.

Приведенный здесь пример в этом случае будет выглядеть следующим образом:

{ваш запрос} &lt;&lt; host=&quot; www.my_rsite.ru&quot;

Подробный пример на языке Perl приведен по ссылке http://xml.yandex.ru/examples.xml?id=420129.

Ограничение поиска регионом или разделом каталога

Вы можете сформировать запрос, ограничив поиск определенным географическим регионом или разделом Яндекс. Каталога. Для этого потребуется использовать коды, которые можно получить по ссылкам:

? коды регионов — http://search.yaca.yandex.ru/geo.c2n;

? коды разделов каталога — http://search.yaca.yandex.ru/cat.c2n.

Например, если вы ищете слона в Казани (код 43), вам потребуется создать следующий запрос:

<query>слон &lt;&lt; cat=(11000043)</query>

Правильная кодировка в запросе

Кодировка при поиске через Яндекс XML задается в первой строке отправляемого запроса:

<?xml version="1.0" encoding="windows-1251"?>

А вот результаты поиска всегда отдаются в кодировке UTF-8, для преобразования которой в любую другую потребуется дополнительная библиотека или модуль, например, Convert::Cyrillic (http://www.neystadt.org/cyrillic/ Convert-Cyrillic.htm).

Поиск картинок

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

Количество запросов на поиск картинок учитывается в общем количестве запросов (все запросы "принадлежат" одному и тому же IP-адресу). Кроме этого, в результатах "обычного" XML-поиска теперь можно показывать одно наиболее релевантное изображение, так, как это происходит в результатах поиска на Яндексе. В этом случае запрос будет выглядеть примерно так (листинг 10.7).

Листинг 10.7. Пример запроса с выводом изображения I

<request>

<query>anoHbK/query>

<groupings>

<groupby attr="ih" mode="deep" />

<groupby attr="d" mode="deep" />

</groupings>

</request>

Поиск в найденном

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

(заповедник Эйн-Геди) && (длиннохвостый скворец)

Примеры решений с использованием Яндекс. XML

Возможности XML-поиска оказались востребованными. Их использует, например, такая поисковая система, как Nigma.ru, визуальная поисковая система Quintura, система "Телеграф" — поиск по белорусским сайтам и другие поисковые системы.

Кроме того, на основе этого варианта поиска разработано несколько простых, но весьма занятных игр, например, "Отчество", в которой по имени и фамилии, вводимой пользователем, ищется наиболее часто встречающееся для этой пары данных отчество. Или игра "Какого оно цвета", в которой для введенного названия предмета подыскивается наиболее часто употребляемый с ним цвет. Почему-то тыкву большинство пользователей Интернета связывают с черным цветом, но вот огурец точно оказался зеленым.

Вы можете сами придумать интересные варианты использования XML-поиска и, если они покажутся интересными и Яндексу, их могут опубликовать с указанием фамилии разработчика. Чем не успех?

Вот интересный пример (листинг 10.7), который вы можете разместить на своем сайте (при условии, что ваш сайт не является коммерческим).

Листинг 10.7. Узнай место сайта в выдаче

#!/usr/bin/perl — w — Ilib use strict;

# модули для получения информации из XML и доступа к

# веб-ресурсам, соответственно use XML::XPath;

use LWP::UserAgent;

# верхняя и нижняя части страницы require"./page-template.pl";

# библиотека функций. Например, для обработки полей присланной

# формы

require"./xml-lib.pl";

print "Content-Type: text/html;charset=utf-8nn"; print &header;

# обработка полей формы my %params = &parse_form;

my $host = $params {'host'}; my $query = $params {'query'}; my $query_esc = xmlescape($query); my $host_esc = xmlescape($host);

$host =~ s[Ahttp://|www.][];

# готовим запрос

my $ua = LWP::UserAgent->new;

$ua->agent("Bond, James Bond/0.07"); my $exit = 1;

$exit = 0 if $ENV{'REQUEST_METHOD'} eq 'POST'; my $reqid = undef; my $page = 0;

my $found = 0; my $pages = 20;

print "<table width='100 %'><tr><td width='16 %'/><td>";

# мы должны получить место сервера в выдаче по некоему запросу.

# делаем запрос по десять ссылок на страницу и запрашиваем 50

# страниц. При нахождении сервера останавливаемся и выдаем его

# место в выдаче

while (not $exit and $page < $pages and $host)

{

my $reqid_tag = '';

$reqid_tag = " <reqid>$reqid</reqid>nn" if (defined $reqid and $reqid);

# XML запрос

my $doc = <<DOC;

<?xml version='1.0' encoding='utf-8'?>

<request>

<query>$query_esc</query>

<page>$page</page>

$reqid_tag

<maxpassages>0</maxpassages>

<groupings>

<groupby attr='d' mode='deep' groups-on-page='10' docs-in-group='1' curcateg='-1'/>

</groupings>

</request>

DOC

my $req = HTTP::Request — > new

# (POST => 'http://xmlsearch.yandex.ru/cgi-bin/xmlsearch.pl'); (POST => 'http://xmlsearch.yandex.ru/cgi-bin/xmlsearch.pl'); $req — > content_type ('application/xml');

$req — > content ("$doc");

# отправляем запрос

my $response = $ua — > request ($req); if ($response->is_success)

{

#print $response — > content;

my $doc = XML::XPath — > new (xml => $response — > content);

# пробуем получить ошибку

my $error = $doc — > findvalue ('/yandexsearch/response/error'); if ("$error")

{

print "Возникла следующая ошибка: ", $error, "<br/>n";

$exit = 1; last;

}

$reqid = $doc — > findvalue ('/yandexsearch/response/reqid'); my $pos = 1;

my @nodes = $doc — > findnodes ('/yandexsearch/response/results/grouping/group/doc/url');

foreach (@nodes)

{

# если URL начинается с имени хоста, выходим из цикла if ($_ — > string_value =~ m^http: //(www.)?$host/i)

{

$found = $pos + $page * 10;

$exit = 1; last;

}

$pos++;

}

$page++;

}

else

{

print "внутренняя ошибка сервера^";

$exit = 1;

}

}

# если что-то найдено, то выводим результат if ($found)

{

print "<p>сайт &laquo;$host&raquo; находится на месте № $found по запросу &laquo;$query&raquo;</p><p>Попробуйте узнать позицию другого сайта!</p><br/>n";

} elsif (defined $host and $host)

{

print "<p>сайт &laquo;$host&raquo; находится далее, чем на". $pages*10." месте в выдаче &laquo;Яндекса&raquo; по запросу &laquo;$query&raquo;</p><p>Попробуйте узнать позицию другого сайта!</p><br/>n";

}

else

{

print "<p>Узнайте позицию сайта в выдаче &laquo;Яндекса&raquo; по запросу!</p>";

}

print "</td></tr></table>";

# выводим форму с запросом. print <<FOKM;

<form method='POST' accept-charset='utf-8'>

<table width='100 %'>

<tr>

<td width="16%"/>

<td width="75%">

<table>

<tr>

<td><label for='query'>Запрос:</label></td>

<td><input type='text' name='query' value='$query_esc'/> &nbsp; Пример: волшебные травы</td>

</tr>

<tr>

<td><label for='host'>?Имя

сервера:</label></td>

<td><input type='text' name='host' value='$host_esc'/> &nbsp; Пример: narcom.ru</td>

</tr>

<tr>

<td/>

<td><input type="submit"

value="?? скать!"/></td>

</tr>

</table>

</td>

<td width="9%">

</tr>

</table>

</form>

FORM

# дописываем html

print &footer;

Оглавление книги


Генерация: 6.748. Запросов К БД/Cache: 3 / 0
поделиться
Вверх Вниз