英文:
Parsing xml in Go
问题
我想解析类似示例中结构化的XML的位。我一直遇到值为空的问题。这只是我正在处理的简化版本,只是为了显示问题。
package main
import (
"encoding/xml"
"fmt"
)
type Entry struct {
VulnCveId string `xml:"entry>vuln:cve-id"`
}
func main() {
v := Entry{}
err := xml.Unmarshal([]byte(data), &v)
if err != nil {
fmt.Printf("error: %v", err)
return
}
fmt.Println(v.VulnCveId)
}
const data = `
<entry id="CVE-2005-4895">
<vuln:vulnerable-configuration id="http://nvd.nist.gov/">
<cpe-lang:logical-test negate="false" operator="OR">
<cpe-lang:fact-ref name="cpe:/a:csilvers:gperftools:0.3" />
<cpe-lang:fact-ref name="cpe:/a:csilvers:gperftools:0.2" />
<cpe-lang:fact-ref name="cpe:/a:csilvers:gperftools:0.1" />
</cpe-lang:logical-test>
</vuln:vulnerable-configuration>
<vuln:vulnerable-software-list>
<vuln:product>cpe:/a:csilvers:gperftools:0.3</vuln:product>
<vuln:product>cpe:/a:csilvers:gperftools:0.1</vuln:product>
<vuln:product>cpe:/a:csilvers:gperftools:0.2</vuln:product>
</vuln:vulnerable-software-list>
<vuln:cve-id>CVE-2005-4895</vuln:cve-id>
<vuln:published-datetime>2012-07-25T15:55:01.273-04:00</vuln:published-datetime>
<vuln:last-modified-datetime>2012-08-09T00:00:00.000-04:00</vuln:last-modified-datetime>
<vuln:cvss>
<cvss:base_metrics>
<cvss:score>5.0</cvss:score>
<cvss:access-vector>NETWORK</cvss:access-vector>
<cvss:access-complexity>LOW</cvss:access-complexity>
<cvss:authentication>NONE</cvss:authentication>
<cvss:confidentiality-impact>NONE</cvss:confidentiality-impact>
<cvss:integrity-impact>NONE</cvss:integrity-impact>
<cvss:availability-impact>PARTIAL</cvss:availability-impact>
<cvss:source>http://nvd.nist.gov</cvss:source>
<cvss:generated-on-datetime>2012-07-26T08:38:00.000-04:00</cvss:generated-on-datetime>
</cvss:base_metrics>
</vuln:cvss>
<vuln:cwe id="CWE-189" />
<vuln:references xml:lang="en" reference_type="UNKNOWN">
<vuln:source>MISC</vuln:source>
<vuln:reference href="http://kqueue.org/blog/2012/03/05/memory-allocator-security-revisited/" xml:lang="en">http://kqueue.org/blog/2012/03/05/memory-allocator-security-revisited/</vuln:reference>
</vuln:references>
<vuln:references xml:lang="en" reference_type="UNKNOWN">
<vuln:source>CONFIRM</vuln:source>
<vuln:reference href="http://code.google.com/p/gperftools/source/browse/tags/perftools-0.4/ChangeLog" xml:lang="en">http://code.google.com/p/gperftools/source/browse/tags/perftools-0.4/ChangeLog</vuln:reference>
</vuln:references>
<vuln:summary>Multiple integer overflows in TCMalloc (tcmalloc.cc) in gperftools before 0.4 make it easier for context-dependent attackers to perform memory-related attacks such as buffer overflows via a large size value, which causes less memory to be allocated than expected.</vuln:summary>
</entry>
`
在这个实例中,v.VulnCveId为空。我做错了什么?
英文:
I'd like to parse bits of XML structured like those in the example. I keep running into values being empty. This is a simplified version of what I'm working with, just to show the issue.
package main
import (
"encoding/xml"
"fmt"
)
type Entry struct {
VulnCveId string `xml:"entry>vuln:cve-id"`
}
func main() {
v := Entry{}
err := xml.Unmarshal([]byte(data), &v)
if err != nil {
fmt.Printf("error: %v", err)
return
}
fmt.Println(v.VulnCveId)
}
const data = `
<entry id="CVE-2005-4895">
<vuln:vulnerable-configuration id="http://nvd.nist.gov/">
<cpe-lang:logical-test negate="false" operator="OR">
<cpe-lang:fact-ref name="cpe:/a:csilvers:gperftools:0.3" />
<cpe-lang:fact-ref name="cpe:/a:csilvers:gperftools:0.2" />
<cpe-lang:fact-ref name="cpe:/a:csilvers:gperftools:0.1" />
</cpe-lang:logical-test>
</vuln:vulnerable-configuration>
<vuln:vulnerable-software-list>
<vuln:product>cpe:/a:csilvers:gperftools:0.3</vuln:product>
<vuln:product>cpe:/a:csilvers:gperftools:0.1</vuln:product>
<vuln:product>cpe:/a:csilvers:gperftools:0.2</vuln:product>
</vuln:vulnerable-software-list>
<vuln:cve-id>CVE-2005-4895</vuln:cve-id>
<vuln:published-datetime>2012-07-25T15:55:01.273-04:00</vuln:published-datetime>
<vuln:last-modified-datetime>2012-08-09T00:00:00.000-04:00</vuln:last-modified-datetime>
<vuln:cvss>
<cvss:base_metrics>
<cvss:score>5.0</cvss:score>
<cvss:access-vector>NETWORK</cvss:access-vector>
<cvss:access-complexity>LOW</cvss:access-complexity>
<cvss:authentication>NONE</cvss:authentication>
<cvss:confidentiality-impact>NONE</cvss:confidentiality-impact>
<cvss:integrity-impact>NONE</cvss:integrity-impact>
<cvss:availability-impact>PARTIAL</cvss:availability-impact>
<cvss:source>http://nvd.nist.gov</cvss:source>
<cvss:generated-on-datetime>2012-07-26T08:38:00.000-04:00</cvss:generated-on-datetime>
</cvss:base_metrics>
</vuln:cvss>
<vuln:cwe id="CWE-189" />
<vuln:references xml:lang="en" reference_type="UNKNOWN">
<vuln:source>MISC</vuln:source>
<vuln:reference href="http://kqueue.org/blog/2012/03/05/memory-allocator-security-revisited/" xml:lang="en">http://kqueue.org/blog/2012/03/05/memory-allocator-security-revisited/</vuln:reference>
</vuln:references>
<vuln:references xml:lang="en" reference_type="UNKNOWN">
<vuln:source>CONFIRM</vuln:source>
<vuln:reference href="http://code.google.com/p/gperftools/source/browse/tags/perftools-0.4/ChangeLog" xml:lang="en">http://code.google.com/p/gperftools/source/browse/tags/perftools-0.4/ChangeLog</vuln:reference>
</vuln:references>
<vuln:summary>Multiple integer overflows in TCMalloc (tcmalloc.cc) in gperftools before 0.4 make it easier for context-dependent attackers to perform memory-related attacks such as buffer overflows via a large size value, which causes less memory to be allocated than expected.</vuln:summary>
</entry>
`
v.VulnCveId is empty in this instance. What am I doing wrong?
答案1
得分: 2
问题是你没有命名空间。你有一个前缀“vuln”,但它没有在任何地方声明。实际上,它甚至不是有效的XML。
将第一行改为:
<entry xmlns:vuln="http://my-namespace.com" id="CVE-2005-4895">
然后将你的结构标签改为:
`xml:"entry>http://my-namespace.com cve-id"`
然后你就可以继续了。
英文:
The problem is that you don't have a namespace. You have a prefix, "vuln", but it's not declared anywhere. It's actually not even valid XML.
Make the first line this:
<entry xmlns:vuln="http://my-namespace.com" id="CVE-2005-4895">
then make your struct tag this
`xml:"entry>http://my-namespace.com cve-id"`
and you should be good to go.
答案2
得分: 1
VulnCveId string xml:"cve-id"
这将返回一个非空的 v.VulnCveId
。
英文:
Note: the same query without the namespace: http://play.golang.org/p/Gh5WltGzw3
VulnCveId string `xml:"cve-id"`
That will return a non-empty v.VulnCveId
.
答案3
得分: 1
VulnCveId string xml:"vuln cve-id"
这也可以使用空格代替冒号来命名空间。
英文:
VulnCveId string xml:"vuln cve-id"
this can also work namespace use space instead of colon
答案4
得分: 0
这对我来说看起来几乎像是一个bug。
- http://play.golang.org/p/ym8zshlUC6 如果我删除你标签中的entry>部分,这个工作的简化案例就可以工作了,根据文档,这是不必要的。
- http://play.golang.org/p/3zt09n5fYa 但是对于你的代码做同样的事情却不起作用,所以这肯定有问题。
英文:
This looks like a bug almost to me.
- http://play.golang.org/p/ym8zshlUC6 Working reduced case if I remove the entry> portion of your tag. which shouldn't be necessary according to the docs.
- http://play.golang.org/p/3zt09n5fYa But doing the same thing for your code doesn't work so this definitely smells fishy.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论