github.com/gophercloud/gophercloud@v1.11.0/openstack/blockstorage/extensions/backups/results.go (about) 1 package backups 2 3 import ( 4 "encoding/json" 5 "time" 6 7 "github.com/gophercloud/gophercloud" 8 "github.com/gophercloud/gophercloud/pagination" 9 ) 10 11 // Backup contains all the information associated with a Cinder Backup. 12 type Backup struct { 13 // ID is the Unique identifier of the backup. 14 ID string `json:"id"` 15 16 // CreatedAt is the date the backup was created. 17 CreatedAt time.Time `json:"-"` 18 19 // UpdatedAt is the date the backup was updated. 20 UpdatedAt time.Time `json:"-"` 21 22 // Name is the display name of the backup. 23 Name string `json:"name"` 24 25 // Description is the description of the backup. 26 Description string `json:"description"` 27 28 // VolumeID is the ID of the Volume from which this backup was created. 29 VolumeID string `json:"volume_id"` 30 31 // SnapshotID is the ID of the snapshot from which this backup was created. 32 SnapshotID string `json:"snapshot_id"` 33 34 // Status is the status of the backup. 35 Status string `json:"status"` 36 37 // Size is the size of the backup, in GB. 38 Size int `json:"size"` 39 40 // Object Count is the number of objects in the backup. 41 ObjectCount int `json:"object_count"` 42 43 // Container is the container where the backup is stored. 44 Container string `json:"container"` 45 46 // HasDependentBackups is whether there are other backups 47 // depending on this backup. 48 HasDependentBackups bool `json:"has_dependent_backups"` 49 50 // FailReason has the reason for the backup failure. 51 FailReason string `json:"fail_reason"` 52 53 // IsIncremental is whether this is an incremental backup. 54 IsIncremental bool `json:"is_incremental"` 55 56 // DataTimestamp is the time when the data on the volume was first saved. 57 DataTimestamp time.Time `json:"-"` 58 59 // ProjectID is the ID of the project that owns the backup. This is 60 // an admin-only field. 61 ProjectID string `json:"os-backup-project-attr:project_id"` 62 63 // Metadata is metadata about the backup. 64 // This requires microversion 3.43 or later. 65 Metadata *map[string]string `json:"metadata"` 66 67 // AvailabilityZone is the Availability Zone of the backup. 68 // This requires microversion 3.51 or later. 69 AvailabilityZone *string `json:"availability_zone"` 70 } 71 72 // CreateResult contains the response body and error from a Create request. 73 type CreateResult struct { 74 commonResult 75 } 76 77 // GetResult contains the response body and error from a Get request. 78 type GetResult struct { 79 commonResult 80 } 81 82 // DeleteResult contains the response body and error from a Delete request. 83 type DeleteResult struct { 84 gophercloud.ErrResult 85 } 86 87 // BackupPage is a pagination.Pager that is returned from a call to the List function. 88 type BackupPage struct { 89 pagination.LinkedPageBase 90 } 91 92 // UnmarshalJSON converts our JSON API response into our backup struct 93 func (r *Backup) UnmarshalJSON(b []byte) error { 94 type tmp Backup 95 var s struct { 96 tmp 97 CreatedAt gophercloud.JSONRFC3339MilliNoZ `json:"created_at"` 98 UpdatedAt gophercloud.JSONRFC3339MilliNoZ `json:"updated_at"` 99 DataTimestamp gophercloud.JSONRFC3339MilliNoZ `json:"data_timestamp"` 100 } 101 err := json.Unmarshal(b, &s) 102 if err != nil { 103 return err 104 } 105 *r = Backup(s.tmp) 106 107 r.CreatedAt = time.Time(s.CreatedAt) 108 r.UpdatedAt = time.Time(s.UpdatedAt) 109 r.DataTimestamp = time.Time(s.DataTimestamp) 110 111 return err 112 } 113 114 // IsEmpty returns true if a BackupPage contains no Backups. 115 func (r BackupPage) IsEmpty() (bool, error) { 116 if r.StatusCode == 204 { 117 return true, nil 118 } 119 120 volumes, err := ExtractBackups(r) 121 return len(volumes) == 0, err 122 } 123 124 func (page BackupPage) NextPageURL() (string, error) { 125 var s struct { 126 Links []gophercloud.Link `json:"backups_links"` 127 } 128 err := page.ExtractInto(&s) 129 if err != nil { 130 return "", err 131 } 132 return gophercloud.ExtractNextURL(s.Links) 133 } 134 135 // ExtractBackups extracts and returns Backups. It is used while iterating over a backups.List call. 136 func ExtractBackups(r pagination.Page) ([]Backup, error) { 137 var s []Backup 138 err := ExtractBackupsInto(r, &s) 139 return s, err 140 } 141 142 // UpdateResult contains the response body and error from an Update request. 143 type UpdateResult struct { 144 commonResult 145 } 146 147 type commonResult struct { 148 gophercloud.Result 149 } 150 151 // Extract will get the Backup object out of the commonResult object. 152 func (r commonResult) Extract() (*Backup, error) { 153 var s Backup 154 err := r.ExtractInto(&s) 155 return &s, err 156 } 157 158 func (r commonResult) ExtractInto(v interface{}) error { 159 return r.Result.ExtractIntoStructPtr(v, "backup") 160 } 161 162 func ExtractBackupsInto(r pagination.Page, v interface{}) error { 163 return r.(BackupPage).Result.ExtractIntoSlicePtr(v, "backups") 164 } 165 166 // RestoreResult contains the response body and error from a restore request. 167 type RestoreResult struct { 168 commonResult 169 } 170 171 // Restore contains all the information associated with a Cinder Backup restore 172 // response. 173 type Restore struct { 174 // BackupID is the Unique identifier of the backup. 175 BackupID string `json:"backup_id"` 176 177 // VolumeID is the Unique identifier of the volume. 178 VolumeID string `json:"volume_id"` 179 180 // Name is the name of the volume, where the backup was restored to. 181 VolumeName string `json:"volume_name"` 182 } 183 184 // Extract will get the Backup restore object out of the RestoreResult object. 185 func (r RestoreResult) Extract() (*Restore, error) { 186 var s Restore 187 err := r.ExtractInto(&s) 188 return &s, err 189 } 190 191 func (r RestoreResult) ExtractInto(v interface{}) error { 192 return r.Result.ExtractIntoStructPtr(v, "restore") 193 } 194 195 // ExportResult contains the response body and error from an export request. 196 type ExportResult struct { 197 commonResult 198 } 199 200 // BackupRecord contains an information about a backup backend storage. 201 type BackupRecord struct { 202 // The service used to perform the backup. 203 BackupService string `json:"backup_service"` 204 205 // An identifier string to locate the backup. 206 BackupURL []byte `json:"backup_url"` 207 } 208 209 // Extract will get the Backup record object out of the ExportResult object. 210 func (r ExportResult) Extract() (*BackupRecord, error) { 211 var s BackupRecord 212 err := r.ExtractInto(&s) 213 return &s, err 214 } 215 216 func (r ExportResult) ExtractInto(v interface{}) error { 217 return r.Result.ExtractIntoStructPtr(v, "backup-record") 218 } 219 220 // ImportResponse struct contains the response of the Backup Import action. 221 type ImportResponse struct { 222 ID string `json:"id"` 223 Name string `json:"name"` 224 } 225 226 // ImportResult contains the response body and error from an import request. 227 type ImportResult struct { 228 gophercloud.Result 229 } 230 231 // Extract will get the Backup object out of the commonResult object. 232 func (r ImportResult) Extract() (*ImportResponse, error) { 233 var s ImportResponse 234 err := r.ExtractInto(&s) 235 return &s, err 236 } 237 238 func (r ImportResult) ExtractInto(v interface{}) error { 239 return r.Result.ExtractIntoStructPtr(v, "backup") 240 } 241 242 // ImportBackup contains all the information to import a Cinder Backup. 243 type ImportBackup struct { 244 ID string `json:"id"` 245 CreatedAt time.Time `json:"-"` 246 UpdatedAt time.Time `json:"-"` 247 VolumeID string `json:"volume_id"` 248 SnapshotID *string `json:"snapshot_id"` 249 Status *string `json:"status"` 250 Size *int `json:"size"` 251 ObjectCount *int `json:"object_count"` 252 Container *string `json:"container"` 253 ServiceMetadata *string `json:"service_metadata"` 254 Service *string `json:"service"` 255 Host *string `json:"host"` 256 UserID string `json:"user_id"` 257 DeletedAt time.Time `json:"-"` 258 DataTimestamp time.Time `json:"-"` 259 TempSnapshotID *string `json:"temp_snapshot_id"` 260 TempVolumeID *string `json:"temp_volume_id"` 261 RestoreVolumeID *string `json:"restore_volume_id"` 262 NumDependentBackups *int `json:"num_dependent_backups"` 263 EncryptionKeyID *string `json:"encryption_key_id"` 264 ParentID *string `json:"parent_id"` 265 Deleted bool `json:"deleted"` 266 DisplayName *string `json:"display_name"` 267 DisplayDescription *string `json:"display_description"` 268 DriverInfo interface{} `json:"driver_info"` 269 FailReason *string `json:"fail_reason"` 270 ProjectID string `json:"project_id"` 271 Metadata map[string]string `json:"metadata"` 272 AvailabilityZone *string `json:"availability_zone"` 273 } 274 275 // UnmarshalJSON converts our JSON API response into our backup struct 276 func (r *ImportBackup) UnmarshalJSON(b []byte) error { 277 type tmp ImportBackup 278 var s struct { 279 tmp 280 CreatedAt time.Time `json:"created_at"` 281 UpdatedAt time.Time `json:"updated_at"` 282 DeletedAt time.Time `json:"deleted_at"` 283 DataTimestamp time.Time `json:"data_timestamp"` 284 } 285 err := json.Unmarshal(b, &s) 286 if err != nil { 287 return err 288 } 289 *r = ImportBackup(s.tmp) 290 291 r.CreatedAt = time.Time(s.CreatedAt) 292 r.UpdatedAt = time.Time(s.UpdatedAt) 293 r.DeletedAt = time.Time(s.DeletedAt) 294 r.DataTimestamp = time.Time(s.DataTimestamp) 295 296 return err 297 } 298 299 // MarshalJSON converts our struct request into JSON backup import request 300 func (r ImportBackup) MarshalJSON() ([]byte, error) { 301 type b ImportBackup 302 type ext struct { 303 CreatedAt *string `json:"created_at"` 304 UpdatedAt *string `json:"updated_at"` 305 DeletedAt *string `json:"deleted_at"` 306 DataTimestamp *string `json:"data_timestamp"` 307 } 308 type tmp struct { 309 b 310 ext 311 } 312 313 var t ext 314 if r.CreatedAt != (time.Time{}) { 315 v := r.CreatedAt.Format(time.RFC3339) 316 t.CreatedAt = &v 317 } 318 if r.UpdatedAt != (time.Time{}) { 319 v := r.UpdatedAt.Format(time.RFC3339) 320 t.UpdatedAt = &v 321 } 322 if r.DeletedAt != (time.Time{}) { 323 v := r.DeletedAt.Format(time.RFC3339) 324 t.DeletedAt = &v 325 } 326 if r.DataTimestamp != (time.Time{}) { 327 v := r.DataTimestamp.Format(time.RFC3339) 328 t.DataTimestamp = &v 329 } 330 331 if r.Metadata == nil { 332 r.Metadata = make(map[string]string) 333 } 334 335 s := tmp{ 336 b(r), 337 t, 338 } 339 340 return json.Marshal(s) 341 }