diff -r 569833f08780 -r 9fe022261dcc structs.go --- a/structs.go Fri Dec 30 18:25:08 2011 -0700 +++ b/structs.go Fri Dec 30 21:49:00 2011 -0700 @@ -95,6 +95,11 @@ XError() *Error // A (non-error) nested element, if any. XChild() *Generic + innerxml() string +} + +type ExtendedStanza interface { + InnerMarshal(io.Writer) os.Error } // message stanza @@ -104,6 +109,7 @@ Id string `xml:"attr"` Type string `xml:"attr"` Lang string `xml:"attr"` + Innerxml string `xml:"innerxml"` Error *Error Subject *Generic Body *Generic @@ -112,6 +118,7 @@ } var _ xml.Marshaler = &Message{} var _ Stanza = &Message{} +var _ ExtendedStanza = &Message{} // presence stanza type Presence struct { @@ -120,6 +127,7 @@ Id string `xml:"attr"` Type string `xml:"attr"` Lang string `xml:"attr"` + Innerxml string `xml:"innerxml"` Error *Error Show *Generic Status *Generic @@ -128,6 +136,7 @@ } var _ xml.Marshaler = &Presence{} var _ Stanza = &Presence{} +var _ ExtendedStanza = &Presence{} // iq stanza type Iq struct { @@ -136,30 +145,13 @@ Id string `xml:"attr"` Type string `xml:"attr"` Lang string `xml:"attr"` + Innerxml string `xml:"innerxml"` Error *Error Any *Generic - Query *RosterQuery } var _ xml.Marshaler = &Iq{} var _ Stanza = &Iq{} -// Roster query/result -type RosterQuery struct { - // Should always be query in the NsRoster namespace - XMLName xml.Name - Item []RosterItem -} - -// See RFC 3921, Section 7.1. -type RosterItem struct { - // Should always be "item" - XMLName xml.Name - Jid string `xml:"attr"` - Subscription string `xml:"attr"` - Name string `xml:"attr"` - Group []string -} - // Describes an XMPP stanza error. See RFC 3920, Section 9.3. type Error struct { // The error type attribute. @@ -282,8 +274,6 @@ u.XMLName.Local) } -// BUG(cjyar) This is fragile. We should find a way to use go's native -// XML marshaling. func marshalXML(st Stanza) ([]byte, os.Error) { buf := bytes.NewBuffer(nil) buf.WriteString("<") @@ -304,15 +294,22 @@ writeField(buf, "xml:lang", st.XLang()) } buf.WriteString(">") - if st.XError() != nil { - bytes, _ := st.XError().MarshalXML() - buf.WriteString(string(bytes)) - } - if st.XChild() != nil { - xml.Marshal(buf, st.XChild()) - } - if iq, ok := st.(*Iq) ; ok && iq.Query != nil { - xml.Marshal(buf, iq.Query) + if ext, ok := st.(ExtendedStanza) ; ok { + if st.XError() != nil { + bytes, _ := st.XError().MarshalXML() + buf.WriteString(string(bytes)) + } + err := ext.InnerMarshal(buf) + if err != nil { + return nil, err + } + } else { + inner := st.innerxml() + if inner == "" { + xml.Marshal(buf, st.XChild()) + } else { + buf.WriteString(st.innerxml()) + } } buf.WriteString("