PageRenderTime 64ms CodeModel.GetById 34ms RepoModel.GetById 0ms app.codeStats 0ms

/vendor/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/requests.go

https://gitlab.com/CORP-RESELLER/kubernetes
Go | 281 lines | 217 code | 35 blank | 29 comment | 81 complexity | 24561c098447f469a7bd6fbfd254dd59 MD5 | raw file
  1. package tokens
  2. import (
  3. "net/http"
  4. "github.com/rackspace/gophercloud"
  5. )
  6. // Scope allows a created token to be limited to a specific domain or project.
  7. type Scope struct {
  8. ProjectID string
  9. ProjectName string
  10. DomainID string
  11. DomainName string
  12. }
  13. func subjectTokenHeaders(c *gophercloud.ServiceClient, subjectToken string) map[string]string {
  14. return map[string]string{
  15. "X-Subject-Token": subjectToken,
  16. }
  17. }
  18. // Create authenticates and either generates a new token, or changes the Scope of an existing token.
  19. func Create(c *gophercloud.ServiceClient, options gophercloud.AuthOptions, scope *Scope) CreateResult {
  20. type domainReq struct {
  21. ID *string `json:"id,omitempty"`
  22. Name *string `json:"name,omitempty"`
  23. }
  24. type projectReq struct {
  25. Domain *domainReq `json:"domain,omitempty"`
  26. Name *string `json:"name,omitempty"`
  27. ID *string `json:"id,omitempty"`
  28. }
  29. type userReq struct {
  30. ID *string `json:"id,omitempty"`
  31. Name *string `json:"name,omitempty"`
  32. Password string `json:"password"`
  33. Domain *domainReq `json:"domain,omitempty"`
  34. }
  35. type passwordReq struct {
  36. User userReq `json:"user"`
  37. }
  38. type tokenReq struct {
  39. ID string `json:"id"`
  40. }
  41. type identityReq struct {
  42. Methods []string `json:"methods"`
  43. Password *passwordReq `json:"password,omitempty"`
  44. Token *tokenReq `json:"token,omitempty"`
  45. }
  46. type scopeReq struct {
  47. Domain *domainReq `json:"domain,omitempty"`
  48. Project *projectReq `json:"project,omitempty"`
  49. }
  50. type authReq struct {
  51. Identity identityReq `json:"identity"`
  52. Scope *scopeReq `json:"scope,omitempty"`
  53. }
  54. type request struct {
  55. Auth authReq `json:"auth"`
  56. }
  57. // Populate the request structure based on the provided arguments. Create and return an error
  58. // if insufficient or incompatible information is present.
  59. var req request
  60. // Test first for unrecognized arguments.
  61. if options.APIKey != "" {
  62. return createErr(ErrAPIKeyProvided)
  63. }
  64. if options.TenantID != "" {
  65. return createErr(ErrTenantIDProvided)
  66. }
  67. if options.TenantName != "" {
  68. return createErr(ErrTenantNameProvided)
  69. }
  70. if options.Password == "" {
  71. if c.TokenID != "" {
  72. // Because we aren't using password authentication, it's an error to also provide any of the user-based authentication
  73. // parameters.
  74. if options.Username != "" {
  75. return createErr(ErrUsernameWithToken)
  76. }
  77. if options.UserID != "" {
  78. return createErr(ErrUserIDWithToken)
  79. }
  80. if options.DomainID != "" {
  81. return createErr(ErrDomainIDWithToken)
  82. }
  83. if options.DomainName != "" {
  84. return createErr(ErrDomainNameWithToken)
  85. }
  86. // Configure the request for Token authentication.
  87. req.Auth.Identity.Methods = []string{"token"}
  88. req.Auth.Identity.Token = &tokenReq{
  89. ID: c.TokenID,
  90. }
  91. } else {
  92. // If no password or token ID are available, authentication can't continue.
  93. return createErr(ErrMissingPassword)
  94. }
  95. } else {
  96. // Password authentication.
  97. req.Auth.Identity.Methods = []string{"password"}
  98. // At least one of Username and UserID must be specified.
  99. if options.Username == "" && options.UserID == "" {
  100. return createErr(ErrUsernameOrUserID)
  101. }
  102. if options.Username != "" {
  103. // If Username is provided, UserID may not be provided.
  104. if options.UserID != "" {
  105. return createErr(ErrUsernameOrUserID)
  106. }
  107. // Either DomainID or DomainName must also be specified.
  108. if options.DomainID == "" && options.DomainName == "" {
  109. return createErr(ErrDomainIDOrDomainName)
  110. }
  111. if options.DomainID != "" {
  112. if options.DomainName != "" {
  113. return createErr(ErrDomainIDOrDomainName)
  114. }
  115. // Configure the request for Username and Password authentication with a DomainID.
  116. req.Auth.Identity.Password = &passwordReq{
  117. User: userReq{
  118. Name: &options.Username,
  119. Password: options.Password,
  120. Domain: &domainReq{ID: &options.DomainID},
  121. },
  122. }
  123. }
  124. if options.DomainName != "" {
  125. // Configure the request for Username and Password authentication with a DomainName.
  126. req.Auth.Identity.Password = &passwordReq{
  127. User: userReq{
  128. Name: &options.Username,
  129. Password: options.Password,
  130. Domain: &domainReq{Name: &options.DomainName},
  131. },
  132. }
  133. }
  134. }
  135. if options.UserID != "" {
  136. // If UserID is specified, neither DomainID nor DomainName may be.
  137. if options.DomainID != "" {
  138. return createErr(ErrDomainIDWithUserID)
  139. }
  140. if options.DomainName != "" {
  141. return createErr(ErrDomainNameWithUserID)
  142. }
  143. // Configure the request for UserID and Password authentication.
  144. req.Auth.Identity.Password = &passwordReq{
  145. User: userReq{ID: &options.UserID, Password: options.Password},
  146. }
  147. }
  148. }
  149. // Add a "scope" element if a Scope has been provided.
  150. if scope != nil {
  151. if scope.ProjectName != "" {
  152. // ProjectName provided: either DomainID or DomainName must also be supplied.
  153. // ProjectID may not be supplied.
  154. if scope.DomainID == "" && scope.DomainName == "" {
  155. return createErr(ErrScopeDomainIDOrDomainName)
  156. }
  157. if scope.ProjectID != "" {
  158. return createErr(ErrScopeProjectIDOrProjectName)
  159. }
  160. if scope.DomainID != "" {
  161. // ProjectName + DomainID
  162. req.Auth.Scope = &scopeReq{
  163. Project: &projectReq{
  164. Name: &scope.ProjectName,
  165. Domain: &domainReq{ID: &scope.DomainID},
  166. },
  167. }
  168. }
  169. if scope.DomainName != "" {
  170. // ProjectName + DomainName
  171. req.Auth.Scope = &scopeReq{
  172. Project: &projectReq{
  173. Name: &scope.ProjectName,
  174. Domain: &domainReq{Name: &scope.DomainName},
  175. },
  176. }
  177. }
  178. } else if scope.ProjectID != "" {
  179. // ProjectID provided. ProjectName, DomainID, and DomainName may not be provided.
  180. if scope.DomainID != "" {
  181. return createErr(ErrScopeProjectIDAlone)
  182. }
  183. if scope.DomainName != "" {
  184. return createErr(ErrScopeProjectIDAlone)
  185. }
  186. // ProjectID
  187. req.Auth.Scope = &scopeReq{
  188. Project: &projectReq{ID: &scope.ProjectID},
  189. }
  190. } else if scope.DomainID != "" {
  191. // DomainID provided. ProjectID, ProjectName, and DomainName may not be provided.
  192. if scope.DomainName != "" {
  193. return createErr(ErrScopeDomainIDOrDomainName)
  194. }
  195. // DomainID
  196. req.Auth.Scope = &scopeReq{
  197. Domain: &domainReq{ID: &scope.DomainID},
  198. }
  199. } else if scope.DomainName != "" {
  200. return createErr(ErrScopeDomainName)
  201. } else {
  202. return createErr(ErrScopeEmpty)
  203. }
  204. }
  205. var result CreateResult
  206. var response *http.Response
  207. response, result.Err = c.Post(tokenURL(c), req, &result.Body, nil)
  208. if result.Err != nil {
  209. return result
  210. }
  211. result.Header = response.Header
  212. return result
  213. }
  214. // Get validates and retrieves information about another token.
  215. func Get(c *gophercloud.ServiceClient, token string) GetResult {
  216. var result GetResult
  217. var response *http.Response
  218. response, result.Err = c.Get(tokenURL(c), &result.Body, &gophercloud.RequestOpts{
  219. MoreHeaders: subjectTokenHeaders(c, token),
  220. OkCodes: []int{200, 203},
  221. })
  222. if result.Err != nil {
  223. return result
  224. }
  225. result.Header = response.Header
  226. return result
  227. }
  228. // Validate determines if a specified token is valid or not.
  229. func Validate(c *gophercloud.ServiceClient, token string) (bool, error) {
  230. response, err := c.Request("HEAD", tokenURL(c), gophercloud.RequestOpts{
  231. MoreHeaders: subjectTokenHeaders(c, token),
  232. OkCodes: []int{204, 404},
  233. })
  234. if err != nil {
  235. return false, err
  236. }
  237. return response.StatusCode == 204, nil
  238. }
  239. // Revoke immediately makes specified token invalid.
  240. func Revoke(c *gophercloud.ServiceClient, token string) RevokeResult {
  241. var res RevokeResult
  242. _, res.Err = c.Delete(tokenURL(c), &gophercloud.RequestOpts{
  243. MoreHeaders: subjectTokenHeaders(c, token),
  244. })
  245. return res
  246. }