如何在Ruby中更新XML文件?

Rad*_*dek 6 ruby xml nokogiri

我有两个XML文件需要使用Ruby进行更新.如果使用Nokogiri完成它会很棒.有人可以帮我怎么做?

Q1:我需要更新<runName>标签

<?xml version="1.0" encoding="ISO-8859-1"?><taftasks>
<taftask environment="Local_edu" password="12324" username="edu">
<testsuite name="login">
<rowsToRun>0</rowsToRun>
<runName>Login_Run 201107041433</runName>
<runDescription>ant</runDescription>
</testsuite>
</taftask>
</taftasks>
Run Code Online (Sandbox Code Playgroud)

Q2:在第二个文件中,我需要更改日志的路径.所以

<property name="reportDir" value="C:\Program Files\TestPro\TestPro Automation Framework\Output Files\builds\basics\logs\" />
Run Code Online (Sandbox Code Playgroud)

看起来像

<property name="reportDir" value="C:\Program Files\TestPro\TestPro Automation Framework\Output Files\builds\basics\logs\201107060928" />

<?xml version="1.0"?>
<!-- build script for TAF command line execution  
<property name="lib.dir" value="${basedir}/lib" />
<project name="Login" default="taf" basedir=".">
-->

<project name="Basics of Edu" default="taf" basedir="C:/Program Files/TestPro/TestPro Automation Framework">
<description>Login_cycle</description>
<property name="lib.dir" value="${basedir}/lib" />
<property name="testPlan" value="C:\Program Files\TestPro\TestPro Automation Framework\Output Files\builds\basics\basics.xml" />
<property name="reportDir" value="C:\Program Files\TestPro\TestPro Automation Framework\Output Files\builds\basics\logs\" />
<property name="format" value="csv" />
<property name="category" value="All" />

</project>
Run Code Online (Sandbox Code Playgroud)

这是与这些问题相关的源代码:

Q1:

require 'rubygems' 
require 'nokogiri'

file_name = 'C:\web\playground\login.xml'
@doc = Nokogiri::XML(File.open(file_name))
runName = @doc.at_css "runName"
puts runName.content 
runName.content = "New run name"
puts runName.content
File.open(file_name, 'w') {|f| f.write(@doc) }
Run Code Online (Sandbox Code Playgroud)

Q2:有关如何value仅搜索一行的任何建议吗?

require 'rubygems' 
require 'nokogiri'

file_name = 'C:\web\playground\login_build.xml'
@doc = Nokogiri::XML(File.open(file_name))

property = @doc.css("property")

property.each {|item|
  if (item['name'] == 'reportDir')
    puts item['value']
    item['value'] = item['value']+'\timestamp'
    puts item['value']
  end
}

File.open(file_name, 'w') {|f| f.write(@doc) }
Run Code Online (Sandbox Code Playgroud)

the*_*Man 9

Q1:

更换:

File.open(file_name, 'w') {|f| f.write(@doc) }
Run Code Online (Sandbox Code Playgroud)

有:

File.open(file_name, 'w') {|f| f.puts @doc.to_xml }
Run Code Online (Sandbox Code Playgroud)

或更好:

File.write(file_name, @doc.to_xml)
Run Code Online (Sandbox Code Playgroud)

你不想要对象@doc,你想要它的XML表示.

Q2:

property = @doc.css("property")
Run Code Online (Sandbox Code Playgroud)

应该:

property = @doc.at('property[name="reportDir"]')
Run Code Online (Sandbox Code Playgroud)

您只需要该特定节点,因此请明确查找.

更换:

property.each {|item|
  if (item['name'] == 'reportDir')
    puts item['value']
    item['value'] = item['value']+'\timestamp'
    puts item['value']
  end
}
Run Code Online (Sandbox Code Playgroud)

有:

property['value'] = property['value'] + 'timestamp'
Run Code Online (Sandbox Code Playgroud)

更换:

File.open(file_name, 'w') {|f| f.write(@doc) }
Run Code Online (Sandbox Code Playgroud)

有:

File.open(file_name, 'w') {|f| f.puts @doc.to_xml }
Run Code Online (Sandbox Code Playgroud)

同样,您不希望该对象@doc,您想要它的XML表示.

  • @doc不是XML.它是一个表示已解析的XML DOM的对象.当对象转换为字符串时,您依赖于Nokogiri输出XML的行为.而不是依赖于默认行为,明确安全; 这样,Nokogiri的默认行为可以改变,您的代码将继续正常工作. (2认同)