results.go 5.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215
  1. package roles
  2. import (
  3. "encoding/json"
  4. "devel.mephi.ru/iacherepanov/openstack-gophercloud"
  5. "devel.mephi.ru/iacherepanov/openstack-gophercloud/internal"
  6. "devel.mephi.ru/iacherepanov/openstack-gophercloud/pagination"
  7. )
  8. // Role grants permissions to a user.
  9. type Role struct {
  10. // DomainID is the domain ID the role belongs to.
  11. DomainID string `json:"domain_id"`
  12. // ID is the unique ID of the role.
  13. ID string `json:"id"`
  14. // Links contains referencing links to the role.
  15. Links map[string]interface{} `json:"links"`
  16. // Name is the role name
  17. Name string `json:"name"`
  18. // Extra is a collection of miscellaneous key/values.
  19. Extra map[string]interface{} `json:"-"`
  20. }
  21. func (r *Role) UnmarshalJSON(b []byte) error {
  22. type tmp Role
  23. var s struct {
  24. tmp
  25. Extra map[string]interface{} `json:"extra"`
  26. }
  27. err := json.Unmarshal(b, &s)
  28. if err != nil {
  29. return err
  30. }
  31. *r = Role(s.tmp)
  32. // Collect other fields and bundle them into Extra
  33. // but only if a field titled "extra" wasn't sent.
  34. if s.Extra != nil {
  35. r.Extra = s.Extra
  36. } else {
  37. var result interface{}
  38. err := json.Unmarshal(b, &result)
  39. if err != nil {
  40. return err
  41. }
  42. if resultMap, ok := result.(map[string]interface{}); ok {
  43. r.Extra = internal.RemainingKeys(Role{}, resultMap)
  44. }
  45. }
  46. return err
  47. }
  48. type roleResult struct {
  49. gophercloud.Result
  50. }
  51. // GetResult is the response from a Get operation. Call its Extract method
  52. // to interpret it as a Role.
  53. type GetResult struct {
  54. roleResult
  55. }
  56. // CreateResult is the response from a Create operation. Call its Extract method
  57. // to interpret it as a Role
  58. type CreateResult struct {
  59. roleResult
  60. }
  61. // UpdateResult is the response from an Update operation. Call its Extract
  62. // method to interpret it as a Role.
  63. type UpdateResult struct {
  64. roleResult
  65. }
  66. // DeleteResult is the response from a Delete operation. Call its ExtractErr to
  67. // determine if the request succeeded or failed.
  68. type DeleteResult struct {
  69. gophercloud.ErrResult
  70. }
  71. // RolePage is a single page of Role results.
  72. type RolePage struct {
  73. pagination.LinkedPageBase
  74. }
  75. // IsEmpty determines whether or not a page of Roles contains any results.
  76. func (r RolePage) IsEmpty() (bool, error) {
  77. roles, err := ExtractRoles(r)
  78. return len(roles) == 0, err
  79. }
  80. // NextPageURL extracts the "next" link from the links section of the result.
  81. func (r RolePage) NextPageURL() (string, error) {
  82. var s struct {
  83. Links struct {
  84. Next string `json:"next"`
  85. Previous string `json:"previous"`
  86. } `json:"links"`
  87. }
  88. err := r.ExtractInto(&s)
  89. if err != nil {
  90. return "", err
  91. }
  92. return s.Links.Next, err
  93. }
  94. // ExtractProjects returns a slice of Roles contained in a single page of
  95. // results.
  96. func ExtractRoles(r pagination.Page) ([]Role, error) {
  97. var s struct {
  98. Roles []Role `json:"roles"`
  99. }
  100. err := (r.(RolePage)).ExtractInto(&s)
  101. return s.Roles, err
  102. }
  103. // Extract interprets any roleResults as a Role.
  104. func (r roleResult) Extract() (*Role, error) {
  105. var s struct {
  106. Role *Role `json:"role"`
  107. }
  108. err := r.ExtractInto(&s)
  109. return s.Role, err
  110. }
  111. // RoleAssignment is the result of a role assignments query.
  112. type RoleAssignment struct {
  113. Role AssignedRole `json:"role,omitempty"`
  114. Scope Scope `json:"scope,omitempty"`
  115. User User `json:"user,omitempty"`
  116. Group Group `json:"group,omitempty"`
  117. }
  118. // AssignedRole represents a Role in an assignment.
  119. type AssignedRole struct {
  120. ID string `json:"id,omitempty"`
  121. }
  122. // Scope represents a scope in a Role assignment.
  123. type Scope struct {
  124. Domain Domain `json:"domain,omitempty"`
  125. Project Project `json:"project,omitempty"`
  126. }
  127. // Domain represents a domain in a role assignment scope.
  128. type Domain struct {
  129. ID string `json:"id,omitempty"`
  130. }
  131. // Project represents a project in a role assignment scope.
  132. type Project struct {
  133. ID string `json:"id,omitempty"`
  134. }
  135. // User represents a user in a role assignment scope.
  136. type User struct {
  137. ID string `json:"id,omitempty"`
  138. }
  139. // Group represents a group in a role assignment scope.
  140. type Group struct {
  141. ID string `json:"id,omitempty"`
  142. }
  143. // RoleAssignmentPage is a single page of RoleAssignments results.
  144. type RoleAssignmentPage struct {
  145. pagination.LinkedPageBase
  146. }
  147. // IsEmpty returns true if the RoleAssignmentPage contains no results.
  148. func (r RoleAssignmentPage) IsEmpty() (bool, error) {
  149. roleAssignments, err := ExtractRoleAssignments(r)
  150. return len(roleAssignments) == 0, err
  151. }
  152. // NextPageURL uses the response's embedded link reference to navigate to
  153. // the next page of results.
  154. func (r RoleAssignmentPage) NextPageURL() (string, error) {
  155. var s struct {
  156. Links struct {
  157. Next string `json:"next"`
  158. } `json:"links"`
  159. }
  160. err := r.ExtractInto(&s)
  161. return s.Links.Next, err
  162. }
  163. // ExtractRoleAssignments extracts a slice of RoleAssignments from a Collection
  164. // acquired from List.
  165. func ExtractRoleAssignments(r pagination.Page) ([]RoleAssignment, error) {
  166. var s struct {
  167. RoleAssignments []RoleAssignment `json:"role_assignments"`
  168. }
  169. err := (r.(RoleAssignmentPage)).ExtractInto(&s)
  170. return s.RoleAssignments, err
  171. }
  172. // AssignmentResult represents the result of an assign operation.
  173. // Call ExtractErr method to determine if the request succeeded or failed.
  174. type AssignmentResult struct {
  175. gophercloud.ErrResult
  176. }
  177. // UnassignmentResult represents the result of an unassign operation.
  178. // Call ExtractErr method to determine if the request succeeded or failed.
  179. type UnassignmentResult struct {
  180. gophercloud.ErrResult
  181. }