Merge pull request #45392 from nicksardo/gce-get-stats

Automatic merge from submit-queue (batch tested with PRs 43006, 45305, 45390, 45412, 45392)

[GCE] Collect latency metric on get/list calls

**What this PR does / why we need it**:
Collects latency & count measurements on GET and LIST operations to GCE cloud.

**Release note**:
```release-note
NONE
```
This commit is contained in:
Kubernetes Submit Queue 2017-05-05 16:39:11 -07:00 committed by GitHub
commit c6ce00968d
13 changed files with 107 additions and 70 deletions

View File

@ -32,7 +32,9 @@ func newBackendServiceMetricContext(request string) *metricContext {
// GetBackendService retrieves a backend by name. // GetBackendService retrieves a backend by name.
func (gce *GCECloud) GetBackendService(name string) (*compute.BackendService, error) { func (gce *GCECloud) GetBackendService(name string) (*compute.BackendService, error) {
return gce.service.BackendServices.Get(gce.projectID, name).Do() mc := newBackendServiceMetricContext("get")
v, err := gce.service.BackendServices.Get(gce.projectID, name).Do()
return v, mc.Observe(err)
} }
// UpdateBackendService applies the given BackendService as an update to an existing service. // UpdateBackendService applies the given BackendService as an update to an existing service.

View File

@ -32,7 +32,9 @@ func newCertMetricContext(request string) *metricContext {
// GetSslCertificate returns the SslCertificate by name. // GetSslCertificate returns the SslCertificate by name.
func (gce *GCECloud) GetSslCertificate(name string) (*compute.SslCertificate, error) { func (gce *GCECloud) GetSslCertificate(name string) (*compute.SslCertificate, error) {
return gce.service.SslCertificates.Get(gce.projectID, name).Do() mc := newCertMetricContext("get")
v, err := gce.service.SslCertificates.Get(gce.projectID, name).Do()
return v, mc.Observe(err)
} }
// CreateSslCertificate creates and returns a SslCertificate. // CreateSslCertificate creates and returns a SslCertificate.
@ -69,6 +71,8 @@ func (gce *GCECloud) DeleteSslCertificate(name string) error {
// ListSslCertificates lists all SslCertificates in the project. // ListSslCertificates lists all SslCertificates in the project.
func (gce *GCECloud) ListSslCertificates() (*compute.SslCertificateList, error) { func (gce *GCECloud) ListSslCertificates() (*compute.SslCertificateList, error) {
mc := newCertMetricContext("list")
// TODO: use PageToken to list all not just the first 500 // TODO: use PageToken to list all not just the first 500
return gce.service.SslCertificates.List(gce.projectID).Do() v, err := gce.service.SslCertificates.List(gce.projectID).Do()
return v, mc.Observe(err)
} }

View File

@ -16,6 +16,15 @@ limitations under the License.
package gce package gce
import "time"
func newClustersMetricContext(request, zone string) *metricContext {
return &metricContext{
start: time.Now(),
attributes: []string{"clusters_" + request, unusedMetricLabel, zone},
}
}
func (gce *GCECloud) ListClusters() ([]string, error) { func (gce *GCECloud) ListClusters() ([]string, error) {
allClusters := []string{} allClusters := []string{}
@ -36,14 +45,16 @@ func (gce *GCECloud) Master(clusterName string) (string, error) {
} }
func (gce *GCECloud) listClustersInZone(zone string) ([]string, error) { func (gce *GCECloud) listClustersInZone(zone string) ([]string, error) {
mc := newClustersMetricContext("list_zone", zone)
// TODO: use PageToken to list all not just the first 500 // TODO: use PageToken to list all not just the first 500
list, err := gce.containerService.Projects.Zones.Clusters.List(gce.projectID, zone).Do() list, err := gce.containerService.Projects.Zones.Clusters.List(gce.projectID, zone).Do()
if err != nil { if err != nil {
return nil, err return nil, mc.Observe(err)
} }
result := []string{} result := []string{}
for _, cluster := range list.Clusters { for _, cluster := range list.Clusters {
result = append(result, cluster.Name) result = append(result, cluster.Name)
} }
return result, nil return result, mc.Observe(nil)
} }

View File

@ -319,6 +319,7 @@ func (gce *GCECloud) GetAutoLabelsForPD(name string, zone string) (map[string]st
// Returns a GCEDisk for the disk, if it is found in the specified zone. // Returns a GCEDisk for the disk, if it is found in the specified zone.
// If not found, returns (nil, nil) // If not found, returns (nil, nil)
func (gce *GCECloud) findDiskByName(diskName string, zone string) (*GCEDisk, error) { func (gce *GCECloud) findDiskByName(diskName string, zone string) (*GCEDisk, error) {
mc := newDiskMetricContext("get", zone)
disk, err := gce.service.Disks.Get(gce.projectID, zone, diskName).Do() disk, err := gce.service.Disks.Get(gce.projectID, zone, diskName).Do()
if err == nil { if err == nil {
d := &GCEDisk{ d := &GCEDisk{
@ -327,12 +328,12 @@ func (gce *GCECloud) findDiskByName(diskName string, zone string) (*GCEDisk, err
Kind: disk.Kind, Kind: disk.Kind,
Type: disk.Type, Type: disk.Type,
} }
return d, nil return d, mc.Observe(nil)
} }
if !isHTTPErrorCode(err, http.StatusNotFound) { if !isHTTPErrorCode(err, http.StatusNotFound) {
return nil, err return nil, mc.Observe(err)
} }
return nil, nil return nil, mc.Observe(nil)
} }
// Like findDiskByName, but returns an error if the disk is not found // Like findDiskByName, but returns an error if the disk is not found

View File

@ -34,7 +34,9 @@ func newFirewallMetricContext(request string, region string) *metricContext {
// GetFirewall returns the Firewall by name. // GetFirewall returns the Firewall by name.
func (gce *GCECloud) GetFirewall(name string) (*compute.Firewall, error) { func (gce *GCECloud) GetFirewall(name string) (*compute.Firewall, error) {
return gce.service.Firewalls.Get(gce.projectID, name).Do() mc := newFirewallMetricContext("get", "")
v, err := gce.service.Firewalls.Get(gce.projectID, name).Do()
return v, mc.Observe(err)
} }
// CreateFirewall creates the given firewall rule. // CreateFirewall creates the given firewall rule.
@ -45,7 +47,6 @@ func (gce *GCECloud) CreateFirewall(name, desc string, sourceRanges netsets.IPNe
} }
mc := newFirewallMetricContext("create", region) mc := newFirewallMetricContext("create", region)
// TODO: This completely breaks modularity in the cloudprovider but // TODO: This completely breaks modularity in the cloudprovider but
// the methods shared with the TCPLoadBalancer take v1.ServicePorts. // the methods shared with the TCPLoadBalancer take v1.ServicePorts.
svcPorts := []v1.ServicePort{} svcPorts := []v1.ServicePort{}
@ -90,7 +91,6 @@ func (gce *GCECloud) UpdateFirewall(name, desc string, sourceRanges netsets.IPNe
} }
mc := newFirewallMetricContext("update", region) mc := newFirewallMetricContext("update", region)
// TODO: This completely breaks modularity in the cloudprovider but // TODO: This completely breaks modularity in the cloudprovider but
// the methods shared with the TCPLoadBalancer take v1.ServicePorts. // the methods shared with the TCPLoadBalancer take v1.ServicePorts.
svcPorts := []v1.ServicePort{} svcPorts := []v1.ServicePort{}

View File

@ -35,7 +35,6 @@ func newForwardingRuleMetricContext(request, region string) *metricContext {
// targetProxyLink is the SelfLink of a TargetHttp(s)Proxy. // targetProxyLink is the SelfLink of a TargetHttp(s)Proxy.
func (gce *GCECloud) CreateGlobalForwardingRule(targetProxyLink, ip, name, portRange string) (*compute.ForwardingRule, error) { func (gce *GCECloud) CreateGlobalForwardingRule(targetProxyLink, ip, name, portRange string) (*compute.ForwardingRule, error) {
mc := newForwardingRuleMetricContext("create", "") mc := newForwardingRuleMetricContext("create", "")
rule := &compute.ForwardingRule{ rule := &compute.ForwardingRule{
Name: name, Name: name,
IPAddress: ip, IPAddress: ip,
@ -59,7 +58,6 @@ func (gce *GCECloud) CreateGlobalForwardingRule(targetProxyLink, ip, name, portR
// targetProxyLink is the SelfLink of a TargetHttp(s)Proxy. // targetProxyLink is the SelfLink of a TargetHttp(s)Proxy.
func (gce *GCECloud) SetProxyForGlobalForwardingRule(fw *compute.ForwardingRule, targetProxyLink string) error { func (gce *GCECloud) SetProxyForGlobalForwardingRule(fw *compute.ForwardingRule, targetProxyLink string) error {
mc := newForwardingRuleMetricContext("set_proxy", "") mc := newForwardingRuleMetricContext("set_proxy", "")
op, err := gce.service.GlobalForwardingRules.SetTarget( op, err := gce.service.GlobalForwardingRules.SetTarget(
gce.projectID, fw.Name, &compute.TargetReference{Target: targetProxyLink}).Do() gce.projectID, fw.Name, &compute.TargetReference{Target: targetProxyLink}).Do()
if err != nil { if err != nil {
@ -73,7 +71,6 @@ func (gce *GCECloud) SetProxyForGlobalForwardingRule(fw *compute.ForwardingRule,
// DeleteGlobalForwardingRule deletes the GlobalForwardingRule by name. // DeleteGlobalForwardingRule deletes the GlobalForwardingRule by name.
func (gce *GCECloud) DeleteGlobalForwardingRule(name string) error { func (gce *GCECloud) DeleteGlobalForwardingRule(name string) error {
mc := newForwardingRuleMetricContext("delete", "") mc := newForwardingRuleMetricContext("delete", "")
op, err := gce.service.GlobalForwardingRules.Delete(gce.projectID, name).Do() op, err := gce.service.GlobalForwardingRules.Delete(gce.projectID, name).Do()
if err != nil { if err != nil {
if isHTTPErrorCode(err, http.StatusNotFound) { if isHTTPErrorCode(err, http.StatusNotFound) {
@ -90,11 +87,15 @@ func (gce *GCECloud) DeleteGlobalForwardingRule(name string) error {
// GetGlobalForwardingRule returns the GlobalForwardingRule by name. // GetGlobalForwardingRule returns the GlobalForwardingRule by name.
func (gce *GCECloud) GetGlobalForwardingRule(name string) (*compute.ForwardingRule, error) { func (gce *GCECloud) GetGlobalForwardingRule(name string) (*compute.ForwardingRule, error) {
return gce.service.GlobalForwardingRules.Get(gce.projectID, name).Do() mc := newForwardingRuleMetricContext("get", "")
v, err := gce.service.GlobalForwardingRules.Get(gce.projectID, name).Do()
return v, mc.Observe(err)
} }
// ListGlobalForwardingRules lists all GlobalForwardingRules in the project. // ListGlobalForwardingRules lists all GlobalForwardingRules in the project.
func (gce *GCECloud) ListGlobalForwardingRules() (*compute.ForwardingRuleList, error) { func (gce *GCECloud) ListGlobalForwardingRules() (*compute.ForwardingRuleList, error) {
mc := newForwardingRuleMetricContext("list", "")
// TODO: use PageToken to list all not just the first 500 // TODO: use PageToken to list all not just the first 500
return gce.service.GlobalForwardingRules.List(gce.projectID).Do() v, err := gce.service.GlobalForwardingRules.List(gce.projectID).Do()
return v, mc.Observe(err)
} }

View File

@ -31,17 +31,17 @@ func newHealthcheckMetricContext(request string) *metricContext {
// GetHttpHealthCheck returns the given HttpHealthCheck by name. // GetHttpHealthCheck returns the given HttpHealthCheck by name.
func (gce *GCECloud) GetHttpHealthCheck(name string) (*compute.HttpHealthCheck, error) { func (gce *GCECloud) GetHttpHealthCheck(name string) (*compute.HttpHealthCheck, error) {
return gce.service.HttpHealthChecks.Get(gce.projectID, name).Do() mc := newHealthcheckMetricContext("get_legacy")
v, err := gce.service.HttpHealthChecks.Get(gce.projectID, name).Do()
return v, mc.Observe(err)
} }
// UpdateHttpHealthCheck applies the given HttpHealthCheck as an update. // UpdateHttpHealthCheck applies the given HttpHealthCheck as an update.
func (gce *GCECloud) UpdateHttpHealthCheck(hc *compute.HttpHealthCheck) error { func (gce *GCECloud) UpdateHttpHealthCheck(hc *compute.HttpHealthCheck) error {
mc := newHealthcheckMetricContext("update_legacy") mc := newHealthcheckMetricContext("update_legacy")
op, err := gce.service.HttpHealthChecks.Update(gce.projectID, hc.Name, hc).Do() op, err := gce.service.HttpHealthChecks.Update(gce.projectID, hc.Name, hc).Do()
if err != nil { if err != nil {
mc.Observe(err) return mc.Observe(err)
return err
} }
return gce.waitForGlobalOp(op, mc) return gce.waitForGlobalOp(op, mc)
@ -50,11 +50,9 @@ func (gce *GCECloud) UpdateHttpHealthCheck(hc *compute.HttpHealthCheck) error {
// DeleteHttpHealthCheck deletes the given HttpHealthCheck by name. // DeleteHttpHealthCheck deletes the given HttpHealthCheck by name.
func (gce *GCECloud) DeleteHttpHealthCheck(name string) error { func (gce *GCECloud) DeleteHttpHealthCheck(name string) error {
mc := newHealthcheckMetricContext("delete_legacy") mc := newHealthcheckMetricContext("delete_legacy")
op, err := gce.service.HttpHealthChecks.Delete(gce.projectID, name).Do() op, err := gce.service.HttpHealthChecks.Delete(gce.projectID, name).Do()
if err != nil { if err != nil {
mc.Observe(err) return mc.Observe(err)
return err
} }
return gce.waitForGlobalOp(op, mc) return gce.waitForGlobalOp(op, mc)
@ -63,11 +61,9 @@ func (gce *GCECloud) DeleteHttpHealthCheck(name string) error {
// CreateHttpHealthCheck creates the given HttpHealthCheck. // CreateHttpHealthCheck creates the given HttpHealthCheck.
func (gce *GCECloud) CreateHttpHealthCheck(hc *compute.HttpHealthCheck) error { func (gce *GCECloud) CreateHttpHealthCheck(hc *compute.HttpHealthCheck) error {
mc := newHealthcheckMetricContext("create_legacy") mc := newHealthcheckMetricContext("create_legacy")
op, err := gce.service.HttpHealthChecks.Insert(gce.projectID, hc).Do() op, err := gce.service.HttpHealthChecks.Insert(gce.projectID, hc).Do()
if err != nil { if err != nil {
mc.Observe(err) return mc.Observe(err)
return err
} }
return gce.waitForGlobalOp(op, mc) return gce.waitForGlobalOp(op, mc)
@ -75,15 +71,20 @@ func (gce *GCECloud) CreateHttpHealthCheck(hc *compute.HttpHealthCheck) error {
// ListHttpHealthChecks lists all HttpHealthChecks in the project. // ListHttpHealthChecks lists all HttpHealthChecks in the project.
func (gce *GCECloud) ListHttpHealthChecks() (*compute.HttpHealthCheckList, error) { func (gce *GCECloud) ListHttpHealthChecks() (*compute.HttpHealthCheckList, error) {
mc := newHealthcheckMetricContext("list_legacy")
// TODO: use PageToken to list all not just the first 500 // TODO: use PageToken to list all not just the first 500
return gce.service.HttpHealthChecks.List(gce.projectID).Do() v, err := gce.service.HttpHealthChecks.List(gce.projectID).Do()
return v, mc.Observe(err)
} }
// Legacy HTTPS Health Checks // Legacy HTTPS Health Checks
// GetHttpsHealthCheck returns the given HttpsHealthCheck by name. // GetHttpsHealthCheck returns the given HttpsHealthCheck by name.
func (gce *GCECloud) GetHttpsHealthCheck(name string) (*compute.HttpsHealthCheck, error) { func (gce *GCECloud) GetHttpsHealthCheck(name string) (*compute.HttpsHealthCheck, error) {
return gce.service.HttpsHealthChecks.Get(gce.projectID, name).Do() mc := newHealthcheckMetricContext("get_legacy")
v, err := gce.service.HttpsHealthChecks.Get(gce.projectID, name).Do()
mc.Observe(err)
return v, err
} }
// UpdateHttpsHealthCheck applies the given HttpsHealthCheck as an update. // UpdateHttpsHealthCheck applies the given HttpsHealthCheck as an update.
@ -103,8 +104,7 @@ func (gce *GCECloud) DeleteHttpsHealthCheck(name string) error {
mc := newHealthcheckMetricContext("delete_legacy") mc := newHealthcheckMetricContext("delete_legacy")
op, err := gce.service.HttpsHealthChecks.Delete(gce.projectID, name).Do() op, err := gce.service.HttpsHealthChecks.Delete(gce.projectID, name).Do()
if err != nil { if err != nil {
mc.Observe(err) return mc.Observe(err)
return err
} }
return gce.waitForGlobalOp(op, mc) return gce.waitForGlobalOp(op, mc)
@ -115,8 +115,7 @@ func (gce *GCECloud) CreateHttpsHealthCheck(hc *compute.HttpsHealthCheck) error
mc := newHealthcheckMetricContext("create_legacy") mc := newHealthcheckMetricContext("create_legacy")
op, err := gce.service.HttpsHealthChecks.Insert(gce.projectID, hc).Do() op, err := gce.service.HttpsHealthChecks.Insert(gce.projectID, hc).Do()
if err != nil { if err != nil {
mc.Observe(err) return mc.Observe(err)
return err
} }
return gce.waitForGlobalOp(op, mc) return gce.waitForGlobalOp(op, mc)
@ -124,26 +123,27 @@ func (gce *GCECloud) CreateHttpsHealthCheck(hc *compute.HttpsHealthCheck) error
// ListHttpsHealthChecks lists all HttpsHealthChecks in the project. // ListHttpsHealthChecks lists all HttpsHealthChecks in the project.
func (gce *GCECloud) ListHttpsHealthChecks() (*compute.HttpsHealthCheckList, error) { func (gce *GCECloud) ListHttpsHealthChecks() (*compute.HttpsHealthCheckList, error) {
mc := newHealthcheckMetricContext("list_legacy")
// TODO: use PageToken to list all not just the first 500 // TODO: use PageToken to list all not just the first 500
return gce.service.HttpsHealthChecks.List(gce.projectID).Do() v, err := gce.service.HttpsHealthChecks.List(gce.projectID).Do()
return v, mc.Observe(err)
} }
// Generic HealthCheck // Generic HealthCheck
// GetHealthCheck returns the given HealthCheck by name. // GetHealthCheck returns the given HealthCheck by name.
func (gce *GCECloud) GetHealthCheck(name string) (*compute.HealthCheck, error) { func (gce *GCECloud) GetHealthCheck(name string) (*compute.HealthCheck, error) {
return gce.service.HealthChecks.Get(gce.projectID, name).Do() mc := newHealthcheckMetricContext("get")
v, err := gce.service.HealthChecks.Get(gce.projectID, name).Do()
return v, mc.Observe(err)
} }
// UpdateHealthCheck applies the given HealthCheck as an update. // UpdateHealthCheck applies the given HealthCheck as an update.
func (gce *GCECloud) UpdateHealthCheck(hc *compute.HealthCheck) error { func (gce *GCECloud) UpdateHealthCheck(hc *compute.HealthCheck) error {
mc := newHealthcheckMetricContext("update") mc := newHealthcheckMetricContext("update")
op, err := gce.service.HealthChecks.Update(gce.projectID, hc.Name, hc).Do() op, err := gce.service.HealthChecks.Update(gce.projectID, hc.Name, hc).Do()
if err != nil { if err != nil {
mc.Observe(err) return mc.Observe(err)
return err
} }
return gce.waitForGlobalOp(op, mc) return gce.waitForGlobalOp(op, mc)
@ -152,12 +152,9 @@ func (gce *GCECloud) UpdateHealthCheck(hc *compute.HealthCheck) error {
// DeleteHealthCheck deletes the given HealthCheck by name. // DeleteHealthCheck deletes the given HealthCheck by name.
func (gce *GCECloud) DeleteHealthCheck(name string) error { func (gce *GCECloud) DeleteHealthCheck(name string) error {
mc := newHealthcheckMetricContext("delete") mc := newHealthcheckMetricContext("delete")
op, err := gce.service.HealthChecks.Delete(gce.projectID, name).Do() op, err := gce.service.HealthChecks.Delete(gce.projectID, name).Do()
if err != nil { if err != nil {
mc.Observe(err) return mc.Observe(err)
return err
} }
return gce.waitForGlobalOp(op, mc) return gce.waitForGlobalOp(op, mc)
@ -166,11 +163,9 @@ func (gce *GCECloud) DeleteHealthCheck(name string) error {
// CreateHealthCheck creates the given HealthCheck. // CreateHealthCheck creates the given HealthCheck.
func (gce *GCECloud) CreateHealthCheck(hc *compute.HealthCheck) error { func (gce *GCECloud) CreateHealthCheck(hc *compute.HealthCheck) error {
mc := newHealthcheckMetricContext("create") mc := newHealthcheckMetricContext("create")
op, err := gce.service.HealthChecks.Insert(gce.projectID, hc).Do() op, err := gce.service.HealthChecks.Insert(gce.projectID, hc).Do()
if err != nil { if err != nil {
mc.Observe(err) return mc.Observe(err)
return err
} }
return gce.waitForGlobalOp(op, mc) return gce.waitForGlobalOp(op, mc)
@ -178,6 +173,8 @@ func (gce *GCECloud) CreateHealthCheck(hc *compute.HealthCheck) error {
// ListHealthChecks lists all HealthCheck in the project. // ListHealthChecks lists all HealthCheck in the project.
func (gce *GCECloud) ListHealthChecks() (*compute.HealthCheckList, error) { func (gce *GCECloud) ListHealthChecks() (*compute.HealthCheckList, error) {
mc := newHealthcheckMetricContext("list")
// TODO: use PageToken to list all not just the first 500 // TODO: use PageToken to list all not just the first 500
return gce.service.HealthChecks.List(gce.projectID).Do() v, err := gce.service.HealthChecks.List(gce.projectID).Do()
return v, mc.Observe(err)
} }

View File

@ -40,7 +40,6 @@ func (gce *GCECloud) CreateInstanceGroup(name string, zone string) (*compute.Ins
op, err := gce.service.InstanceGroups.Insert( op, err := gce.service.InstanceGroups.Insert(
gce.projectID, zone, &compute.InstanceGroup{Name: name}).Do() gce.projectID, zone, &compute.InstanceGroup{Name: name}).Do()
if err != nil { if err != nil {
mc.Observe(err) mc.Observe(err)
return nil, err return nil, err
@ -59,7 +58,6 @@ func (gce *GCECloud) DeleteInstanceGroup(name string, zone string) error {
op, err := gce.service.InstanceGroups.Delete( op, err := gce.service.InstanceGroups.Delete(
gce.projectID, zone, name).Do() gce.projectID, zone, name).Do()
if err != nil { if err != nil {
mc.Observe(err) mc.Observe(err)
return err return err
@ -71,24 +69,27 @@ func (gce *GCECloud) DeleteInstanceGroup(name string, zone string) error {
// ListInstanceGroups lists all InstanceGroups in the project and // ListInstanceGroups lists all InstanceGroups in the project and
// zone. // zone.
func (gce *GCECloud) ListInstanceGroups(zone string) (*compute.InstanceGroupList, error) { func (gce *GCECloud) ListInstanceGroups(zone string) (*compute.InstanceGroupList, error) {
mc := newInstanceGroupMetricContext("list", zone)
// TODO: use PageToken to list all not just the first 500 // TODO: use PageToken to list all not just the first 500
return gce.service.InstanceGroups.List(gce.projectID, zone).Do() v, err := gce.service.InstanceGroups.List(gce.projectID, zone).Do()
return v, mc.Observe(err)
} }
// ListInstancesInInstanceGroup lists all the instances in a given // ListInstancesInInstanceGroup lists all the instances in a given
// instance group and state. // instance group and state.
func (gce *GCECloud) ListInstancesInInstanceGroup(name string, zone string, state string) (*compute.InstanceGroupsListInstances, error) { func (gce *GCECloud) ListInstancesInInstanceGroup(name string, zone string, state string) (*compute.InstanceGroupsListInstances, error) {
mc := newInstanceGroupMetricContext("list_instances", zone)
// TODO: use PageToken to list all not just the first 500 // TODO: use PageToken to list all not just the first 500
return gce.service.InstanceGroups.ListInstances( v, err := gce.service.InstanceGroups.ListInstances(
gce.projectID, zone, name, gce.projectID, zone, name,
&compute.InstanceGroupsListInstancesRequest{InstanceState: state}).Do() &compute.InstanceGroupsListInstancesRequest{InstanceState: state}).Do()
return v, mc.Observe(err)
} }
// AddInstancesToInstanceGroup adds the given instances to the given // AddInstancesToInstanceGroup adds the given instances to the given
// instance group. // instance group.
func (gce *GCECloud) AddInstancesToInstanceGroup(name string, zone string, instanceNames []string) error { func (gce *GCECloud) AddInstancesToInstanceGroup(name string, zone string, instanceNames []string) error {
mc := newInstanceGroupMetricContext("add_instances", zone) mc := newInstanceGroupMetricContext("add_instances", zone)
if len(instanceNames) == 0 { if len(instanceNames) == 0 {
return nil return nil
} }
@ -115,10 +116,10 @@ func (gce *GCECloud) AddInstancesToInstanceGroup(name string, zone string, insta
// the instance group. // the instance group.
func (gce *GCECloud) RemoveInstancesFromInstanceGroup(name string, zone string, instanceNames []string) error { func (gce *GCECloud) RemoveInstancesFromInstanceGroup(name string, zone string, instanceNames []string) error {
mc := newInstanceGroupMetricContext("remove_instances", zone) mc := newInstanceGroupMetricContext("remove_instances", zone)
if len(instanceNames) == 0 { if len(instanceNames) == 0 {
return nil return nil
} }
instances := []*compute.InstanceReference{} instances := []*compute.InstanceReference{}
for _, ins := range instanceNames { for _, ins := range instanceNames {
instanceLink := makeHostURL(gce.projectID, zone, ins) instanceLink := makeHostURL(gce.projectID, zone, ins)
@ -146,7 +147,6 @@ func (gce *GCECloud) RemoveInstancesFromInstanceGroup(name string, zone string,
// AddPortToInstanceGroup adds a port to the given instance group. // AddPortToInstanceGroup adds a port to the given instance group.
func (gce *GCECloud) AddPortToInstanceGroup(ig *compute.InstanceGroup, port int64) (*compute.NamedPort, error) { func (gce *GCECloud) AddPortToInstanceGroup(ig *compute.InstanceGroup, port int64) (*compute.NamedPort, error) {
mc := newInstanceGroupMetricContext("add_port", ig.Zone) mc := newInstanceGroupMetricContext("add_port", ig.Zone)
for _, np := range ig.NamedPorts { for _, np := range ig.NamedPorts {
if np.Port == port { if np.Port == port {
glog.V(3).Infof("Instance group %v already has named port %+v", ig.Name, np) glog.V(3).Infof("Instance group %v already has named port %+v", ig.Name, np)
@ -183,5 +183,7 @@ func (gce *GCECloud) AddPortToInstanceGroup(ig *compute.InstanceGroup, port int6
// GetInstanceGroup returns an instance group by name. // GetInstanceGroup returns an instance group by name.
func (gce *GCECloud) GetInstanceGroup(name string, zone string) (*compute.InstanceGroup, error) { func (gce *GCECloud) GetInstanceGroup(name string, zone string) (*compute.InstanceGroup, error) {
return gce.service.InstanceGroups.Get(gce.projectID, zone, name).Do() mc := newInstanceGroupMetricContext("get", zone)
v, err := gce.service.InstanceGroups.Get(gce.projectID, zone, name).Do()
return v, mc.Observe(err)
} }

View File

@ -36,10 +36,10 @@ import (
"k8s.io/kubernetes/pkg/cloudprovider" "k8s.io/kubernetes/pkg/cloudprovider"
) )
func newInstancesMetricContext(request string) *metricContext { func newInstancesMetricContext(request, zone string) *metricContext {
return &metricContext{ return &metricContext{
start: time.Now(), start: time.Now(),
attributes: []string{"instances_" + request, unusedMetricLabel, unusedMetricLabel}, attributes: []string{"instances_" + request, unusedMetricLabel, zone},
} }
} }
@ -164,7 +164,7 @@ func (gce *GCECloud) AddSSHKeyToAllInstances(user string, keyData []byte) error
}) })
} }
mc := newInstancesMetricContext("add_ssh_key") mc := newInstancesMetricContext("add_ssh_key", "")
op, err := gce.service.Projects.SetCommonInstanceMetadata( op, err := gce.service.Projects.SetCommonInstanceMetadata(
gce.projectID, project.CommonInstanceMetadata).Do() gce.projectID, project.CommonInstanceMetadata).Do()
@ -197,6 +197,7 @@ func (gce *GCECloud) GetAllZones() (sets.String, error) {
// TODO: Parallelize, although O(zones) so not too bad (N <= 3 typically) // TODO: Parallelize, although O(zones) so not too bad (N <= 3 typically)
for _, zone := range gce.managedZones { for _, zone := range gce.managedZones {
mc := newInstancesMetricContext("list", zone)
// We only retrieve one page in each zone - we only care about existence // We only retrieve one page in each zone - we only care about existence
listCall := gce.service.Instances.List(gce.projectID, zone) listCall := gce.service.Instances.List(gce.projectID, zone)
@ -213,11 +214,12 @@ func (gce *GCECloud) GetAllZones() (sets.String, error) {
// Just a minimal set of fields - we only care about existence // Just a minimal set of fields - we only care about existence
listCall = listCall.Fields("items(name)") listCall = listCall.Fields("items(name)")
res, err := listCall.Do() res, err := listCall.Do()
if err != nil { if err != nil {
return nil, err return nil, mc.Observe(err)
} }
mc.Observe(nil)
if len(res.Items) != 0 { if len(res.Items) != 0 {
zones.Insert(zone) zones.Insert(zone)
} }
@ -338,7 +340,9 @@ func (gce *GCECloud) getInstanceByName(name string) (*gceInstance, error) {
// Avoid changing behaviour when not managing multiple zones // Avoid changing behaviour when not managing multiple zones
for _, zone := range gce.managedZones { for _, zone := range gce.managedZones {
name = canonicalizeInstanceName(name) name = canonicalizeInstanceName(name)
mc := newInstancesMetricContext("get", zone)
res, err := gce.service.Instances.Get(gce.projectID, zone, name).Do() res, err := gce.service.Instances.Get(gce.projectID, zone, name).Do()
mc.Observe(err)
if err != nil { if err != nil {
glog.Errorf("getInstanceByName: failed to get instance %s; err: %v", name, err) glog.Errorf("getInstanceByName: failed to get instance %s; err: %v", name, err)

View File

@ -42,6 +42,7 @@ func (gce *GCECloud) ListRoutes(clusterName string) ([]*cloudprovider.Route, err
pageToken := "" pageToken := ""
page := 0 page := 0
for ; page == 0 || (pageToken != "" && page < maxPages); page++ { for ; page == 0 || (pageToken != "" && page < maxPages); page++ {
mc := newRoutesMetricContext("list_page")
listCall := gce.service.Routes.List(gce.projectID) listCall := gce.service.Routes.List(gce.projectID)
prefix := truncateClusterName(clusterName) prefix := truncateClusterName(clusterName)
@ -50,6 +51,7 @@ func (gce *GCECloud) ListRoutes(clusterName string) ([]*cloudprovider.Route, err
listCall = listCall.PageToken(pageToken) listCall = listCall.PageToken(pageToken)
} }
res, err := listCall.Do() res, err := listCall.Do()
mc.Observe(err)
if err != nil { if err != nil {
glog.Errorf("Error getting routes from GCE: %v", err) glog.Errorf("Error getting routes from GCE: %v", err)
return nil, err return nil, err
@ -110,7 +112,7 @@ func (gce *GCECloud) CreateRoute(clusterName string, nameHint string, route *clo
} }
func (gce *GCECloud) DeleteRoute(clusterName string, route *cloudprovider.Route) error { func (gce *GCECloud) DeleteRoute(clusterName string, route *cloudprovider.Route) error {
mc := newRoutesMetricContext("create") mc := newRoutesMetricContext("delete")
deleteOp, err := gce.service.Routes.Delete(gce.projectID, route.Name).Do() deleteOp, err := gce.service.Routes.Delete(gce.projectID, route.Name).Do()
if err != nil { if err != nil {
return mc.Observe(err) return mc.Observe(err)

View File

@ -59,6 +59,8 @@ func (gce *GCECloud) DeleteGlobalStaticIP(name string) error {
} }
// GetGlobalStaticIP returns the global static IP by name. // GetGlobalStaticIP returns the global static IP by name.
func (gce *GCECloud) GetGlobalStaticIP(name string) (address *compute.Address, err error) { func (gce *GCECloud) GetGlobalStaticIP(name string) (*compute.Address, error) {
return gce.service.GlobalAddresses.Get(gce.projectID, name).Do() mc := newStaticIPMetricContext("get")
v, err := gce.service.GlobalAddresses.Get(gce.projectID, name).Do()
return v, mc.Observe(err)
} }

View File

@ -32,7 +32,9 @@ func newTargetProxyMetricContext(request string) *metricContext {
// GetTargetHttpProxy returns the UrlMap by name. // GetTargetHttpProxy returns the UrlMap by name.
func (gce *GCECloud) GetTargetHttpProxy(name string) (*compute.TargetHttpProxy, error) { func (gce *GCECloud) GetTargetHttpProxy(name string) (*compute.TargetHttpProxy, error) {
return gce.service.TargetHttpProxies.Get(gce.projectID, name).Do() mc := newTargetProxyMetricContext("get")
v, err := gce.service.TargetHttpProxies.Get(gce.projectID, name).Do()
return v, mc.Observe(err)
} }
// CreateTargetHttpProxy creates and returns a TargetHttpProxy with the given UrlMap. // CreateTargetHttpProxy creates and returns a TargetHttpProxy with the given UrlMap.
@ -79,20 +81,24 @@ func (gce *GCECloud) DeleteTargetHttpProxy(name string) error {
// ListTargetHttpProxies lists all TargetHttpProxies in the project. // ListTargetHttpProxies lists all TargetHttpProxies in the project.
func (gce *GCECloud) ListTargetHttpProxies() (*compute.TargetHttpProxyList, error) { func (gce *GCECloud) ListTargetHttpProxies() (*compute.TargetHttpProxyList, error) {
mc := newTargetProxyMetricContext("list")
// TODO: use PageToken to list all not just the first 500 // TODO: use PageToken to list all not just the first 500
return gce.service.TargetHttpProxies.List(gce.projectID).Do() v, err := gce.service.TargetHttpProxies.List(gce.projectID).Do()
return v, mc.Observe(err)
} }
// TargetHttpsProxy management // TargetHttpsProxy management
// GetTargetHttpsProxy returns the UrlMap by name. // GetTargetHttpsProxy returns the UrlMap by name.
func (gce *GCECloud) GetTargetHttpsProxy(name string) (*compute.TargetHttpsProxy, error) { func (gce *GCECloud) GetTargetHttpsProxy(name string) (*compute.TargetHttpsProxy, error) {
return gce.service.TargetHttpsProxies.Get(gce.projectID, name).Do() mc := newTargetProxyMetricContext("get")
v, err := gce.service.TargetHttpsProxies.Get(gce.projectID, name).Do()
return v, mc.Observe(err)
} }
// CreateTargetHttpsProxy creates and returns a TargetHttpsProxy with the given UrlMap and SslCertificate. // CreateTargetHttpsProxy creates and returns a TargetHttpsProxy with the given UrlMap and SslCertificate.
func (gce *GCECloud) CreateTargetHttpsProxy(urlMap *compute.UrlMap, sslCert *compute.SslCertificate, name string) (*compute.TargetHttpsProxy, error) { func (gce *GCECloud) CreateTargetHttpsProxy(urlMap *compute.UrlMap, sslCert *compute.SslCertificate, name string) (*compute.TargetHttpsProxy, error) {
mc := newTargetProxyMetricContext("delete") mc := newTargetProxyMetricContext("create")
proxy := &compute.TargetHttpsProxy{ proxy := &compute.TargetHttpsProxy{
Name: name, Name: name,
UrlMap: urlMap.SelfLink, UrlMap: urlMap.SelfLink,
@ -133,7 +139,6 @@ func (gce *GCECloud) SetSslCertificateForTargetHttpsProxy(proxy *compute.TargetH
// DeleteTargetHttpsProxy deletes the TargetHttpsProxy by name. // DeleteTargetHttpsProxy deletes the TargetHttpsProxy by name.
func (gce *GCECloud) DeleteTargetHttpsProxy(name string) error { func (gce *GCECloud) DeleteTargetHttpsProxy(name string) error {
mc := newTargetProxyMetricContext("delete") mc := newTargetProxyMetricContext("delete")
op, err := gce.service.TargetHttpsProxies.Delete(gce.projectID, name).Do() op, err := gce.service.TargetHttpsProxies.Delete(gce.projectID, name).Do()
if err != nil { if err != nil {
if isHTTPErrorCode(err, http.StatusNotFound) { if isHTTPErrorCode(err, http.StatusNotFound) {
@ -146,6 +151,8 @@ func (gce *GCECloud) DeleteTargetHttpsProxy(name string) error {
// ListTargetHttpsProxies lists all TargetHttpsProxies in the project. // ListTargetHttpsProxies lists all TargetHttpsProxies in the project.
func (gce *GCECloud) ListTargetHttpsProxies() (*compute.TargetHttpsProxyList, error) { func (gce *GCECloud) ListTargetHttpsProxies() (*compute.TargetHttpsProxyList, error) {
mc := newTargetProxyMetricContext("list")
// TODO: use PageToken to list all not just the first 500 // TODO: use PageToken to list all not just the first 500
return gce.service.TargetHttpsProxies.List(gce.projectID).Do() v, err := gce.service.TargetHttpsProxies.List(gce.projectID).Do()
return v, mc.Observe(err)
} }

View File

@ -32,7 +32,9 @@ func newUrlMapMetricContext(request string) *metricContext {
// GetUrlMap returns the UrlMap by name. // GetUrlMap returns the UrlMap by name.
func (gce *GCECloud) GetUrlMap(name string) (*compute.UrlMap, error) { func (gce *GCECloud) GetUrlMap(name string) (*compute.UrlMap, error) {
return gce.service.UrlMaps.Get(gce.projectID, name).Do() mc := newUrlMapMetricContext("get")
v, err := gce.service.UrlMaps.Get(gce.projectID, name).Do()
return v, mc.Observe(err)
} }
// CreateUrlMap creates an url map, using the given backend service as the default service. // CreateUrlMap creates an url map, using the given backend service as the default service.
@ -80,6 +82,8 @@ func (gce *GCECloud) DeleteUrlMap(name string) error {
// ListUrlMaps lists all UrlMaps in the project. // ListUrlMaps lists all UrlMaps in the project.
func (gce *GCECloud) ListUrlMaps() (*compute.UrlMapList, error) { func (gce *GCECloud) ListUrlMaps() (*compute.UrlMapList, error) {
mc := newUrlMapMetricContext("list")
// TODO: use PageToken to list all not just the first 500 // TODO: use PageToken to list all not just the first 500
return gce.service.UrlMaps.List(gce.projectID).Do() v, err := gce.service.UrlMaps.List(gce.projectID).Do()
return v, mc.Observe(err)
} }