- PVSM.RU - https://www.pvsm.ru -

Индексация AJAX-сайтов

Индексация AJAX сайтов

Вместе с разработкой Joosy [1], AJAX внезапно – но ожидаемо, – заполонил все проекты, за которые мы беремся. Парадигма оказалась крайне удачной во всех аспектах, кроме одного. Того самого классического: «AJAX? Индексация? Пфф...». Пока мы делаем интернет-банки, это нас вполне устраивает. Но как не отказывать себе в этом изысканном удовольствии для открытых Web-ресурсов?

А вот как: Google AJAX Crawling [2] – это стандарт Google, который позволяет при формировании AJAX-адресов специальным образом (#!) заставить Google магически запрашивать вместо него другой магический адрес. С которого Google будет ждать HTML-дамп этой страницы, который он весело прожует. Добрые люди уже написали статью про то как это работает [3]. Ну а нам остается научиться эффективно этот дамп формировать. Да так, чтоб без вмешательства в код самого приложения.


Hashbang [4] – это маленький прокси-сервер на Ruby, работающий по протоколу Rack. Последнее означает, что для того чтобы его поднять сгодится любой web-сервер, работающий с Ruby и/или Rails. А для тех, кто использует собственно Rails, мы приготовили парочку особенных плюшек. Но обо всем по порядку.

Общее устройство

При инициализации, Hashbang создает в своих недрах инстанс WebKit-браузера. После того как запрос с указанием нужного URL запущен, он открывает нужный адрес, ждет специального Javascript-события и возвращает HTML код на момент, когда это событие произошло.

Это означает, что все, что вам потребуется изменить в текущем приложении – это вызывать

Suncsraper.finish()

когда страницу, подготавливаемую Javascript'ом можно считать готовой.

В боевом режиме это будет выглядеть так:

Индексация AJAX сайтов

Про внутренний браузер и производительность

Мы много экспериментировали с возможными реализациями «безголового» браузера. Пробовали Watir [5] и разные существующие биндинги Qt [6]. Ничего хорошего не вышло. Отчаявшись, мы просто написали свой биндинг к Qt-WebKit, который и только и умеет, что возвращать HTML, отслеживая событие: Sunscraper [7]. Написано это чудо на смеси C/C++ и подключается к Ruby посредством FFI [8]. Это значит, что Sunscraper должен работать не только на MRI, но и на JRuby/Rubinius. К сожалению, с Rubinius он все-таки не работает из-за багов в реализации того самого FFI.

Так как все, что мы запускаем – это сам движок WebKit, производительность близка к максимальной для решения этой задачи. Реальные данные с живых серверов в процессе сбора.

Перед установкой

Sunscraper использует Qt. Поэтому он обязательно вам понадобится для установки gem'а Hashbang. Если вы используете Mac, мы рекомендуем Homebrew [9]: brew install qt. В Linux можно ставить любой, посвежее, из пакетов.

Development-режим для тех, кто на рельсах

Если вы не разрабатываете на Rails, смело переходите к следующему параграфу, который расскажет о внедрении Hashbang в бой.

Для установки Hashbang в Rails-проект, необходимо выполнить следующую последовательность действий:

  1. Добавить gem hashbang в Gemfile
  2. Сгенерировать базовое приложение с помощью rails g hashbang

Теперь внутри вашего Rails-приложения, в папке hashbang, лежит мини-приложение самого Hashbang'а. А это значит, что вам нужно пропустить первый абзац в части «настройки и запуска».

В development-среде, Hashbang вставляет в загрузку Rails свой middleware, который перехватывает все запросы, содержащие магический фрагмент _escaped_fragment_ и автоматически обрабатывает их. Проблема лишь одна: Webrick работает в один поток. А так как Hashbang запрашивает «сам себя», это приводит к дедлоку. Поэтому чтобы потестировать текущее приложение локально, запустите его с помощью rake hashbang:rails. Эта команда запустит ваше приложение под сервером Unicorn в два поток. После запуска – localhost:3000/?_escaped_fragment_ – и проверяйте HTML. Только не забудьте, что в самом AJAX-приложении надо вызывать Sunscraper.finish().

Чтобы сэмулировать запуск Hashbang в боевом режиме, где он работает через /?url=http://..., используйте команду rake hashbang:standalone.

Настройка и запуск

Если вы не используете Rails, базовое приложение можно взять из специального репозитория [10]. Все, что вам надо будет сделать – разместить его где-нибудь, убедиться что у вас установлен gem bundler и сделать в корне приложения bundle install.

Внутри сгенерированного/скопированного Hashbang-приложения лежит файл config.rb, который обязательно надо отредактировать для эффективной работы. В нем всего две директивы:

  • url: регулярное выражение, которому должен соответствовать запрашиваемый URL
  • timeout: таймаут в милисекундах, который hashbang будет дожидаться события Sunscraper.finish()

Предположим, что для запуска сервиса мы используем модуль Passenger [11], который реализует работу с Rack на базе Nginx. В этом случае для корректной работы нам нужно добиться следующего:

  • На специальном внутреннем адресе у нас должно работать приложение Hasbang
  • Все запросы, содержащие _escaped_fragment_ должны пробрасываться на это приложение, причем пробрасываться uri-escaped абсолютным урлом в параметр url=....
  • Нам нужно ограничить количество параллельных ресурсов к этому приложению, потому что врядли нас будут индексировать в сто потоков, а ресурсы WebKit любит.

Вот какой конфигурационный файл можно использовать: https://gist.github.com/2127685 [12]. Это пример использования Hashbang в Ralis-приложении.

О грустном

К сожалению, в наши родные пенаты, Яндекс, этот стандарт так и не дошел. Его поддерживает Google, его поддерживает Bing (а значит и Yahoo). Даже crawler Facebook и тот его поддерживает. А Яндекс – нет. Это значит, что Hashbang никак не поможет вашей индексации в отечественном сегменте интернета. По крайней мере пока. Мы направляем яростные лучики добра в сторону команды Яндекса и желаем им поскорее обратить свой взор на столь активно развивающийся технологический сегмент Web'а :).

В заключение

Несмотря на то, что мы уже используем Hashbang в бою, мы еще не обкатали его на всех возможных конфигурациях. Если у вас возникнут какие-то проблемы при его сборке или настройке, мы всегда рады новым Issues на гитхабе [13].

Спасибо :).

Автор: inossidabile


Сайт-источник PVSM.RU: https://www.pvsm.ru

Путь до страницы источника: https://www.pvsm.ru/javascript/3861

Ссылки в тексте:

[1] Joosy: http://guides.joosy.ws/

[2] Google AJAX Crawling: https://developers.google.com/webmasters/ajax-crawling/

[3] статью про то как это работает: http://habrahabr.ru/post/71838/

[4] Hashbang: http://github.com/roundlake/hashbang

[5] Watir: http://watir.com/

[6] Qt: http://qt.nokia.com/products/

[7] Sunscraper: https://github.com/roundlake/sunscraper

[8] FFI: https://github.com/ffi/ffi

[9] Homebrew: http://mxcl.github.com/homebrew/

[10] специального репозитория: https://github.com/roundlake/hashbang-sample

[11] Passenger: http://www.modrails.com/

[12] https://gist.github.com/2127685: https://gist.github.com/2127685

[13] новым Issues на гитхабе: https://github.com/roundlake/hashbang/issues