cloudstack_instances.go 5.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165
  1. /*
  2. Copyright 2016 The Kubernetes Authors.
  3. Licensed under the Apache License, Version 2.0 (the "License");
  4. you may not use this file except in compliance with the License.
  5. You may obtain a copy of the License at
  6. http://www.apache.org/licenses/LICENSE-2.0
  7. Unless required by applicable law or agreed to in writing, software
  8. distributed under the License is distributed on an "AS IS" BASIS,
  9. WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  10. See the License for the specific language governing permissions and
  11. limitations under the License.
  12. */
  13. package cloudstack
  14. import (
  15. "context"
  16. "errors"
  17. "fmt"
  18. "github.com/xanzy/go-cloudstack/cloudstack"
  19. "k8s.io/api/core/v1"
  20. "k8s.io/apimachinery/pkg/types"
  21. cloudprovider "k8s.io/cloud-provider"
  22. "k8s.io/klog"
  23. )
  24. // NodeAddresses returns the addresses of the specified instance.
  25. func (cs *CSCloud) NodeAddresses(ctx context.Context, name types.NodeName) ([]v1.NodeAddress, error) {
  26. instance, count, err := cs.client.VirtualMachine.GetVirtualMachineByName(
  27. string(name),
  28. cloudstack.WithProject(cs.projectID),
  29. )
  30. if err != nil {
  31. if count == 0 {
  32. return nil, cloudprovider.InstanceNotFound
  33. }
  34. return nil, fmt.Errorf("error retrieving node addresses: %v", err)
  35. }
  36. return cs.nodeAddresses(instance)
  37. }
  38. // NodeAddressesByProviderID returns the addresses of the specified instance.
  39. func (cs *CSCloud) NodeAddressesByProviderID(ctx context.Context, providerID string) ([]v1.NodeAddress, error) {
  40. instance, count, err := cs.client.VirtualMachine.GetVirtualMachineByID(
  41. providerID,
  42. cloudstack.WithProject(cs.projectID),
  43. )
  44. if err != nil {
  45. if count == 0 {
  46. return nil, cloudprovider.InstanceNotFound
  47. }
  48. return nil, fmt.Errorf("error retrieving node addresses: %v", err)
  49. }
  50. return cs.nodeAddresses(instance)
  51. }
  52. func (cs *CSCloud) nodeAddresses(instance *cloudstack.VirtualMachine) ([]v1.NodeAddress, error) {
  53. if len(instance.Nic) == 0 {
  54. return nil, errors.New("instance does not have an internal IP")
  55. }
  56. addresses := []v1.NodeAddress{
  57. {Type: v1.NodeInternalIP, Address: instance.Nic[0].Ipaddress},
  58. }
  59. if instance.Hostname != "" {
  60. addresses = append(addresses, v1.NodeAddress{Type: v1.NodeHostName, Address: instance.Hostname})
  61. }
  62. if instance.Publicip != "" {
  63. addresses = append(addresses, v1.NodeAddress{Type: v1.NodeExternalIP, Address: instance.Publicip})
  64. } else {
  65. // Since there is no sane way to determine the external IP if the host isn't
  66. // using static NAT, we will just fire a log message and omit the external IP.
  67. klog.V(4).Infof("Could not determine the public IP of host %v (%v)", instance.Name, instance.Id)
  68. }
  69. return addresses, nil
  70. }
  71. // InstanceID returns the cloud provider ID of the specified instance.
  72. func (cs *CSCloud) InstanceID(ctx context.Context, name types.NodeName) (string, error) {
  73. instance, count, err := cs.client.VirtualMachine.GetVirtualMachineByName(
  74. string(name),
  75. cloudstack.WithProject(cs.projectID),
  76. )
  77. if err != nil {
  78. if count == 0 {
  79. return "", cloudprovider.InstanceNotFound
  80. }
  81. return "", fmt.Errorf("error retrieving instance ID: %v", err)
  82. }
  83. return instance.Id, nil
  84. }
  85. // InstanceType returns the type of the specified instance.
  86. func (cs *CSCloud) InstanceType(ctx context.Context, name types.NodeName) (string, error) {
  87. instance, count, err := cs.client.VirtualMachine.GetVirtualMachineByName(
  88. string(name),
  89. cloudstack.WithProject(cs.projectID),
  90. )
  91. if err != nil {
  92. if count == 0 {
  93. return "", cloudprovider.InstanceNotFound
  94. }
  95. return "", fmt.Errorf("error retrieving instance type: %v", err)
  96. }
  97. return instance.Serviceofferingname, nil
  98. }
  99. // InstanceTypeByProviderID returns the type of the specified instance.
  100. func (cs *CSCloud) InstanceTypeByProviderID(ctx context.Context, providerID string) (string, error) {
  101. instance, count, err := cs.client.VirtualMachine.GetVirtualMachineByID(
  102. providerID,
  103. cloudstack.WithProject(cs.projectID),
  104. )
  105. if err != nil {
  106. if count == 0 {
  107. return "", cloudprovider.InstanceNotFound
  108. }
  109. return "", fmt.Errorf("error retrieving instance type: %v", err)
  110. }
  111. return instance.Serviceofferingname, nil
  112. }
  113. // AddSSHKeyToAllInstances is currently not implemented.
  114. func (cs *CSCloud) AddSSHKeyToAllInstances(ctx context.Context, user string, keyData []byte) error {
  115. return cloudprovider.NotImplemented
  116. }
  117. // CurrentNodeName returns the name of the node we are currently running on.
  118. func (cs *CSCloud) CurrentNodeName(ctx context.Context, hostname string) (types.NodeName, error) {
  119. return types.NodeName(hostname), nil
  120. }
  121. // InstanceExistsByProviderID returns if the instance still exists.
  122. func (cs *CSCloud) InstanceExistsByProviderID(ctx context.Context, providerID string) (bool, error) {
  123. _, count, err := cs.client.VirtualMachine.GetVirtualMachineByID(
  124. providerID,
  125. cloudstack.WithProject(cs.projectID),
  126. )
  127. if err != nil {
  128. if count == 0 {
  129. return false, nil
  130. }
  131. return false, fmt.Errorf("error retrieving instance: %v", err)
  132. }
  133. return true, nil
  134. }
  135. // InstanceShutdownByProviderID returns true if the instance is in safe state to detach volumes
  136. func (cs *CSCloud) InstanceShutdownByProviderID(ctx context.Context, providerID string) (bool, error) {
  137. return false, cloudprovider.NotImplemented
  138. }