From 402164cea83385cff0880d5391cf6be3168ce527 Mon Sep 17 00:00:00 2001 From: Nathan Coad Date: Wed, 27 Sep 2023 17:06:00 +1000 Subject: [PATCH] initial commit --- README.md | 0 go.mod | 21 +++++++++++++ go.sum | 36 ++++++++++++++++++++++ main.go | 89 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 146 insertions(+) create mode 100644 README.md create mode 100644 go.mod create mode 100644 go.sum create mode 100644 main.go diff --git a/README.md b/README.md new file mode 100644 index 0000000..e69de29 diff --git a/go.mod b/go.mod new file mode 100644 index 0000000..e12135f --- /dev/null +++ b/go.mod @@ -0,0 +1,21 @@ +module ucs-exporter/v2 + +go 1.21.0 + +require ( + github.com/dnaeon/go-ucs v0.0.0-20180427075322-a04ea35bf5de + github.com/prometheus/client_golang v1.16.0 +) + +require ( + github.com/beorn7/perks v1.0.1 // indirect + github.com/cespare/xxhash/v2 v2.2.0 // indirect + github.com/golang/protobuf v1.5.3 // indirect + github.com/matttproud/golang_protobuf_extensions v1.0.4 // indirect + github.com/prometheus/client_model v0.3.0 // indirect + github.com/prometheus/common v0.42.0 // indirect + github.com/prometheus/procfs v0.10.1 // indirect + golang.org/x/sys v0.8.0 // indirect + golang.org/x/time v0.3.0 // indirect + google.golang.org/protobuf v1.30.0 // indirect +) diff --git a/go.sum b/go.sum new file mode 100644 index 0000000..237f85a --- /dev/null +++ b/go.sum @@ -0,0 +1,36 @@ +github.com/beorn7/perks v1.0.1 h1:VlbKKnNfV8bJzeqoa4cOKqO6bYr3WgKZxO8Z16+hsOM= +github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw= +github.com/cespare/xxhash/v2 v2.2.0 h1:DC2CZ1Ep5Y4k3ZQ899DldepgrayRUGE6BBZ/cd9Cj44= +github.com/cespare/xxhash/v2 v2.2.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= +github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= +github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/dnaeon/go-ucs v0.0.0-20180427075322-a04ea35bf5de h1:TPQ2PEbeZy0m8Y/zO+IQx9pUDMqfanACLJqREaLroJU= +github.com/dnaeon/go-ucs v0.0.0-20180427075322-a04ea35bf5de/go.mod h1:CnATpmPv6+QWYn/4O/qrRmxhSvfsiTMB4mVBfsWwKs8= +github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= +github.com/golang/protobuf v1.3.5/go.mod h1:6O5/vntMXwX2lRkT1hjjk0nAC1IDOTvTlVgjlRvqsdk= +github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= +github.com/golang/protobuf v1.5.3 h1:KhyjKVUg7Usr/dYsdSqoFveMYd5ko72D+zANwlG1mmg= +github.com/golang/protobuf v1.5.3/go.mod h1:XVQd3VNwM+JqD3oG2Ue2ip4fOMUkwXdXDdiuN0vRsmY= +github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.5.9 h1:O2Tfq5qg4qc4AmwVlvv0oLiVAGB7enBSJ2x2DqQFi38= +github.com/google/go-cmp v0.5.9/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= +github.com/matttproud/golang_protobuf_extensions v1.0.4 h1:mmDVorXM7PCGKw94cs5zkfA9PSy5pEvNWRP0ET0TIVo= +github.com/matttproud/golang_protobuf_extensions v1.0.4/go.mod h1:BSXmuO+STAnVfrANrmjBb36TMTDstsz7MSK+HVaYKv4= +github.com/prometheus/client_golang v1.16.0 h1:yk/hx9hDbrGHovbci4BY+pRMfSuuat626eFsHb7tmT8= +github.com/prometheus/client_golang v1.16.0/go.mod h1:Zsulrv/L9oM40tJ7T815tM89lFEugiJ9HzIqaAx4LKc= +github.com/prometheus/client_model v0.3.0 h1:UBgGFHqYdG/TPFD1B1ogZywDqEkwp3fBMvqdiQ7Xew4= +github.com/prometheus/client_model v0.3.0/go.mod h1:LDGWKZIo7rky3hgvBe+caln+Dr3dPggB5dvjtD7w9+w= +github.com/prometheus/common v0.42.0 h1:EKsfXEYo4JpWMHH5cg+KOUWeuJSov1Id8zGR8eeI1YM= +github.com/prometheus/common v0.42.0/go.mod h1:xBwqVerjNdUDjgODMpudtOMwlOwf2SaTr1yjz4b7Zbc= +github.com/prometheus/procfs v0.10.1 h1:kYK1Va/YMlutzCGazswoHKo//tZVlFpKYh+PymziUAg= +github.com/prometheus/procfs v0.10.1/go.mod h1:nwNm2aOCAYw8uTR/9bWRREkZFxAUcWzPHWJq+XBB/FM= +golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sys v0.8.0 h1:EBmGv8NaZBZTWvrbjNoL6HVt+IVy3QDQpJs7VRIw3tU= +golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/time v0.3.0 h1:rg5rLMjNzMS1RkNLzCG38eapWhnYLFYXDXj2gOlr8j4= +golang.org/x/time v0.3.0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= +google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= +google.golang.org/protobuf v1.30.0 h1:kPPoIgf3TsEvrm0PFe15JQ+570QVxYzEvvHqChK+cng= +google.golang.org/protobuf v1.30.0/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I= diff --git a/main.go b/main.go new file mode 100644 index 0000000..6ca62e4 --- /dev/null +++ b/main.go @@ -0,0 +1,89 @@ +package main + +import ( + "context" + "crypto/tls" + "encoding/xml" + "flag" + "log" + "net/http" + + "github.com/dnaeon/go-ucs/api" + "github.com/dnaeon/go-ucs/mo" + "github.com/prometheus/client_golang/prometheus/promhttp" +) + +var sha1ver string // sha1 revision used to build the program +var buildTime string // when the executable was built + +func main() { + vURL := flag.String("url", "", "The URL of a UCS Manager, eg https://server.domain.example/nuova") + vUser := flag.String("user", "ucspe", "The username to use when connecting to UCS Manager") + vPass := flag.String("password", "ucspe", "The password to use when connecting to UCS Manager") + flag.Parse() + + // The following example shows how to retrieve all compute blades. + + // Skip SSL certificate verification of remote endpoint. + tr := &http.Transport{ + TLSClientConfig: &tls.Config{InsecureSkipVerify: true}, + } + httpClient := &http.Client{Transport: tr} + + // Create a new Cisco UCS API client + config := api.Config{ + Endpoint: *vURL, + Username: *vUser, + Password: *vPass, + HttpClient: httpClient, + } + + client, err := api.NewClient(config) + if err != nil { + log.Fatalf("Unable to create API client: %s", err) + } + + ctx := context.Background() + + log.Printf("Logging in to %s\n", config.Endpoint) + if _, err := client.AaaLogin(ctx); err != nil { + log.Fatalf("Unable to login: %s\n", err) + } + defer client.AaaLogout(ctx) + + log.Printf("Got authentication cookie: %s\n", client.Cookie) + + // The type into which we unmarshal the result data + type blades struct { + XMLName xml.Name + Blades []mo.ComputeBlade `xml:"computeBlade"` + } + + req := api.ConfigResolveClassRequest{ + Cookie: client.Cookie, + ClassId: "computeBlade", + InHierarchical: "false", + } + + var out blades + + log.Println("Retrieving managed objects with class `computeBlade`") + if err := client.ConfigResolveClass(ctx, req, &out); err != nil { + log.Fatalf("Unable to retrieve `computeBlade` managed object: %s", err) + } + + log.Printf("Retrieved %d compute blades\n", len(out.Blades)) + for _, blade := range out.Blades { + log.Printf("%s:\n", blade.Dn) + log.Printf("\tNumber of CPUs: %d\n", blade.NumOfCpus) + log.Printf("\tTotal Memory: %d\n", blade.TotalMemory) + log.Printf("\tModel: %s\n", blade.Model) + log.Printf("\tVendor: %s\n", blade.Vendor) + } + + // Start prometheus exporter + http.Handle("/metrics", promhttp.Handler()) + + // TODO - run this in a go routine to avoid blocking, as per cbs code + log.Fatal(http.ListenAndServe(":9101", nil)) +}