github.com/gophercloud/gophercloud@v1.11.0/openstack/clustering/v1/policies/results.go (about)

     1  package policies
     2  
     3  import (
     4  	"encoding/json"
     5  	"fmt"
     6  	"strconv"
     7  	"time"
     8  
     9  	"github.com/gophercloud/gophercloud"
    10  	"github.com/gophercloud/gophercloud/pagination"
    11  )
    12  
    13  // Policy represents a clustering policy in the Openstack cloud.
    14  type Policy struct {
    15  	CreatedAt time.Time              `json:"-"`
    16  	Data      map[string]interface{} `json:"data"`
    17  	Domain    string                 `json:"domain"`
    18  	ID        string                 `json:"id"`
    19  	Name      string                 `json:"name"`
    20  	Project   string                 `json:"project"`
    21  	Spec      Spec                   `json:"spec"`
    22  	Type      string                 `json:"type"`
    23  	UpdatedAt time.Time              `json:"-"`
    24  	User      string                 `json:"user"`
    25  }
    26  
    27  func (r *Policy) UnmarshalJSON(b []byte) error {
    28  	type tmp Policy
    29  	var s struct {
    30  		tmp
    31  		CreatedAt string `json:"created_at,omitempty"`
    32  		UpdatedAt string `json:"updated_at,omitempty"`
    33  	}
    34  	err := json.Unmarshal(b, &s)
    35  	if err != nil {
    36  		return err
    37  	}
    38  	*r = Policy(s.tmp)
    39  
    40  	if s.CreatedAt != "" {
    41  		r.CreatedAt, err = time.Parse(gophercloud.RFC3339MilliNoZ, s.CreatedAt)
    42  		if err != nil {
    43  			r.CreatedAt, err = time.Parse(time.RFC3339, s.CreatedAt)
    44  			if err != nil {
    45  				return err
    46  			}
    47  		}
    48  	}
    49  
    50  	if s.UpdatedAt != "" {
    51  		r.UpdatedAt, err = time.Parse(gophercloud.RFC3339MilliNoZ, s.UpdatedAt)
    52  		if err != nil {
    53  			r.UpdatedAt, err = time.Parse(time.RFC3339, s.UpdatedAt)
    54  			if err != nil {
    55  				return err
    56  			}
    57  		}
    58  	}
    59  
    60  	return nil
    61  }
    62  
    63  // Spec represents an OpenStack clustering policy spec.
    64  type Spec struct {
    65  	Description string                 `json:"description"`
    66  	Properties  map[string]interface{} `json:"properties"`
    67  	Type        string                 `json:"type"`
    68  	Version     string                 `json:"-"`
    69  }
    70  
    71  func (r *Spec) UnmarshalJSON(b []byte) error {
    72  	type tmp Spec
    73  	var s struct {
    74  		tmp
    75  		Version interface{} `json:"version"`
    76  	}
    77  	err := json.Unmarshal(b, &s)
    78  	if err != nil {
    79  		return err
    80  	}
    81  	*r = Spec(s.tmp)
    82  
    83  	switch t := s.Version.(type) {
    84  	case float64:
    85  		if t == 1 {
    86  			r.Version = fmt.Sprintf("%.1f", t)
    87  		} else {
    88  			r.Version = strconv.FormatFloat(t, 'f', -1, 64)
    89  		}
    90  	case string:
    91  		r.Version = t
    92  	}
    93  
    94  	return nil
    95  }
    96  
    97  func (r Spec) MarshalJSON() ([]byte, error) {
    98  	spec := struct {
    99  		Type       string                 `json:"type"`
   100  		Version    string                 `json:"version"`
   101  		Properties map[string]interface{} `json:"properties"`
   102  	}{
   103  		Type:       r.Type,
   104  		Version:    r.Version,
   105  		Properties: r.Properties,
   106  	}
   107  	return json.Marshal(spec)
   108  }
   109  
   110  // policyResult is the resposne of a base Policy result.
   111  type policyResult struct {
   112  	gophercloud.Result
   113  }
   114  
   115  // Extract interpets any policyResult-base result as a Policy.
   116  func (r policyResult) Extract() (*Policy, error) {
   117  	var s struct {
   118  		Policy *Policy `json:"policy"`
   119  	}
   120  	err := r.ExtractInto(&s)
   121  
   122  	return s.Policy, err
   123  }
   124  
   125  // CreateResult is the result of an Update operation. Call its Extract
   126  // method to interpret it as a Policy.
   127  type CreateResult struct {
   128  	policyResult
   129  }
   130  
   131  // GetResult is the result of a Get operation. Call its Extract method to
   132  // interpret it as a Policy.
   133  type GetResult struct {
   134  	policyResult
   135  }
   136  
   137  // UpdateResult is the result of an Update operation. Call its Extract
   138  // method to interpret it as a Policy.
   139  type UpdateResult struct {
   140  	policyResult
   141  }
   142  
   143  // ValidateResult is the result of a Validate operation. Call its Extract
   144  // method to interpret it as a Policy.
   145  type ValidateResult struct {
   146  	policyResult
   147  }
   148  
   149  // DeleteResult is the result of a Delete operation. Call its Extract
   150  // method to interpret it as a DeleteHeader.
   151  type DeleteResult struct {
   152  	gophercloud.ErrResult
   153  }
   154  
   155  // PolicyPage contains a list page of all policies from a List call.
   156  type PolicyPage struct {
   157  	pagination.MarkerPageBase
   158  }
   159  
   160  // IsEmpty determines if a PolicyPage contains any results.
   161  func (page PolicyPage) IsEmpty() (bool, error) {
   162  	if page.StatusCode == 204 {
   163  		return true, nil
   164  	}
   165  
   166  	policies, err := ExtractPolicies(page)
   167  	return len(policies) == 0, err
   168  }
   169  
   170  // LastMarker returns the last policy ID in a ListResult.
   171  func (r PolicyPage) LastMarker() (string, error) {
   172  	policies, err := ExtractPolicies(r)
   173  	if err != nil {
   174  		return "", err
   175  	}
   176  	if len(policies) == 0 {
   177  		return "", nil
   178  	}
   179  	return policies[len(policies)-1].ID, nil
   180  }
   181  
   182  // ExtractPolicies returns a slice of Policies from the List operation.
   183  func ExtractPolicies(r pagination.Page) ([]Policy, error) {
   184  	var s struct {
   185  		Policies []Policy `json:"policies"`
   186  	}
   187  	err := (r.(PolicyPage)).ExtractInto(&s)
   188  	return s.Policies, err
   189  }