Как получить идентификатор (например, xpath) из объекта nokogiri? - PullRequest
4 голосов
/ 19 августа 2011

Прогулка по нокогири и выбор элементов с помощью xpath довольно просты.Мне нужно наоборот, то есть: мне нужно, например, вызвать .to_xpath на узле nokogiri, чтобы получить полный путь xpath элемента для сохранения его в записи.

Любой знает способ сделать это

Ответы [ 2 ]

11 голосов
/ 19 августа 2011

Самый простой способ, которым я могу думать, был бы:

Nokogiri::CSS.xpath_for node.css_path

РЕДАКТИРОВАТЬ: вы можете попробовать path метод тоже.

1 голос
/ 19 августа 2011

Самая простая вещь, о которой я могу подумать, это использовать parent для построения пути элемента обратно к корню (то есть обратно к <html>) и previous_elementв каждом узле, чтобы выяснить числовой индекс этого узла среди его братьев и сестер.Поскольку будет ровно один <body> и <html> (Нокогири добавит их для вас за вашей спиной, если необходимо), вы можете перестать ходить по родителям, как только вы нажмете на узел <body>.

Алгоритмвыглядит следующим образом:

  1. Инициализация: path = [ ], n - это узел, который у вас уже есть.
  2. Установите s = n и звоните s = s.previous_element до s.nil? и считайтесколько итераций вы сделали, это даст вам позицию n среди его братьев и сестер.Поместите позицию в index.Имейте в виду, что позиции XPath основаны на одном.
  3. Сохраните новый компонент пути: path.unshift('*[' + index.to_s + ']').
  4. Установите p = n.parent, если p не является <body>, тогда n = p и вернитесь к шагу 2.
  5. Добавьте последние известные нам компоненты: path.unshift('body').unshift('html').
  6. Создайте выражение XPath: xpath = '/' + path.join('/')

Итак, учитывая некоторый HTML-код вроде этого:

<ul><li>a</li><li><b>b<em>c</em></b></li></ul>

и начальный узел <em>c</em>, вы получите XPath, подобный этому:

/html/body/*[1]/*[2]/*[1]/*[1]

Не совсем красивоно, по крайней мере, процесс довольно прост, и результирующий XPath будет уникальным.

Если вам нужны пути к большинству узлов в DOM, вы можете начать с корня и нумеровать все узлы на пути вниз,Таким образом, вы могли бы избежать прогулки с братьями и сестрами снова и снова.

...