Example #1
0
func main() {
	// fmt.Println(string(data))
	rdr := bytes.NewReader(data)
	var m mxj.Map
	var err error
	// We read processing docs sequentially.
	// Un-rooted ProcInst or Comments are processed AND just reencoded. (XmlSeqIndent() knows how, now.)
	for m, err = mxj.NewMapXmlSeqReader(rdr); m != nil || err != io.EOF; m, err = mxj.NewMapXmlSeqReader(rdr) {
		if err != nil {
			if err != mxj.NO_ROOT {
				fmt.Println("NewMapXmlSeq err:", err)
				fmt.Println("m:", m)
			} else if m != nil {
				x, _ := m.XmlSeqIndent("", "  ")
				fmt.Println(string(x))
			}
			continue
		}
		// fmt.Println(m.StringIndent())

		// We have Two different arrays of Items in the XML doc, one nested in the other.
		if err = copyCmts(m, "WebTest.Items"); err != nil {
			fmt.Println("err:", err)
		}
		if err = copyCmts(m, "WebTest.Items.TransactionTimer.Items"); err != nil {
			fmt.Println("err:", err)
		}
		// re-encode the map with the Items.Comment[#seq==n].#attr.CommentText
		// values copied to the Items.Request[#seq==n+1].#attr.ReportingName elements.
		b, err := m.XmlSeqIndent("", "  ")
		if err != nil {
			fmt.Println("XmlIndent err:", err)
			return
		}
		fmt.Println(string(b))
	}
}
Example #2
0
func main() {
	// fmt.Println(string(data))
	rdr := bytes.NewReader(data)
	// We read processing docs sequentially.
	// Un-rooted ProcInst or Comments are processed AND just re-encoded. (XmlSeqIndent() knows how, now.)
	for m, err := mxj.NewMapXmlSeqReader(rdr); m != nil || err != io.EOF; m, err = mxj.NewMapXmlSeqReader(rdr) {
		if err != nil {
			if err != mxj.NoRoot {
				fmt.Println("NewMapXmlSeq err:", err)
				fmt.Println("m:", m)
			} else if m != nil {
				x, _ := m.XmlSeqIndent("", "  ")
				fmt.Println(string(x))
			}
			continue
		}
		// fmt.Println(m.StringIndent())

		// get the array of TransactionTimer  entries for the 'path'
		vals, err := m.ValuesForPath("WebTest.Items.TransactionTimer")
		if err != nil {
			fmt.Printf("ValuesForPath err: %s", err.Error())
			continue
		} else if len(vals) == 0 {
			fmt.Printf("no vals for WebTest.Items.TransactionTimer")
			continue
		}
		// process each TransactionTimer element ...
		for _, t := range vals {
			tmap := t.(map[string]interface{})
			// get Name from attrs
			tname, _ := mxj.Map(tmap).ValueForPathString("#attr.Name.#text")

			// now process TransactionTimer.Items value ... is a map[string]interface{} value
			// with Comment and Request keys with array values
			vm, ok := tmap["Items"].(map[string]interface{})
			if !ok {
				fmt.Println("assertion failed")
				return
			}
			// get the Comment list
			c, ok := vm["Comment"]
			if !ok { // --> no Items.Comment elements
				continue
			}
			// Don't assume that Comment is an array.
			// There may be just one value, in which case it will decode as map[string]interface{}.
			switch c.(type) {
			case map[string]interface{}:
				c = []interface{}{c}
			}
			cmt := c.([]interface{})
			// get the Request list
			r, ok := vm["Request"]
			if !ok { // --> no Items.Request elements
				continue
			}
			// Don't assume the Request is an array.
			// There may be just one value, in which case it will decode as map[string]interface{}.
			switch r.(type) {
			case map[string]interface{}:
				r = []interface{}{r}
			}
			req := r.([]interface{})

			// fmt.Println("Comment:", cmt)
			// fmt.Println("Request:", req)

			// Comment elements with #seq==n are followed by Request element with #seq==n+1.
			// For each Comment.#seq==n extract the CommentText attribute value and use it to
			// set the ReportingName attribute value in Request.#seq==n+1.
			for _, v := range cmt {
				vmap := v.(map[string]interface{})
				seq := vmap["#seq"].(int) // type is int
				// extract CommentText attr from array of "#attr"
				acmt, _ := mxj.Map(vmap).ValueForPathString("#attr.CommentText.#text")
				if acmt == "" {
					fmt.Println("no CommentText value in Comment attributes")
				}
				// fmt.Println(seq, acmt)
				// find the request with the #seq==seq+1 value
				var r map[string]interface{}
				for _, vv := range req {
					rt := vv.(map[string]interface{})
					if rt["#seq"].(int) == seq+1 {
						r = rt
						break
					}
				}
				if r == nil { // no Request with #seq==seq+1
					continue
				}
				if err := mxj.Map(r).SetValueForPath(tname+", "+acmt, "#attr.ReportingName.#text"); err != nil {
					fmt.Println("SetValueForPath err:", err)
					break
				}
			}
		}

		// re-encode the map with the TransactionTimer.#attr.Name & Items.Comment[#seq==n].#attr.CommentText
		// values copied to the Items.Request[#seq==n+1].#attr.ReportingName elements.
		b, err := m.XmlSeqIndent("", "  ")
		if err != nil {
			fmt.Println("XmlIndent err:", err)
			return
		}
		fmt.Println(string(b))
	}
}