Как преобразовать XML в хэш в ruby?

#ruby-on-rails #ruby #xml #hash

#ruby-on-rails #рубиновый #xml #хэш

Вопрос:

У меня есть XML-код, который я хочу преобразовать в хэш

    <meta_description><language id="1"></language><language id="2"></language></meta_description>
    <meta_keywords><language id="1"></language><language id="2"></language></meta_keywords>
    <meta_title><language id="1"></language><language id="2" ></language></meta_title>
    <link_rewrite><language id="1" >konsult-500-krtim</language><language id="2" >konsult-500-krtim</language></link_rewrite>
    <name><language id="1" >Konsult 500 kr/tim</language><language id="2" >Konsult 500 kr/tim</language></name>
    <description><language id="1" ></language><language id="2" ></language></description>
    <description_short><language id="1" ></language><language id="2" ></language></description_short>
    <available_now><language id="1" ></language><language id="2" ></language></available_now>
    <available_later><language id="1" ></language><language id="2" ></language></available_later>
    <associations>
    <categories nodeType="category" api="categories">
    <category>
    <id>2</id>
    </category>
    </categories>
    <images nodeType="image" api="images"/>
    <combinations nodeType="combination" api="combinations"/>
    <product_option_values nodeType="product_option_value" api="product_option_values"/>
    <product_features nodeType="product_feature" api="product_features"/>
    <tags nodeType="tag" api="tags"/>
    <stock_availables nodeType="stock_available" api="stock_availables">
    <stock_available>
    <id>111</id>
    <id_product_attribute>0</id_product_attribute>
    </stock_available>
    </stock_availables>
    <accessories nodeType="product" api="products"/>
    <product_bundle nodeType="product" api="products"/>
    </associations>
 

Я хочу преобразовать этот XML — файл в хэш .
Я пытаюсь найти функции, которые преобразуют этот xml в h=Hash.new
Как я это делаю?

Комментарии:

1. Для начала, вам нужно иметь действительный HTML-код, чтобы любой из приведенных ниже ответов работал. Этот xml содержит ошибки, вы можете проверить его с помощью такого инструмента

2. Вот вариант вашего примера с удаленной ошибкой xml

Ответ №1:

Существует Hash#from_xml метод ActiveSupport, который вы можете использовать:

 xml = File.open("data.xml").read # if your xml is in the 'data.xml' file
Hash.from_xml(xml)
 

Комментарии:

1. Это работает, если вы используете Rails, в котором monkey исправляет класс Hash. Однако это не будет работать из коробки в чистом ruby.

Ответ №2:

Если вы используете Rails, вы можете использовать приведенный выше ответ, в противном случае вам может потребоваться ActiveSuppport gem:

 require 'active_support/core_ext/hash'

xml = '<foo>bar</foo>'
hash = Hash.from_xml(xml)
=>{"foo"=>"bar"}
 

Обратите внимание, что это будет работать только с допустимым xml. Смотрите Комментарии к op. Также обратите внимание, что использование атрибутов элемента, например id="1" , не будет преобразовываться обратно таким же образом, например:

 xml = %q(
  <root>
    <foo id="1"></foo>
    <bar id="2"></bar>
  </root>).strip

hash = Hash.from(xml)
=>{"root"=>{"foo"=>{"id"=>"1"}, "bar"=>{"id"=>"2"}}}

puts hash.to_xml
# will output
 
 <?xml version="1.0" encoding="UTF-8"?>
<hash>
  <root>
    <foo>
      <id>1</id>
    </foo>
    <bar>
      <id>2</id>
    </bar>
  </root>
</hash>
 

Ответ №3:

Используйте nokogiri для анализа XML-ответа на ruby hash. Это довольно быстро.

 require 'active_support/core_ext/hash'  #from_xml 
require 'nokogiri'

doc = Nokogiri::XML(response_body)
Hash.from_xml(doc.to_s)
 

Комментарии:

1. Зачем вам здесь нужен Nokogiri? если respons_body это тип xml, то он не нужен. Например Hash.from_xml(HTTParty.get('https://www.w3schools.com/xml/note.xml').body) , работает нормально. Да, я использовал HTTParty в качестве примера, но это должно проиллюстрировать суть.