In this post, i will describe how i play with the new HMC API with Go. I am very new to Go so it was an excellent way to practice it.

github repository

I put my examples in this github repository

http session

The simplest way in go is to use net/http library.

The first step is to allow the usage of HMC self-signed certificate in the session :

tr := &http.Transport{
  TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
 }

The second is to use a cookiejar to store the session informations with net/http/cookiejar :

jar, err := cookiejar.New(nil)

It’s possible to reuse a existing jar but, for my examples, i created it from scratch.

After that, we only need to pass this parameters along the user, password and url to the http session :

&Session{client: &http.Client{Transport: tr, Jar: jar}, User: user, Password: password, url: url}

parsing xml

Trying to parse the xml response in go gave me a very good surprise. encoding/xml library provides a elegant way to parse xml based on struct.

I defined a struct with the first node of the xml response :

type Feed struct {
  XMLName xml.Name `xml:"feed"`
  Entries []Entry `xml:"entry"`
}

So here i am expecting a xml structure starting with a node which can contain multiple node described by Entry struct and so on. I show below the example where i gather Shared Storage Pool informations :

type Feed struct {
 XMLName xml.Name `xml:"feed"`
 Entries []Entry `xml:"entry"`
}
type Entry struct {
 XMLName xml.Name `xml:"entry"`
 Contents []Content `xml:"content"`
}

type Content struct {
 XMLName xml.Name `xml:"content"`
 SharedStoragePools []SharedStoragePool `xml:"http://www.ibm.com/xmlns/systems/power/firmware/uom/mc/2012_10/ SharedStoragePool"`
}

type SharedStoragePool struct {
 XMLName xml.Name `xml:"http://www.ibm.com/xmlns/systems/power/firmware/uom/mc/2012_10/ SharedStoragePool"`
 Name string `xml:"StoragePoolName"`
 UUID string `xml:"UniqueDeviceID"`
 Capacity float64
 FreeSpace float64
}

So i am expecting this kind of structure in the xml response :

<feed>
  <entry>
    <content>
       <sharedstoragepool:sharedstoragepool>
         <StoragePoolName>some name</StoragePoolName>
       </sharedstoragepool:sharedstoragepool>
    </content>
  </entry>
</feed>

I use xml.Name to ensure than the xml node has the correct name. If it’s not the case, xml.Unmarshalling will throw an error.

Another great thing, i can map the xml attribute to defined name very easily. For example, instead of using the defined name StoragePoolName i would like to use Name :

Name string `xml:"StoragePoolName"`

I only need to specify with xml: the real field in the xml node.

No need to specify the xml attribute if it keep the same naming convention, here a example for Capacity :

Capacity float64

remark: if you want to access the attribute, you need to follow go convention and have uppercase first character.

The only ‘trick’ was for the xml namespace where the syntax needed to include the url. So for sharedstoragepool:sharedstoragepool the syntax was :

XMLName xml.Name `xml:"http://www.ibm.com/xmlns/systems/power/firmware/uom/mc/2012_10/ SharedStoragePool"`

This part is extracted from the xml response itself. No way to guess it.

templates

HMC API requests are very structured so using text/template library is very efficient.

// template for login request
 logintemplate := `<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
  <LogonRequest xmlns="http://www.ibm.com/xmlns/systems/power/firmware/web/mc/2012_10/" schemaVersion="V1_1_0">
    <Metadata>
      <Atom/>
    </Metadata>
    <UserID kb="CUR" kxe="false">{{.User}}</UserID>
    <Password kb="CUR" kxe="false">{{.Password}}</Password>
  </LogonRequest>`

Here the template is included directly in the source code but it could be stored in another file. The templating system is similar to handlebars in javascript. {{.User}} will be replaced by the content of User variable.

examples

The examples in the git repository are somewhat basic but i hope it gives a good idea of how to start to play with the HMC Api in golang.

You can see a example of a python script on the HMC programmer’s community