Go 自定义xml解码器问题

Go 自定义xml解码器问题,go,Go,我有多个通过的测试用例,但是这一个失败了。我在这里遗漏了什么导致解码器错误读取目标密钥的内容 const respGenericFault1 = `<?xml version='1.0' encoding='UTF-8'?> <SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsi="http://www.w3.org/1999/XMLSchema-in

我有多个通过的测试用例,但是这一个失败了。我在这里遗漏了什么导致解码器错误读取目标密钥的内容

const respGenericFault1 = `<?xml version='1.0' encoding='UTF-8'?>
<SOAP-ENV:Envelope
  xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"
  xmlns:xsi="http://www.w3.org/1999/XMLSchema-instance"
  xmlns:xsd="http://www.w3.org/1999/XMLSchema">
   <SOAP-ENV:Body>
     <SOAP-ENV:Fault>
         <faultcode xsi:type="xsd:string">SOAP-ENV:Client</faultcode>
         <faultstring xsi:type="xsd:string">Failed to validate</faultstring>
     </SOAP-ENV:Fault>
  </SOAP-ENV:Body>
</SOAP-ENV:Envelope>`

type Fault struct {
    FaultCode, FaultString string
}

func (f Fault) Error() string {
    return "Fault Code: '" + f.FaultCode + "' FaultString: '" + f.FaultString + "'"
}

func ParseFault(b []byte) error {
    reader := bytes.NewReader(b)
    d := xml.NewDecoder(reader)

    var start xml.StartElement
    fault := Fault{}
    found := false

    // iterate through the tokens
    for {
        tok, _ := d.Token()
        if tok == nil {
            break
        }

        // switch on token type
        switch t := tok.(type) {
        case xml.StartElement:
            start = t.Copy()
            fmt.Println(start.Name.Local)
        case xml.CharData:
            key := strings.ToLower(start.Name.Local)
            // fault was found, capture the values and mark as found
            if key == "faultcode" {
                found = true
                fault.FaultCode = string(t)
                fmt.Printf("%#v\n", string(t))
            } else if key == "faultstring" {
                found = true
                fault.FaultString = string(t)
            }
        }
    }

    if found {
        return fault
    }
    return nil
}

func main() {
    err := ParseFault([]byte(respGenericFault1))
    fmt.Printf("%#v\n", err)
}
const respGenericFault1=`
SOAP-ENV:客户端
验证失败
`
类型断层构造{
错误代码,错误字符串
}
func(f Fault)Error()字符串{
返回“故障代码:”+f.FaultCode+“'FaultString:”“+f.FaultString+””
}
func ParseFault(b[]字节)错误{
读卡器:=字节。新建读卡器(b)
d:=xml.NewDecoder(读取器)
var start xml.StartElement
故障:=故障{}
发现:=假
//遍历标记
为了{
tok,:=d.令牌()
如果tok==nil{
打破
}
//打开令牌类型
开关t:=tok(类型){
case xml.StartElement:
start=t.Copy()
fmt.Println(start.Name.Local)
case xml.CharData:
key:=strings.ToLower(start.Name.Local)
//发现故障,捕获值并标记为已发现
if key==“faultcode”{
找到=真
fault.FaultCode=字符串(t)
fmt.Printf(“%#v\n”,字符串(t))
}如果键==“faultstring”,则为else{
找到=真
fault.FaultString=字符串(t)
}
}
}
如果找到{
回程故障
}
归零
}
func main(){
错误:=ParseFault([]字节(respGenericFault1))
fmt.Printf(“%#v\n”,err)
}

这里是操场url:

您的代码成功捕获了
错误字符串
错误代码
,但随后无意中用包含标记之间空白的
xml.CharData
覆盖它

这里有一个固定版本:。注释第52行以查看故障模式

或者,您可以使用
encoding/xml Unmarshal
将xml直接解析为结构。看