Статистика поисковых запросов: парсинг выдачи Яндекса

Ajax-приложение, позволяющее у себя на сайте показывать таблицу статистики поисковых запросов Yandex.

Итак, на странице где все будет отображаться, разместите этот html-код:

<form method="post" name="queries_form" onsubmit="goParseYandex();return false;">
<table cellpadding="0" cellspacing="0" border="0">
   <tr>
      <td>Поисковый запрос:</td>
      <td><input type="text" name="query" /></td>
      <td><input type="button" name="ok_btn" value="Проанализировать"
           onclick="goParseYandex();return false;" /></td>
   </tr>
</table>
</form>
<div id="noticeDiv"></div>
<table cellpadding="0" cellspacing="0" border="0" id="queries_results_table">
   <tr>
      <td>
         <h1 class="contentTitle">Что искали с этим словом:</h1>
         <div id="queries_stat"></div>
      </td>
      <td>
         <h1 class="contentTitle">Что еще искали люди:</h1>
         <div id="more_queries"></div>
      </td>
   </tr>
</table>

Вводим запрос в соответствующее поле, нажимаем кнопку - запускаем функцию goParseYandex(), которая посылает ajax-запрос скрипту ajax_analyse.php:

function goParseYandex() {
   var query = document.forms['queries_form'].query.value;
   if (!query) return false;
   var data = new Object();
   data.query = query;
   data.action = 'queries_stat';
   var noticeDiv = document.getElementById('noticeDiv');
   noticeDiv.style.display = 'block';
   noticeDiv.style.color = 'red';
   noticeDiv.innerHTML = 'Ожидание...';
   document.getElementById('queries_stat').innerHTML = '';
   document.getElementById('more_queries').innerHTML = '';
   // Отправляем ajax-запрос на сервер:
   if (!serverRequest('/ajax_analyze.php', data, retParseYandex)) {
      alert('Произошла ошибка, попробуйте позднее.');
      noticeDiv.style.display = 'none';
   }
}

Скрипт обработчик ajax-запроса делает запрос на соответствующий url. Получает ответ, распарсивает его в удобный вид, и отвечает javascript-у:

if (count($_POST) == 0) {
   echo "0|Не было принято никаких данных.";exit;
}
$action = $_POST['action'];
$query = trim($_POST['query']);
if ($action == 'queries_stat') {
   //Здесь мы делаем запрос на сервер яндекса
   $text = @file_get_contents("http://direct.yandex.ru/stat/wordsstat.pl?rpt=ppc&shw=1&text=".
                               urlencode($query));
   if (!$text) {
      echo "0|Неизвестная ошибка.";
      exit;
   }
   preg_match_all("/(.*)<\/table>/Us", $text, $a);
   unset($text);
   function filter($str) {
      return (substr_count($str, 'tlist') == 0 ? false : true);
   }
   $b = array_values(array_filter($a[1], "filter"));
   if (sizeof($b) == 0) {
      echo "2|Нет данных по такому запросу. Попробуйте другой.";
      exit;
   }
   unset($a);
   $b_mass = array();
   foreach($b as $k => $v) {
      $b_mass[$k] = substr_count($v, 'tlist');
   }
   arsort($b_mass);
   $b_mass = array_slice($b_mass, 0, 2);
   $b_final = array();
   foreach($b_mass as $k => $v) {
      array_push($b_final, $b[$k]);
   }
   unset($b);
   unset($b_mass);
   $patt = "/<tr.*tlist.*>.*<a.*>(.*)<\/a>.*<td.*right.*>([0-9]+)<\/td>.*<\/tr>/Us";
   preg_match_all($patt, $b_final[0], $c1);
   preg_match_all($patt, $b_final[1], $c2);
   $res1 = '';	
   if (sizeof($c1[1]) != sizeof($c1[2])) {
      $n = min(sizeof($c1[1]), sizeof($c1[2])) > 50 ? 50 : min(sizeof($c1[1]), sizeof($c1[2]));
      $c1[1] = array_slice($c1[1], 0, $n);
      $c1[2] = array_slice($c1[2], 0, $n);
   }elseif (sizeof($c1[1]) > 50) {
      $c1[1] = array_slice($c1[1], 0, 50);
      $c1[2] = array_slice($c1[2], 0, 50);
   }
   foreach ($c1[1] as $k => $v) {
   $res1 .= '|||'.$v.'||'.(isset($c1[2][$k]) ? $c1[2][$k] : '');
   }
   $res2 = '';
   if (sizeof($c2[1]) != sizeof($c2[2])) {
      $n = min(sizeof($c2[1]), sizeof($c2[2])) > 50 ? 50 : min(sizeof($c2[1]), sizeof($c2[2]));
      $c2[1] = array_slice($c2[1], 0, $n);
      $c2[2] = array_slice($c2[2], 0, $n);
   }elseif (sizeof($c2[1]) > 50) {
      $c2[1] = array_slice($c2[1], 0, 50);
      $c2[2] = array_slice($c2[2], 0, 50);
   }
   arsort($c2[2]);
   foreach ($c2[2] as $k => $v) {
      $res2 .= '|||'.$c2[1][$k].'||'.($v ? $v : '');
   }
   if (strlen($res1) == 0) {
      echo "0|Результат не получен. Сообщите об ошибке при вашем запросе вебмастеру.";
      exit;
   }else {
      echo '1|'.utf8_win(substr($res1, 3).'|%|'.substr($res2, 3));
   }
}

А javascript-функция, которая будет обрабатывать ответ этого скрипта - retParseYandex(). Суть ее работы проста - получает строку, парсит и создает html:

function retParseYandex(request) {
   ...	// Обработка ошибок и т.п.	
   document.getElementById('queries_results_table').style.visibility = 'visible';
   response = request.responseText.substring(2, request.responseText.length);
   noticeDiv.innerHTML = 'Готово.';
   noticeDiv.style.color = 'green';
   reg = /^(.*)\|%\|(.*)$/;
   res = response.match(reg);
   c1 = res[1];
   c2 = res[2];
   res = c1.split("|||");
   reg = /^(.*)\|\|(.*)$/;
   if (res.length != 0) {
      HTML = '';
      var resTable1 = document.getElementById('queries_stat');
      for (var i = 0; i < res.length; i++) {
         c1i = res[i].match(reg);
         query = c1i[1];
         amount = c1i[2];
         HTML += '
' + amount + '
' + query + '
'; } resTable1.innerHTML += HTML; } res = c2.split("|||"); if (res.length != 0) { HTML = '' var resTable2 = document.getElementById('more_queries'); for (var i = 0; i < res.length; i++) { c1i = res[i].match(reg); query = c1i[1]; amount = c1i[2]; HTML += '
' + amount + '
' + query + '
'; } resTable2.innerHTML += HTML; } return true; }

Вот и все. Этот бред у меня прекрасно работает, надеюсь и вам он будет полезен. Мне бы в свое время такая статья очень помогла, поэтому я решил написать и опубликовать ее.

Комментарии

мой пример внутри корпоративной сети, поэтому звиняйте..