forked from hashicorp/terraform
/
resource_alicloud_eip_association.go
131 lines (103 loc) · 3.04 KB
/
resource_alicloud_eip_association.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
package alicloud
import (
"fmt"
"strings"
"github.com/denverdino/aliyungo/common"
"github.com/denverdino/aliyungo/ecs"
"github.com/hashicorp/terraform/helper/resource"
"github.com/hashicorp/terraform/helper/schema"
"time"
)
func resourceAliyunEipAssociation() *schema.Resource {
return &schema.Resource{
Create: resourceAliyunEipAssociationCreate,
Read: resourceAliyunEipAssociationRead,
Delete: resourceAliyunEipAssociationDelete,
Schema: map[string]*schema.Schema{
"allocation_id": &schema.Schema{
Type: schema.TypeString,
Optional: true,
Computed: true,
ForceNew: true,
},
"instance_id": &schema.Schema{
Type: schema.TypeString,
Optional: true,
Computed: true,
ForceNew: true,
},
},
}
}
func resourceAliyunEipAssociationCreate(d *schema.ResourceData, meta interface{}) error {
conn := meta.(*AliyunClient).ecsconn
allocationId := d.Get("allocation_id").(string)
instanceId := d.Get("instance_id").(string)
if err := conn.AssociateEipAddress(allocationId, instanceId); err != nil {
return err
}
d.SetId(allocationId + ":" + instanceId)
return resourceAliyunEipAssociationRead(d, meta)
}
func resourceAliyunEipAssociationRead(d *schema.ResourceData, meta interface{}) error {
client := meta.(*AliyunClient)
allocationId, instanceId, err := getAllocationIdAndInstanceId(d, meta)
if err != nil {
return err
}
eip, err := client.DescribeEipAddress(allocationId)
if err != nil {
if notFoundError(err) {
d.SetId("")
return nil
}
return err
}
if eip.InstanceId != instanceId {
d.SetId("")
return nil
}
d.Set("instance_id", eip.InstanceId)
d.Set("allocation_id", allocationId)
return nil
}
func resourceAliyunEipAssociationDelete(d *schema.ResourceData, meta interface{}) error {
conn := meta.(*AliyunClient).ecsconn
allocationId, instanceId, err := getAllocationIdAndInstanceId(d, meta)
if err != nil {
return err
}
return resource.Retry(5*time.Minute, func() *resource.RetryError {
err := conn.UnassociateEipAddress(allocationId, instanceId)
if err != nil {
e, _ := err.(*common.Error)
errCode := e.ErrorResponse.Code
if errCode == InstanceIncorrectStatus || errCode == HaVipIncorrectStatus {
return resource.RetryableError(fmt.Errorf("Eip in use - trying again while make it unassociated."))
}
}
args := &ecs.DescribeEipAddressesArgs{
RegionId: getRegion(d, meta),
AllocationId: allocationId,
}
eips, _, descErr := conn.DescribeEipAddresses(args)
if descErr != nil {
return resource.NonRetryableError(descErr)
} else if eips == nil || len(eips) < 1 {
return nil
}
for _, eip := range eips {
if eip.Status != ecs.EipStatusAvailable {
return resource.RetryableError(fmt.Errorf("Eip in use - trying again while make it unassociated."))
}
}
return nil
})
}
func getAllocationIdAndInstanceId(d *schema.ResourceData, meta interface{}) (string, string, error) {
parts := strings.Split(d.Id(), ":")
if len(parts) != 2 {
return "", "", fmt.Errorf("invalid resource id")
}
return parts[0], parts[1], nil
}