forked from kubernetes/kubernetes
-
Notifications
You must be signed in to change notification settings - Fork 0
/
results.go
147 lines (115 loc) · 4.12 KB
/
results.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
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
package snapshots
import (
"github.com/rackspace/gophercloud"
os "github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots"
"github.com/rackspace/gophercloud/pagination"
"github.com/mitchellh/mapstructure"
)
// Status is the type used to represent a snapshot's status
type Status string
// Constants to use for supported statuses
const (
Creating Status = "CREATING"
Available Status = "AVAILABLE"
Deleting Status = "DELETING"
Error Status = "ERROR"
DeleteError Status = "ERROR_DELETING"
)
// Snapshot is the Rackspace representation of an external block storage device.
type Snapshot struct {
// The timestamp when this snapshot was created.
CreatedAt string `mapstructure:"created_at"`
// The human-readable description for this snapshot.
Description string `mapstructure:"display_description"`
// The human-readable name for this snapshot.
Name string `mapstructure:"display_name"`
// The UUID for this snapshot.
ID string `mapstructure:"id"`
// The random metadata associated with this snapshot. Note: unlike standard
// OpenStack snapshots, this cannot actually be set.
Metadata map[string]string `mapstructure:"metadata"`
// Indicates the current progress of the snapshot's backup procedure.
Progress string `mapstructure:"os-extended-snapshot-attributes:progress"`
// The project ID.
ProjectID string `mapstructure:"os-extended-snapshot-attributes:project_id"`
// The size of the volume which this snapshot backs up.
Size int `mapstructure:"size"`
// The status of the snapshot.
Status Status `mapstructure:"status"`
// The ID of the volume which this snapshot seeks to back up.
VolumeID string `mapstructure:"volume_id"`
}
// CreateResult represents the result of a create operation
type CreateResult struct {
os.CreateResult
}
// GetResult represents the result of a get operation
type GetResult struct {
os.GetResult
}
// UpdateResult represents the result of an update operation
type UpdateResult struct {
gophercloud.Result
}
func commonExtract(resp interface{}, err error) (*Snapshot, error) {
if err != nil {
return nil, err
}
var respStruct struct {
Snapshot *Snapshot `json:"snapshot"`
}
err = mapstructure.Decode(resp, &respStruct)
return respStruct.Snapshot, err
}
// Extract will get the Snapshot object out of the GetResult object.
func (r GetResult) Extract() (*Snapshot, error) {
return commonExtract(r.Body, r.Err)
}
// Extract will get the Snapshot object out of the CreateResult object.
func (r CreateResult) Extract() (*Snapshot, error) {
return commonExtract(r.Body, r.Err)
}
// Extract will get the Snapshot object out of the UpdateResult object.
func (r UpdateResult) Extract() (*Snapshot, error) {
return commonExtract(r.Body, r.Err)
}
// ExtractSnapshots extracts and returns Snapshots. It is used while iterating over a snapshots.List call.
func ExtractSnapshots(page pagination.Page) ([]Snapshot, error) {
var response struct {
Snapshots []Snapshot `json:"snapshots"`
}
err := mapstructure.Decode(page.(os.ListResult).Body, &response)
return response.Snapshots, err
}
// WaitUntilComplete will continually poll a snapshot until it successfully
// transitions to a specified state. It will do this for at most the number of
// seconds specified.
func (snapshot Snapshot) WaitUntilComplete(c *gophercloud.ServiceClient, timeout int) error {
return gophercloud.WaitFor(timeout, func() (bool, error) {
// Poll resource
current, err := Get(c, snapshot.ID).Extract()
if err != nil {
return false, err
}
// Has it been built yet?
if current.Progress == "100%" {
return true, nil
}
return false, nil
})
}
// WaitUntilDeleted will continually poll a snapshot until it has been
// successfully deleted, i.e. returns a 404 status.
func (snapshot Snapshot) WaitUntilDeleted(c *gophercloud.ServiceClient, timeout int) error {
return gophercloud.WaitFor(timeout, func() (bool, error) {
// Poll resource
_, err := Get(c, snapshot.ID).Extract()
// Check for a 404
if casted, ok := err.(*gophercloud.UnexpectedResponseCodeError); ok && casted.Actual == 404 {
return true, nil
} else if err != nil {
return false, err
}
return false, nil
})
}