英文:
How to parse Soap Envelope in Golang ?
问题
我是你的中文翻译助手,以下是你要翻译的内容:
我对golang和Soap都不太熟悉,在解析Soap消息时遇到了问题。
-
我有一个Soap消息:
<soap:Envelope SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/">
soap:Body
<activationPack_completeResponse"http://tempuri.org/">
<activationPack_completeResult xsi:type="xsd:string">Active</activationPack_completeResult>
</activationPack_completeResponse>
</soap:Body>
</soap:Envelope>
现在我应该如何在golang中解析它们?对于Soap Envelope,我的结构声明应该是什么样的?
我有以下一些结构:
type MyRespEnvelope struct {
XMLName xml.Name `xml:"http://schemas.xmlsoap.org/soap/envelope/ Envelope"`
Soap *Body
}
type Body struct {
XMLName xml.Name `xml:"http://schemas.xmlsoap.org/soap/envelope/ Body"`
GetResponse *ActivationPack_CompleteResponse
}
type ActivationPack_CompleteResponse struct {
XMLName xml.Name `xml:"activationPack_completeResponse"`
Id string `xml:"xmlns,attr"`
MyVar string `xml:"activationPack_completeResult"`
}
但是我得到了以下错误:
error: expected element <Envelope> in name space http://schemas.xmlsoap.org/soap/envelope/ but have soap*stopped,reason="end-stepping-range",frame={addr="0x0000000000401211",func="main.UnmarshalFirstDitto",args=[{name="data",value="\"\\nNotice: Undefined variable: area in /var/www/nusoap/dittotv.php on line 25\\n\\nNotice: Undefined variable: area in /var/www/nusoap/dittotv.php on line 27\\n\\nNotice: Undefined variable: area in /var/www/nu\"..."}],file="/media/winshare/Golang/WorkSpace/src/DittoTv/ditto.go",fullname="/media/winshare/Golang/WorkSpace/src/DittoTv/ditto.go",line="60"},thread-id="1",stopped-threads="all",core="0"
请问有人可以告诉我如何声明我的结构,以便能够解析Soap消息吗?
英文:
I am new to golang and Soap and having trouble in parsing soap msg.
1.I have an Soap message
<?xml version="1.0" encoding="UTF-8"?>
<soap:Envelope SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/">
<soap:Body>
<activationPack_completeResponse"http://tempuri.org/">
<activationPack_completeResult xsi:type="xsd:string">Active</activationPack_completeResult>
</activationPack_completeResponse>
</soap:Body>
</soap:Envelope>
Now how should i Unmarshal them in golang what should be my struct declaration for tag Soap Envelope.
I have some structure as below:
type MyRespEnvelope struct {
XMLName xml.Name `xml:"http://schemas.xmlsoap.org/soap/envelope/ Envelope"`
Soap *Body
}
type Body struct {
XMLName xml.Name `xml:"http://schemas.xmlsoap.org/soap/envelope/ Body"`
GetResponse *ActivationPack_CompleteResponse
}
type ActivationPack_CompleteResponse struct {
XMLName xml.Name `xml:"activationPack_completeResponse"`
Id string `xml:"xmlns,attr"`
MyVar string `xml:"activationPack_completeResult"`
}
But I am getting error as below:
error: expected element <Envelope> in name space http://schemas.xmlsoap.org/soap/envelope/ but have soap*stopped,reason="end-stepping-range",frame={addr="0x0000000000401211",func="main.UnmarshalFirstDitto",args=[{name="data",value="\"\\nNotice: Undefined variable: area in /var/www/nusoap/dittotv.php on line 25\\n\\nNotice: Undefined variable: area in /var/www/nusoap/dittotv.php on line 27\\n\\nNotice: Undefined variable: area in /var/www/nu\"..."}],file="/media/winshare/Golang/WorkSpace/src/DittoTv/ditto.go",fullname="/media/winshare/Golang/WorkSpace/src/DittoTv/ditto.go",line="60"},thread-id="1",stopped-threads="all",core="0"
So someone please tell me how should i declare my structure so that i am able to parse the soap message.
答案1
得分: 11
你的XML格式不正确,我猜测是复制粘贴出了问题。我已经进行了修正,在第4行将<activationPack_completeResponse"http://tempuri.org/">
改为<activationPack_completeResponse Id="http://tempuri.org/">
。
你的类型定义有问题。在MyRespEnvelope
中,你将Body
结构体称为Soap
。如果没有定义其XML名称,你将无法得到任何结果。一个更简单的修复方法是将名称从Soap
改为Body
。
我不是XML的专家,但我认为你在命名空间方面做错了一些事情。我简化了你的类型定义,这里是一个可工作的示例:http://play.golang.org/p/957GWzfdvN
package main
import "fmt"
import "encoding/xml"
type MyRespEnvelope struct {
XMLName xml.Name
Body Body
}
type Body struct {
XMLName xml.Name
GetResponse completeResponse `xml:"activationPack_completeResponse"`
}
type completeResponse struct {
XMLName xml.Name `xml:"activationPack_completeResponse"`
Id string `xml:"Id,attr"`
MyVar string `xml:"activationPack_completeResult"`
}
func main() {
Soap := []byte(`<?xml version="1.0" encoding="UTF-8"?>
<soap:Envelope SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/">
<soap:Body>
<activationPack_completeResponse Id="http://tempuri.org/">
<activationPack_completeResult xsi:type="xsd:string">Active</activationPack_completeResult>
</activationPack_completeResponse>
</soap:Body>
</soap:Envelope>`)
res := &MyRespEnvelope{}
err := xml.Unmarshal(Soap, res)
fmt.Println(res.Body, err)
}
注意:在我编写的代码中,我没有使用指向结构体的指针,而是直接使用了结构体本身。你可以根据你的意图和个人偏好使用任何一种方式。
英文:
-
Your XML was malformed, I assume it's a bad copy-paste. I corrected it, line 4:
<activationPack_completeResponse"http://tempuri.org/">
-><activationPack_completeResponse Id="http://tempuri.org/">
-
Your types were wrong. in
MyRespEnvelope
you call theBody
structSoap
. Without defining its xml name you're not going to get anything. An easier fix is to change the name fromSoap
toBody
. -
I'm not an expert in XML, but I think you were doing something wrong with namespaces.
simplifying your types a little, here is a working example: http://play.golang.org/p/957GWzfdvNpackage main import "fmt" import "encoding/xml" type MyRespEnvelope struct { XMLName xml.Name Body Body } type Body struct { XMLName xml.Name GetResponse completeResponse `xml:"activationPack_completeResponse"` } type completeResponse struct { XMLName xml.Name `xml:"activationPack_completeResponse"` Id string `xml:"Id,attr"` MyVar string `xml:"activationPack_completeResult"` } func main() { Soap := []byte(`<?xml version="1.0" encoding="UTF-8"?> <soap:Envelope SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/"> <soap:Body> <activationPack_completeResponse Id="http://tempuri.org/"> <activationPack_completeResult xsi:type="xsd:string">Active</activationPack_completeResult> </activationPack_completeResponse> </soap:Body> </soap:Envelope>`) res := &MyRespEnvelope{} err := xml.Unmarshal(Soap, res) fmt.Println(res.Body, err) }
Note: In the code I put together, I don't use pointer to structs but the structs themselves. You can use either depending on how you're intending to use it, and your preferences I guess.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论