使用Nokogiri搜索XML文档以获取特定路径并进行更改(使用前面的Cucumber)
我想在XML文档中搜索特定路径,然后将其更改为其他路径。这是XML的相关部分:
<Root>
<Application>
<Connections>
<AutoAccept>true</AutoAccept>
<AllowDomains/>
</Connections>
<Streams>
<StreamType>default</StreamType>
<StorageDir>/C:/blah/flash/</StorageDir>
我想将“/ C:/ blah / flash /”更改为其他值。这就是我的代码方式:
Given(/^Update the Apreso configuration file$/) do
xmldoc = Nokogiri::XML(DATA['DATA_WOWZA1'])
xmldoc.search("/Root/Application/Streams/StorageDir").each do |node|
node.content = "Newpath"
end
puts xmldoc.to_xml
end
“DATA_WOWZA1”是我通过YAML文件传递的XML文件的路径。当我运行它传递的代码但XML文件没有反映出变化时,想法?
答案 0 :(得分:1)
您需要为Nokogiri::XML
提供一串XML,而不是文件路径字符串。尝试:
xmldoc = Nokogiri::XML(File.read DATA['DATA_WOWZA1'])
但是,获得原始XML输出并没有意义。您确定您的测试正在输出XML吗?
如果您想将文件保存到位,则需要执行以下操作:
File.open(DATA['DATA_WOWZA1'], 'w') { |f| f.puts xmldoc.to_xml }
答案 1 :(得分:0)
如果只有一个StorageDir
节点,那么您的工作太辛苦了:
require 'nokogiri'
doc = Nokogiri::XML(<<EOT)
<Root>
<Application>
<Connections>
<AutoAccept>true</AutoAccept>
<AllowDomains/>
</Connections>
<Streams>
<StreamType>default</StreamType>
<StorageDir>/C:/blah/flash/</StorageDir>
</Streams>
</Application>
</Root>
EOT
doc.at('StorageDir').content = 'd:/path/to/foo'
puts doc.to_xml
# >> <?xml version="1.0"?>
# >> <Root>
# >> <Application>
# >> <Connections>
# >> <AutoAccept>true</AutoAccept>
# >> <AllowDomains/>
# >> </Connections>
# >> <Streams>
# >> <StreamType>default</StreamType>
# >> <StorageDir>d:/path/to/foo</StorageDir>
# >> </Streams>
# >> </Application>
# >> </Root>
也可以轻松覆盖原始文件。这是未经测试的,但看起来不错:
XML_FILE = 'path/to/xml'
doc = Nokogiri::XML(open(XML_FILE, 'r'))
doc.at('StorageDir').content = 'd:/path/to/foo'
File.write("#{ XML_FILE }.new", doc.to_xml)
注意,我没有覆盖原始文件,我正在写一个新文件。如果代码出现问题,例如修改错误的节点,这将保留旧文件而不是破坏其内容。
在生产系统中,您希望写入新文件,然后将旧文件重命名为安全文件,将新文件重命名为旧文件名,然后选择删除旧文件。 #39;确保一切正常。通过这样做,如果出现问题,你就可以了。