Если Вам хотя бы один раз в жизни приходилось проводить анализ ссылок на странице сайта, то Вы представляете себе сколько времени может занять такой анализ, особенно, если проводить его без применения сервисоы типа pr-cy.ru. Но, даже и с применением таких мощных инструментов анализа контента на странице сайта могут возникнуть некоторые пролемы.
Например, вы работаете оптимизатором на GoGetLinks — покупаете ссылки на блогах, сайтах и при этом используете все возможные варианты размещения ссылок — от простой контекстной ссылки до ссылок-картинок. Естественно, в данном случае, в ваши задачи будет входить как минимум проверка ссылок на:
1. отсутствие атрибутов ссылки типа noindex, nofollow
2. расположение ссылки вне тегов noindex
3. точное, в соответствие с заданием, содержание анкора
4. точное значение атрибута href
5. отсутствие в ссылке каких-либо атрибутов для её скрытия, например, цвет текста, размер шрифта и т.д.
и т.д. список можно продолжать практически до бесконечности и здесь всё зависит от Ваших требований и предпочтений. Проверять руками большое количество ссылок — не вариант, т.к. потери времени будут колоссальными. Использовать сервисы? Можно, но получить всю необходимую Вам информацию тоже не получится. Как вариант, можно разработать небольшую программку, которая автоматизирует те задачи, которые необходимы именно для Вас. И в этом нам очень сильно может помочь MSHTML и Delphi.
Вообще, «обучать» машины проводить какие-либо действия занятие интересное и занимательное. Например, как научить программу «понимать», что ссылка не индексируется поисковой машиной? Одна и та же ссылка может быть записана так:
Анкор ссылки Анкор ссылки
В первом случае ссылку не увидят Рамблер и Яндекс, во втором — Google. В обоих случаях для Вас, как для оптимизатора такие ссылки не желательны.
В «обучении» программы нам поможет MSHTML. Напишем простое приложение, которое будет проверять все ссылки на странице и при этом:
1. Выписывать арибуты href и rel
2. Проверять окрестности ссылки на наличие тегов noindex.
3. Выводить сообщение о том, каким образом будет проиндексирована ссылка.
Для работы нам понадобится модуль MSHTML и, в зависимости от Ваших предпочтений, любая библиотека для работы с http-протоколом для загрузки контента страницы. Я буду, как обычно, использовать Synapse.
Приложение будет выглядеть следующим образом:
В Edit будем записывать адрес страницы для анализа, а в ListBox выводить результаты анализа.
Теперь подключаем в uses необхоимые модули и пишем первую процедуру цель которой — загрузка контента страницы и подготовка данных для анализа.
uses mshtml, httpsend{для synapse}... [...] var FMain: TFMain; Doc: IHTMLDocument2; implementation [...] procedure TFMain.LoadDocument(const URL: string); var Content: TStringList; V:OLEVariant; begin with THTTPSend.Create do begin if HTTPMethod('GET',Edit1.Text) then begin Content:=TStringList.Create; Content.LoadFromStream(Document); end else raise Exception.Create('Загрузка не удалась'); end; //Создаем документ Doc:=CoHTMLDocument.Create as IHTMLDocument2; V:=VarArrayCreate([0,0],varVariant); V[0]:=Content.Text; Doc.write(PSafeArray(TVarData(v).VArray)); end;
Теперь нам необходимо выбрать из документа все имеющиеся в нем ссылки и провести анализ. Вначале приведу полный листинг процедуры:
procedure TFMain.Button1Click(Sender: TObject); var i,j:integer; Link: IHTMLElement; Parent: IHTMLElement; Child: IHTMLElementCollection; RelAttr,Anchor : string; begin LoadDocument(Edit1.Text); for I := 0 to Doc.links.length - 1 do begin Link:=Doc.links.item(i,0)as IHTMLElement; ListBox1.Items.Add('-------'+IntToStr(Link.sourceIndex)+'-------'); Anchor:=Link.innerText; if length(Trim(Anchor))>0 then ListBox1.Items.Add('Анкор: '+Anchor) else ListBox1.Items.Add('Анкор - картинка или другой объект'); ListBox1.Items.Add('href: '+ Link.getAttribute('href',0)); RelAttr:=Link.getAttribute('rel',0); if length(Trim(RelAttr))>0 then begin ListBox1.Items.Add('rel: '+RelAttr); if pos('nofollow',lowercase(RelAttr))>0 then ListBox1.Items.Add('НЕ ИНДЕКСИРУЕТСЯ GOOGLE'); end; parent:=Link.parentElement as IHTMLElement; child:=parent.all as IHTMLElementCollection; for j:= Child.length - 1 downto 0 do begin Parent:=child.item(j,0) as IHTMLElement; if (Parent<>nil)and(Parent.sourceIndex<=(Link.sourceIndex-1)) then begin if Parent.tagName='NOINDEX' then begin ListBox1.Items.Add('НЕ ИНДЕКСИРУЕТСЯ РАМБЛЕРОМ И ЯНДЕКСОМ'); break; end; end; end; end; end;
Теперь рассмотрим всю процедуру по частям. Вначале мы получаем коллекцию ссылок в документе проходим по всей коллекции в цикле:
for I := 0 to Doc.links.length - 1 do begin Link:=Doc.links.item(i,0)as IHTMLElement;//элемент ссылки [...]
Дальше мы выписываем в ListBox порядковый номер элемента в исходнике HTML и получаем текст анкора ссылки:
ListBox1.Items.Add('-------'+IntToStr(Link.sourceIndex)+'-------'); Anchor:=Link.innerText; //анкор ссылки
Если анкор оказывается пустым, то это значит, что для ссылки используется картинка или другой элемент, но не текст, поэтому выводим соответствующие сообщения в ListBox:
if length(Trim(Anchor))>0 then ListBox1.Items.Add('Анкор: '+Anchor) else ListBox1.Items.Add('Анкор - картинка или другой объект');
Далее получаем адрес на который ведет ссылка (атрибут href) и проверяем атрибут rel на наличие nofollow. Если nofollow присутствует, то это означает, что ссылка не проиндексируется Гуглом. Очем мы и сообщаем в ListBox:
ListBox1.Items.Add('href: '+ Link.getAttribute('href',0)); RelAttr:=Link.getAttribute('rel',0); if length(Trim(RelAttr))>0 then begin ListBox1.Items.Add('rel: '+RelAttr); if pos('nofollow',lowercase(RelAttr))>0 then ListBox1.Items.Add('НЕ ИНДЕКСИРУЕТСЯ GOOGLE'); end;
А дальше начинается самое интересное — проверка окрестности ссылки на наличие noindex. Для проверки я использовал свойство IHTMLElement — parentElement. Это свойство определяет HTML-элемент документа в котором содержится элемент, в данном случае — анализируемая ссылка. Свойство parentElement возвращает нам такие HTML-элементы как p, div, li и т.д. Например, если мы будем анализировать ссылку, содержащуюся в таком фргменте HTML:
то parentElement вернет нам DIV. Таким образом, для того, чтобы сделать вывод о том, индексируется ли ссылка Яндексом и Рамблером, нам необходимо:
1. Получить parentElement для ссылки
2. Пройтись по всей коллекции элементов, которые являются для parentElement дочерними и определить есть ли перед ссылкой тэг noindex.
Для упрощения этой задачи я использую свойство элемента IHTMLElement sourceIndex по которому определяю, что полученный элемент коллекции находится перед ссылкой. А также проожу второй цикл в обратном порядке — от последнего элемента к первому:
parent:=Link.parentElement as IHTMLElement;//gjkexbkb hjlbntkmcrbq'ktvtyn child:=parent.all as IHTMLElementCollection;//коллекчия "детей" для parent for j:= Child.length - 1 downto 0 do begin Parent:=child.item(j,0) as IHTMLElement;//отдельный элемент коллекции if (Parent<>nil)and(Parent.sourceIndex<=(Link.sourceIndex-1)) then begin if Parent.tagName='NOINDEX' then //встретился тэг noindex begin ListBox1.Items.Add('НЕ ИНДЕКСИРУЕТСЯ РАМБЛЕРОМ И ЯНДЕКСОМ'); break;//дальше можно не проверять end; end; end;
После выполнения этой процедуры анализа вид программы может быть следующим:
Возможности программы можно развивать как угодно: можно «научить» программу анализировать в каком месте стоит ссылка — отдельно или в предложении, какие атрибуты имеет картинка ссылки, выделять только внешние или только внутренние ссылки и т.д. А мне остается только выложить исходники, рассмотренной в статье программы, чтобы Вы могли продолжить изучение mshtml.
С недавнего времени Яндекс, работает с rel=nofollow также, как и Google (http://ru.wikipedia.org/wiki/Nofollow#nofollow_.D0.B8_.D0.AF.D0.BD.D0.B4.D0.B5.D0.BA.D1.81)
Доброго времени суток!
При получении относительной ссылки, Link.getAttribute(‘href’,0) начинается с ‘about’. Можно ли получить ссылку в том виде, в каком она есть в коде?
Приветствую, Keeper!
На память реализацию не помню, но то, что можно получить ссылку можно знаю точно. По-моему эту тему подробно рассматривала Маша в своем блоге «Парсинг от А до Я» где-то в ранних своих статьях.
Русский текст ссылок в листбоксе отображается кракозябой, не подскажете как это исправить?
Конвертировать текст UTF-8 в ANSI