github.com/huaweicloud/golangsdk@v0.0.0-20210831081626-d823fe11ceba/openstack/imageservice/v2/images/results.go (about) 1 package images 2 3 import ( 4 "encoding/json" 5 "fmt" 6 "reflect" 7 "time" 8 9 "github.com/huaweicloud/golangsdk" 10 "github.com/huaweicloud/golangsdk/internal" 11 "github.com/huaweicloud/golangsdk/pagination" 12 ) 13 14 // Image represents an image found in the OpenStack Image service. 15 type Image struct { 16 // ID is the image UUID. 17 ID string `json:"id"` 18 19 // Name is the human-readable display name for the image. 20 Name string `json:"name"` 21 22 // Status is the image status. It can be "queued" or "active" 23 // See imageservice/v2/images/type.go 24 Status ImageStatus `json:"status"` 25 26 // Tags is a list of image tags. Tags are arbitrarily defined strings 27 // attached to an image. 28 Tags []string `json:"tags"` 29 30 // ContainerFormat is the format of the container. 31 // Valid values are ami, ari, aki, bare, and ovf. 32 ContainerFormat string `json:"container_format"` 33 34 // DiskFormat is the format of the disk. 35 // If set, valid values are ami, ari, aki, vhd, vmdk, raw, qcow2, vdi, 36 // and iso. 37 DiskFormat string `json:"disk_format"` 38 39 // MinDiskGigabytes is the amount of disk space in GB that is required to 40 // boot the image. 41 MinDiskGigabytes int `json:"min_disk"` 42 43 // MinRAMMegabytes [optional] is the amount of RAM in MB that is required to 44 // boot the image. 45 MinRAMMegabytes int `json:"min_ram"` 46 47 // Owner is the tenant ID the image belongs to. 48 Owner string `json:"owner"` 49 50 // Protected is whether the image is deletable or not. 51 Protected bool `json:"protected"` 52 53 // Visibility defines who can see/use the image. 54 Visibility ImageVisibility `json:"visibility"` 55 56 // Checksum is the checksum of the data that's associated with the image. 57 Checksum string `json:"checksum"` 58 59 // SizeBytes is the size of the data that's associated with the image. 60 SizeBytes int64 `json:"-"` 61 62 // Metadata is a set of metadata associated with the image. 63 // Image metadata allow for meaningfully define the image properties 64 // and tags. 65 // See http://docs.openstack.org/developer/glance/metadefs-concepts.html. 66 Metadata map[string]string `json:"metadata"` 67 68 // Properties is a set of key-value pairs, if any, that are associated with 69 // the image. 70 Properties map[string]interface{} 71 72 // CreatedAt is the date when the image has been created. 73 CreatedAt time.Time `json:"created_at"` 74 75 // UpdatedAt is the date when the last change has been made to the image or 76 // it's properties. 77 UpdatedAt time.Time `json:"updated_at"` 78 79 // File is the trailing path after the glance endpoint that represent the 80 // location of the image or the path to retrieve it. 81 File string `json:"file"` 82 83 // Schema is the path to the JSON-schema that represent the image or image 84 // entity. 85 Schema string `json:"schema"` 86 87 // VirtualSize is the virtual size of the image 88 VirtualSize int64 `json:"virtual_size"` 89 } 90 91 func (r *Image) UnmarshalJSON(b []byte) error { 92 type tmp Image 93 var s struct { 94 tmp 95 SizeBytes interface{} `json:"size"` 96 } 97 err := json.Unmarshal(b, &s) 98 if err != nil { 99 return err 100 } 101 *r = Image(s.tmp) 102 103 switch t := s.SizeBytes.(type) { 104 case nil: 105 r.SizeBytes = 0 106 case float32: 107 r.SizeBytes = int64(t) 108 case float64: 109 r.SizeBytes = int64(t) 110 default: 111 return fmt.Errorf("Unknown type for SizeBytes: %v (value: %v)", reflect.TypeOf(t), t) 112 } 113 114 // Bundle all other fields into Properties 115 var result interface{} 116 err = json.Unmarshal(b, &result) 117 if err != nil { 118 return err 119 } 120 if resultMap, ok := result.(map[string]interface{}); ok { 121 delete(resultMap, "self") 122 delete(resultMap, "size") 123 r.Properties = internal.RemainingKeys(Image{}, resultMap) 124 } 125 126 return err 127 } 128 129 type commonResult struct { 130 golangsdk.Result 131 } 132 133 // Extract interprets any commonResult as an Image. 134 func (r commonResult) Extract() (*Image, error) { 135 var s *Image 136 err := r.ExtractInto(&s) 137 return s, err 138 } 139 140 // CreateResult represents the result of a Create operation. Call its Extract 141 // method to interpret it as an Image. 142 type CreateResult struct { 143 commonResult 144 } 145 146 // UpdateResult represents the result of an Update operation. Call its Extract 147 // method to interpret it as an Image. 148 type UpdateResult struct { 149 commonResult 150 } 151 152 // GetResult represents the result of a Get operation. Call its Extract 153 // method to interpret it as an Image. 154 type GetResult struct { 155 commonResult 156 } 157 158 // DeleteResult represents the result of a Delete operation. Call its 159 // ExtractErr method to interpret it as an Image. 160 type DeleteResult struct { 161 golangsdk.ErrResult 162 } 163 164 // ImagePage represents the results of a List request. 165 type ImagePage struct { 166 serviceURL string 167 pagination.LinkedPageBase 168 } 169 170 // IsEmpty returns true if an ImagePage contains no Images results. 171 func (r ImagePage) IsEmpty() (bool, error) { 172 images, err := ExtractImages(r) 173 return len(images) == 0, err 174 } 175 176 // NextPageURL uses the response's embedded link reference to navigate to 177 // the next page of results. 178 func (r ImagePage) NextPageURL() (string, error) { 179 var s struct { 180 Next string `json:"next"` 181 } 182 err := r.ExtractInto(&s) 183 if err != nil { 184 return "", err 185 } 186 187 if s.Next == "" { 188 return "", nil 189 } 190 191 return nextPageURL(r.serviceURL, s.Next) 192 } 193 194 // ExtractImages interprets the results of a single page from a List() call, 195 // producing a slice of Image entities. 196 func ExtractImages(r pagination.Page) ([]Image, error) { 197 var s struct { 198 Images []Image `json:"images"` 199 } 200 err := (r.(ImagePage)).ExtractInto(&s) 201 return s.Images, err 202 }