conjur-api 5.3.8.pre.319 → 5.3.8.pre.321

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (150) hide show
  1. checksums.yaml +4 -4
  2. data/.codeclimate.yml +10 -0
  3. data/.dockerignore +1 -0
  4. data/.github/CODEOWNERS +10 -0
  5. data/.gitignore +32 -0
  6. data/.gitleaks.toml +219 -0
  7. data/.overcommit.yml +16 -0
  8. data/.project +18 -0
  9. data/.rubocop.yml +3 -0
  10. data/.rubocop_settings.yml +86 -0
  11. data/.rubocop_todo.yml +709 -0
  12. data/.yardopts +1 -0
  13. data/CHANGELOG.md +448 -0
  14. data/CONTRIBUTING.md +138 -0
  15. data/Dockerfile +16 -0
  16. data/Gemfile +7 -0
  17. data/Jenkinsfile +136 -0
  18. data/LICENSE +202 -0
  19. data/README.md +162 -0
  20. data/Rakefile +47 -0
  21. data/SECURITY.md +42 -0
  22. data/VERSION +1 -1
  23. data/bin/parse-changelog.sh +12 -0
  24. data/ci/configure_v4.sh +12 -0
  25. data/ci/configure_v5.sh +19 -0
  26. data/ci/oauth/keycloak/create_client +18 -0
  27. data/ci/oauth/keycloak/create_user +21 -0
  28. data/ci/oauth/keycloak/fetch_certificate +18 -0
  29. data/ci/oauth/keycloak/keycloak_functions.sh +71 -0
  30. data/ci/oauth/keycloak/standalone.xml +578 -0
  31. data/ci/oauth/keycloak/wait_for_server +56 -0
  32. data/ci/submit-coverage +36 -0
  33. data/conjur-api.gemspec +41 -0
  34. data/dev/Dockerfile.dev +12 -0
  35. data/dev/docker-compose.yml +56 -0
  36. data/dev/start +22 -0
  37. data/dev/stop +5 -0
  38. data/docker-compose.yml +98 -0
  39. data/example/demo_v4.rb +49 -0
  40. data/example/demo_v5.rb +57 -0
  41. data/features/authenticators.feature +41 -0
  42. data/features/authn.feature +14 -0
  43. data/features/authn_local.feature +32 -0
  44. data/features/exists.feature +37 -0
  45. data/features/group.feature +11 -0
  46. data/features/host.feature +50 -0
  47. data/features/host_factory_create_host.feature +28 -0
  48. data/features/host_factory_token.feature +63 -0
  49. data/features/load_policy.feature +61 -0
  50. data/features/members.feature +51 -0
  51. data/features/new_api.feature +36 -0
  52. data/features/permitted.feature +70 -0
  53. data/features/permitted_roles.feature +30 -0
  54. data/features/public_keys.feature +11 -0
  55. data/features/resource_fields.feature +53 -0
  56. data/features/role_fields.feature +15 -0
  57. data/features/rotate_api_key.feature +13 -0
  58. data/features/step_definitions/api_steps.rb +52 -0
  59. data/features/step_definitions/policy_steps.rb +134 -0
  60. data/features/step_definitions/result_steps.rb +11 -0
  61. data/features/support/env.rb +19 -0
  62. data/features/support/hooks.rb +3 -0
  63. data/features/support/world.rb +12 -0
  64. data/features/update_password.feature +14 -0
  65. data/features/user.feature +58 -0
  66. data/features/variable_fields.feature +20 -0
  67. data/features/variable_value.feature +60 -0
  68. data/features_v4/authn_local.feature +27 -0
  69. data/features_v4/exists.feature +29 -0
  70. data/features_v4/host.feature +18 -0
  71. data/features_v4/host_factory_token.feature +49 -0
  72. data/features_v4/members.feature +39 -0
  73. data/features_v4/permitted.feature +15 -0
  74. data/features_v4/permitted_roles.feature +8 -0
  75. data/features_v4/resource_fields.feature +47 -0
  76. data/features_v4/rotate_api_key.feature +13 -0
  77. data/features_v4/step_definitions/api_steps.rb +17 -0
  78. data/features_v4/step_definitions/result_steps.rb +3 -0
  79. data/features_v4/support/env.rb +23 -0
  80. data/features_v4/support/policy.yml +34 -0
  81. data/features_v4/support/world.rb +12 -0
  82. data/features_v4/variable_fields.feature +11 -0
  83. data/features_v4/variable_value.feature +54 -0
  84. data/lib/conjur/acts_as_resource.rb +123 -0
  85. data/lib/conjur/acts_as_role.rb +142 -0
  86. data/lib/conjur/acts_as_rolsource.rb +32 -0
  87. data/lib/conjur/acts_as_user.rb +68 -0
  88. data/lib/conjur/api/authenticators.rb +43 -0
  89. data/lib/conjur/api/authn.rb +144 -0
  90. data/lib/conjur/api/host_factories.rb +71 -0
  91. data/lib/conjur/api/ldap_sync.rb +38 -0
  92. data/lib/conjur/api/policies.rb +56 -0
  93. data/lib/conjur/api/pubkeys.rb +53 -0
  94. data/lib/conjur/api/resources.rb +109 -0
  95. data/lib/conjur/api/roles.rb +98 -0
  96. data/lib/conjur/api/router/v4.rb +206 -0
  97. data/lib/conjur/api/router/v5.rb +269 -0
  98. data/lib/conjur/api/variables.rb +59 -0
  99. data/lib/conjur/api.rb +105 -0
  100. data/lib/conjur/base.rb +355 -0
  101. data/lib/conjur/base_object.rb +57 -0
  102. data/lib/conjur/build_object.rb +47 -0
  103. data/lib/conjur/cache.rb +26 -0
  104. data/lib/conjur/cert_utils.rb +63 -0
  105. data/lib/conjur/cidr.rb +71 -0
  106. data/lib/conjur/configuration.rb +460 -0
  107. data/lib/conjur/escape.rb +129 -0
  108. data/lib/conjur/exceptions.rb +4 -0
  109. data/lib/conjur/group.rb +41 -0
  110. data/lib/conjur/has_attributes.rb +98 -0
  111. data/lib/conjur/host.rb +27 -0
  112. data/lib/conjur/host_factory.rb +75 -0
  113. data/lib/conjur/host_factory_token.rb +78 -0
  114. data/lib/conjur/id.rb +71 -0
  115. data/lib/conjur/layer.rb +9 -0
  116. data/lib/conjur/log.rb +72 -0
  117. data/lib/conjur/log_source.rb +60 -0
  118. data/lib/conjur/policy.rb +34 -0
  119. data/lib/conjur/policy_load_result.rb +61 -0
  120. data/lib/conjur/query_string.rb +12 -0
  121. data/lib/conjur/resource.rb +29 -0
  122. data/lib/conjur/role.rb +29 -0
  123. data/lib/conjur/role_grant.rb +85 -0
  124. data/lib/conjur/routing.rb +29 -0
  125. data/lib/conjur/user.rb +40 -0
  126. data/lib/conjur/variable.rb +208 -0
  127. data/lib/conjur/webservice.rb +30 -0
  128. data/lib/conjur-api/version.rb +24 -0
  129. data/lib/conjur-api.rb +2 -0
  130. data/publish.sh +5 -0
  131. data/spec/api/host_factories_spec.rb +34 -0
  132. data/spec/api_spec.rb +254 -0
  133. data/spec/base_object_spec.rb +13 -0
  134. data/spec/cert_utils_spec.rb +173 -0
  135. data/spec/cidr_spec.rb +34 -0
  136. data/spec/configuration_spec.rb +330 -0
  137. data/spec/has_attributes_spec.rb +63 -0
  138. data/spec/helpers/errors_matcher.rb +34 -0
  139. data/spec/helpers/request_helpers.rb +10 -0
  140. data/spec/id_spec.rb +29 -0
  141. data/spec/ldap_sync_spec.rb +21 -0
  142. data/spec/log_source_spec.rb +13 -0
  143. data/spec/log_spec.rb +42 -0
  144. data/spec/roles_spec.rb +24 -0
  145. data/spec/spec_helper.rb +113 -0
  146. data/spec/ssl_spec.rb +109 -0
  147. data/spec/uri_escape_spec.rb +21 -0
  148. data/test.sh +76 -0
  149. data/tmp/.keep +0 -0
  150. metadata +194 -3
@@ -0,0 +1,142 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Copyright 2013-2018 CyberArk Ltd.
4
+ #
5
+ # Licensed under the Apache License, Version 2.0 (the "License");
6
+ # you may not use this file except in compliance with the License.
7
+ # You may obtain a copy of the License at
8
+ #
9
+ # http://www.apache.org/licenses/LICENSE-2.0
10
+ #
11
+ # Unless required by applicable law or agreed to in writing, software
12
+ # distributed under the License is distributed on an "AS IS" BASIS,
13
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
+ # See the License for the specific language governing permissions and
15
+ # limitations under the License.
16
+
17
+ module Conjur
18
+
19
+ # This module provides methods for things that have an associated {Conjur::Role}.
20
+ #
21
+ # All high level Conjur assets (groups and users, for example) are composed of both a role and a resource. This allows
22
+ # these assets to have permissions on other assets, and for other assets to have permission
23
+ # on them.
24
+ #
25
+ # The {Conjur::ActsAsRole} module itself should be considered private, but it's methods are
26
+ # public when added to a Conjur asset class.
27
+ module ActsAsRole
28
+
29
+ # Login name of the role. This is formed from the role kind and role id.
30
+ # For users, the role kind can be omitted.
31
+ def login
32
+ [ kind, identifier ].delete_if{|t| t == "user"}.join('/')
33
+ end
34
+
35
+ # Check whether this object exists by performing a HEAD request to its URL.
36
+ #
37
+ # This method will return false if the object doesn't exist.
38
+ #
39
+ # @example
40
+ # does_not_exist = api.user 'does-not-exist' # This returns without error.
41
+ #
42
+ # # this is wrong!
43
+ # owner = does_not_exist.members # raises RestClient::ResourceNotFound
44
+ #
45
+ # # this is right!
46
+ # owner = if does_not_exist.exists?
47
+ # does_not_exist.members
48
+ # else
49
+ # nil # or some sensible default
50
+ # end
51
+ #
52
+ # @return [Boolean] does it exist?
53
+ def exists?
54
+ begin
55
+ rbac_role_resource.head
56
+ true
57
+ rescue RestClient::Forbidden
58
+ true
59
+ rescue RestClient::ResourceNotFound
60
+ false
61
+ end
62
+ end
63
+
64
+ # Find all roles of which this role is a member. By default, role relationships are recursively expanded,
65
+ # so if `a` is a member of `b`, and `b` is a member of `c`, `a.all` will include `c`.
66
+ #
67
+ # ### Permissions
68
+ # You must be a member of the role to call this method.
69
+ #
70
+ # You can restrict the roles returned to one or more role ids. This feature is mainly useful
71
+ # for checking whether this role is a member of any of a set of roles.
72
+ #
73
+ # ### Options
74
+ #
75
+ # * **recursive** Defaults to +true+, performs recursive expansion of the memberships.
76
+ #
77
+ # @example Show all roles of which `"conjur:group:pubkeys-1.0/key-managers"` is a member
78
+ # # Add alice to the group, so we see something interesting
79
+ # key_managers = api.group('pubkeys-1.0/key-managers')
80
+ # key_managers.add_member api.user('alice')
81
+ #
82
+ # # Show the memberships, mapped to the member ids.
83
+ # key_managers.role.all.map(&:id)
84
+ # # => ["conjur:group:pubkeys-1.0/admin", "conjur:user:alice"]
85
+ #
86
+ # @example See if role `"conjur:user:alice"` is a member of either `"conjur:groups:developers"` or `"conjur:group:ops"`
87
+ # is_member = api.role('conjur:user:alice').all(filter: ['conjur:group:developers', 'conjur:group:ops']).any?
88
+ #
89
+ # @param [Hash] options options for the request
90
+ # @return [Array<Conjur::Role>] Roles of which this role is a member
91
+ def memberships options = {}
92
+ request = if options.delete(:recursive) == false
93
+ options["memberships"] = true
94
+ else
95
+ options["all"] = true
96
+ end
97
+ if filter = options.delete(:filter)
98
+ filter = [filter] unless filter.is_a?(Array)
99
+ options["filter"] = filter.map(&Id.method(:new))
100
+ end
101
+
102
+ result = JSON.parse(rbac_role_resource[options_querystring options].get)
103
+ if result.is_a?(Hash) && ( count = result['count'] )
104
+ count
105
+ else
106
+ host = Conjur.configuration.core_url
107
+ result.collect do |item|
108
+ if item.is_a?(String)
109
+ build_object(item, default_class: Role)
110
+ else
111
+ RoleGrant.parse_from_json(item, self.options)
112
+ end
113
+ end
114
+ end
115
+ end
116
+
117
+ # Fetch the direct members of this role. The results are *not* recursively expanded).
118
+ #
119
+ # ### Permissions
120
+ # You must be a member of the role to call this method.
121
+ #
122
+ # @param options [Hash, nil] extra parameters to pass to the webservice method.
123
+ # @return [Array<Conjur::RoleGrant>] the role memberships
124
+ # @raise [RestClient::Forbidden] if you don't have permission to perform this operation
125
+ def members options = {}
126
+ options["members"] = true
127
+ result = JSON.parse(rbac_role_resource[options_querystring options].get)
128
+ if result.is_a?(Hash) && ( count = result['count'] )
129
+ count
130
+ else
131
+ parser_for(:members, credentials, result)
132
+ end
133
+ end
134
+
135
+ private
136
+
137
+ # RestClient::Resource for RBAC role operations.
138
+ def rbac_role_resource
139
+ url_for(:roles_role, credentials, id)
140
+ end
141
+ end
142
+ end
@@ -0,0 +1,32 @@
1
+ #
2
+ # Copyright (C) 2013-2017 Conjur Inc
3
+ #
4
+ # Permission is hereby granted, free of charge, to any person obtaining a copy of
5
+ # this software and associated documentation files (the "Software"), to deal in
6
+ # the Software without restriction, including without limitation the rights to
7
+ # use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
8
+ # the Software, and to permit persons to whom the Software is furnished to do so,
9
+ # subject to the following conditions:
10
+ #
11
+ # The above copyright notice and this permission notice shall be included in all
12
+ # copies or substantial portions of the Software.
13
+ #
14
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
16
+ # FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
17
+ # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
18
+ # IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
19
+ # CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
20
+ #
21
+ module Conjur
22
+
23
+ # This module provides methods for things that have an associated {Conjur::Role} and
24
+ # {Conjur::Resource}.
25
+ module ActsAsRolsource
26
+ # @api private
27
+ def self.included(base)
28
+ base.include ActsAsRole
29
+ base.include ActsAsResource
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,68 @@
1
+ #
2
+ # Copyright 2013-2017 Conjur Inc
3
+ #
4
+ # Permission is hereby granted, free of charge, to any person obtaining a copy of
5
+ # this software and associated documentation files (the "Software"), to deal in
6
+ # the Software without restriction, including without limitation the rights to
7
+ # use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
8
+ # the Software, and to permit persons to whom the Software is furnished to do so,
9
+ # subject to the following conditions:
10
+ #
11
+ # The above copyright notice and this permission notice shall be included in all
12
+ # copies or substantial portions of the Software.
13
+ #
14
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
16
+ # FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
17
+ # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
18
+ # IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
19
+ # CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
20
+ #
21
+ module Conjur
22
+ # This module provides methods for things that are like users (specifically, those that have
23
+ # api keys).
24
+ module ActsAsUser
25
+ # @api private
26
+ def self.included(base)
27
+ base.include ActsAsRolsource
28
+ end
29
+
30
+ # Returns a newly created user's api_key.
31
+ #
32
+ # @note The API key is not returned by {API#resource}. It is only available
33
+ # via {API#login}, when the object is newly created, and when the API key is rotated.
34
+ #
35
+ # @return [String] the api key
36
+ # @raise [Exception] when the object isn't newly created.
37
+ def api_key
38
+ attributes['api_key'] or raise "api_key is only available on a newly created #{kind}"
39
+ end
40
+
41
+ # Create an api logged in as this user-like thing.
42
+ #
43
+ # @note As with {#api_key}, this method only works on newly created instances.
44
+ # @see #api_key
45
+ # @return [Conjur::API] an api logged in as this user-like thing.
46
+ def api
47
+ Conjur::API.new_from_key login, api_key, account: account
48
+ end
49
+
50
+ # Rotate this role's API key. You must have `update` permission on the user to do so.
51
+ #
52
+ # @note You will not be able to access the API key returned by this method later, so you should
53
+ # probably hang onto it it.
54
+ #
55
+ # @note You cannot rotate your own API key with this method. To do so, use `Conjur::API.rotate_api_key`.
56
+ #
57
+ # @note This feature requires a Conjur appliance running version 4.6 or higher.
58
+ #
59
+ # @return [String] the new API key for this user.
60
+ def rotate_api_key
61
+ if login == username
62
+ raise 'You cannot rotate your own API key via this method. To do so, use `Conjur::API.rotate_api_key`'
63
+ end
64
+
65
+ url_for(:authn_rotate_api_key, credentials, account, id).put("").body
66
+ end
67
+ end
68
+ end
@@ -0,0 +1,43 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'conjur/webservice'
4
+
5
+ module Conjur
6
+ # API contains each of the methods for access the Conjur API endpoints
7
+ #-- :reek:DataClump for authenticator identifier fields (name, id, account)
8
+ class API
9
+ # @!group Authenticators
10
+
11
+ # List all configured authenticators
12
+ def authenticator_list
13
+ JSON.parse(url_for(:authenticators).get)
14
+ end
15
+
16
+ # Fetches the available authentication providers for the authenticator and account.
17
+ # The authenticators must be loaded in Conjur policy prior to fetching.
18
+ #
19
+ # @param [String] authenticator the authenticator type to retrieve providers for
20
+ def authentication_providers authenticator, account: Conjur.configuration.account
21
+ JSON.parse(url_for(:authentication_providers, account, authenticator, credentials).get)
22
+ end
23
+
24
+ # Enables an authenticator in Conjur. The authenticator must be defined and
25
+ # loaded in Conjur policy prior to enabling it.
26
+ #
27
+ # @param [String] authenticator the authenticator type to enable (e.g. authn-k8s)
28
+ # @param [String] id the service ID of the authenticator to enable
29
+ def authenticator_enable authenticator, id, account: Conjur.configuration.account
30
+ url_for(:authenticator, account, authenticator, id, credentials).patch(enabled: true)
31
+ end
32
+
33
+ # Disables an authenticator in Conjur.
34
+ #
35
+ # @param [String] authenticator the authenticator type to disable (e.g. authn-k8s)
36
+ # @param [String] id the service ID of the authenticator to disable
37
+ def authenticator_disable authenticator, id, account: Conjur.configuration.account
38
+ url_for(:authenticator, account, authenticator, id, credentials).patch(enabled: false)
39
+ end
40
+
41
+ # @!endgroup
42
+ end
43
+ end
@@ -0,0 +1,144 @@
1
+ #
2
+ # Copyright 2013-2017 Conjur Inc
3
+ #
4
+ # Permission is hereby granted, free of charge, to any person obtaining a copy of
5
+ # this software and associated documentation files (the "Software"), to deal in
6
+ # the Software without restriction, including without limitation the rights to
7
+ # use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
8
+ # the Software, and to permit persons to whom the Software is furnished to do so,
9
+ # subject to the following conditions:
10
+ #
11
+ # The above copyright notice and this permission notice shall be included in all
12
+ # copies or substantial portions of the Software.
13
+ #
14
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
16
+ # FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
17
+ # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
18
+ # IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
19
+ # CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
20
+ #
21
+ require 'conjur/user'
22
+
23
+ module Conjur
24
+ class API
25
+ def whoami
26
+ JSON.parse(url_for(:whoami, credentials).get)
27
+ end
28
+
29
+ class << self
30
+ #@!group Authentication
31
+
32
+ # Exchanges a username and a password for an api key. The api key
33
+ # is preferable for storage and use in code, as it can be rotated and has far greater entropy than
34
+ # a user memorizable password.
35
+ #
36
+ # * Note that this method works only for {Conjur::User}s. While
37
+ # {Conjur::Host}s are roles, they do not have passwords.
38
+ # * If you pass an api key to this method instead of a password, it will verify and return the API key.
39
+ # * This method uses HTTP Basic Authentication to send the credentials.
40
+ #
41
+ # @example
42
+ # bob_api_key = Conjur::API.login('bob', 'bob_password')
43
+ # bob_api_key == Conjur::API.login('bob', bob_api_key) # => true
44
+ #
45
+ # @param [String] username The `username` or `login` for the
46
+ # {http://developer.conjur.net/reference/services/directory/user Conjur User}.
47
+ # @param [String] password The `password` or `api key` to authenticate with.
48
+ # @param [String] account The organization account.
49
+ # @return [String] the API key.
50
+ def login username, password, account: Conjur.configuration.account
51
+ if Conjur.log
52
+ Conjur.log << "Logging in #{username} to account #{account} via Basic authentication\n"
53
+ end
54
+ url_for(:authn_login, account, username, password).get
55
+ end
56
+
57
+ # Authenticates using a third party authenticator like authn-oidc. It will return an
58
+ # access token to be used to authenticate further API calls.
59
+ #
60
+ # @param [String] authenticator
61
+ # @param [String] service_id
62
+ # @param [String] account The organization account.
63
+ # @param [Hash] params Additional params to send to authenticator
64
+ # @return [String] A JSON formatted authentication token.
65
+ def authenticator_authenticate authenticator, service_id, account: Conjur.configuration.account, options: {}
66
+ if Conjur.log
67
+ Conjur.log << "Authenticating to account #{account} using #{authenticator}/#{service_id}\n"
68
+ end
69
+ JSON.parse url_for(:authenticator_authenticate, account, service_id, authenticator, options).get
70
+ end
71
+
72
+ # Exchanges Conjur the API key (refresh token) for an access token. The access token can
73
+ # then be used to authenticate further API calls.
74
+ #
75
+ # @param [String] username The username or host id for which we want a token
76
+ # @param [String] api_key The api key
77
+ # @param [String] account The organization account.
78
+ # @return [String] A JSON formatted authentication token.
79
+ def authenticate username, api_key, account: Conjur.configuration.account
80
+ account ||= Conjur.configuration.account
81
+ if Conjur.log
82
+ Conjur.log << "Authenticating #{username} to account #{account}\n"
83
+ end
84
+ JSON.parse url_for(:authn_authenticate, account, username).post(api_key, content_type: 'text/plain')
85
+ end
86
+
87
+ # Obtains an access token from the +authn_local+ service. The access token can
88
+ # then be used to authenticate further API calls.
89
+ #
90
+ # @param [String] username The username or host id for which we want a token
91
+ # @param [String] account The organization account.
92
+ # @return [String] A JSON formatted authentication token.
93
+ def authenticate_local username, account: Conjur.configuration.account, expiration: nil, cidr: nil
94
+ account ||= Conjur.configuration.account
95
+ if Conjur.log
96
+ Conjur.log << "Authenticating #{username} to account #{account} using authn_local\n"
97
+ end
98
+
99
+ require 'json'
100
+ require 'socket'
101
+ message = url_for(:authn_authenticate_local, username, account, expiration, cidr)
102
+ JSON.parse(UNIXSocket.open(Conjur.configuration.authn_local_socket) {|s| s.puts message; s.gets })
103
+ end
104
+
105
+ # Change a user's password. To do this, you must have the user's current password. This does not change or rotate
106
+ # api keys. However, you *can* use the user's api key as the *current* password, if the user was not created
107
+ # with a password.
108
+ #
109
+ # @param [String] username the name of the user whose password we want to change.
110
+ # @param [String] password the user's *current* password *or* api key.
111
+ # @param [String] new_password the new password for the user.
112
+ # @param [String] account The organization account.
113
+ # @return [void]
114
+ def update_password username, password, new_password, account: Conjur.configuration.account
115
+ if Conjur.log
116
+ Conjur.log << "Updating password for #{username} in account #{account}\n"
117
+ end
118
+ url_for(:authn_update_password, account, username, password).put new_password
119
+ end
120
+
121
+ #@!endgroup
122
+
123
+ #@!group Password and API key management
124
+
125
+ # Rotate the currently authenticated user or host API key by generating and returning a new one.
126
+ # The old API key is no longer valid after calling this method. You must have the current
127
+ # API key or password to perform this operation. This method *does not* affect a user's password.
128
+ #
129
+ # @param [String] username the name of the user or host whose API key we want to change
130
+ # @param [String] password the user's current api key
131
+ # @param [String] account The organization account.
132
+ # @return [String] the new API key
133
+ def rotate_api_key username, password, account: Conjur.configuration.account
134
+ if Conjur.log
135
+ Conjur.log << "Rotating API key for self (#{username} in account #{account})\n"
136
+ end
137
+
138
+ url_for(:authn_rotate_own_api_key, account, username, password).put('').body
139
+ end
140
+
141
+ #@!endgroup
142
+ end
143
+ end
144
+ end
@@ -0,0 +1,71 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Copyright 2013-2018 CyberArk Ltd.
4
+ #
5
+ # Licensed under the Apache License, Version 2.0 (the "License");
6
+ # you may not use this file except in compliance with the License.
7
+ # You may obtain a copy of the License at
8
+ #
9
+ # http://www.apache.org/licenses/LICENSE-2.0
10
+ #
11
+ # Unless required by applicable law or agreed to in writing, software
12
+ # distributed under the License is distributed on an "AS IS" BASIS,
13
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
+ # See the License for the specific language governing permissions and
15
+ # limitations under the License.
16
+
17
+ require 'conjur/host_factory'
18
+
19
+ module Conjur
20
+ class API
21
+ #@!group Host Factory
22
+
23
+ class << self
24
+ # Use a host factory token to create a new host. Unlike most other methods, this
25
+ # method does not require a Conjur access token. The host factory token is the
26
+ # authentication and authorization to create the host.
27
+ #
28
+ # The token must be valid. The host id can be a new host, or an existing host.
29
+ # If the host already exists, the server verifies that its layer memberships
30
+ # match the host factory exactly. Then, its API key is rotated and returned with
31
+ # the response.
32
+ #
33
+ # @param [String] token the host factory token.
34
+ # @param [String] id the id of a new or existing host.
35
+ # @param options [Hash] additional host creation options.
36
+ # @return [Host]
37
+ def host_factory_create_host token, id, options = {}
38
+ token = token.token if token.is_a?(HostFactoryToken)
39
+ response = url_for(:host_factory_create_host, token)
40
+ .post(options.merge(id: id)).body
41
+
42
+ attributes = JSON.parse(response)
43
+ # in v4 'id' is just the identifier
44
+ host_id = attributes['roleid'] || attributes['id']
45
+
46
+ Host.new(host_id, {}).tap do |host|
47
+ host.attributes = attributes
48
+ end
49
+ end
50
+
51
+ # Revokes a host factory token. After revocation, the token can no longer be used to
52
+ # create hosts.
53
+ #
54
+ # @param [Hash] credentials authentication credentials of the current user.
55
+ # @param [String] token the host factory token.
56
+ def revoke_host_factory_token credentials, token
57
+ url_for(:host_factory_revoke_token, credentials, token).delete
58
+ end
59
+ end
60
+
61
+ # Revokes a host factory token. After revocation, the token can no longer be used to
62
+ # create hosts.
63
+ #
64
+ # @param [String] token the host factory token.
65
+ def revoke_host_factory_token token
66
+ self.class.revoke_host_factory_token credentials, token
67
+ end
68
+
69
+ #@!endgroup
70
+ end
71
+ end
@@ -0,0 +1,38 @@
1
+ #
2
+ # Copyright 2013-2018 Conjur Inc
3
+ #
4
+ # Permission is hereby granted, free of charge, to any person obtaining a copy of
5
+ # this software and associated documentation files (the "Software"), to deal in
6
+ # the Software without restriction, including without limitation the rights to
7
+ # use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
8
+ # the Software, and to permit persons to whom the Software is furnished to do so,
9
+ # subject to the following conditions:
10
+ #
11
+ # The above copyright notice and this permission notice shall be included in all
12
+ # copies or substantial portions of the Software.
13
+ #
14
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
16
+ # FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
17
+ # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
18
+ # IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
19
+ # CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
20
+ #
21
+
22
+ module Conjur
23
+ class API
24
+
25
+ # Retrieve the policy for the given LDAP sync
26
+ # configuration. Configurations created through the Conjur UI are
27
+ # named +default+, so the default value of +config_name+ can be
28
+ # used.
29
+ #
30
+ # For details on the use of LDAP sync, see
31
+ # https://developer.conjur.net/reference/services/ldap_sync/ .
32
+ #
33
+ # @param [String] config_name the name of the LDAP sync configuration.
34
+ def ldap_sync_policy config_name: 'default'
35
+ JSON.parse(url_for(:ldap_sync_policy, credentials, config_name).get)
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,56 @@
1
+ #
2
+ # Copyright 2013-2017 Conjur Inc
3
+ #
4
+ # Permission is hereby granted, free of charge, to any person obtaining a copy of
5
+ # this software and associated documentation files (the "Software"), to deal in
6
+ # the Software without restriction, including without limitation the rights to
7
+ # use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
8
+ # the Software, and to permit persons to whom the Software is furnished to do so,
9
+ # subject to the following conditions:
10
+ #
11
+ # The above copyright notice and this permission notice shall be included in all
12
+ # copies or substantial portions of the Software.
13
+ #
14
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
16
+ # FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
17
+ # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
18
+ # IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
19
+ # CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
20
+ #
21
+ require 'conjur/policy_load_result'
22
+ require 'conjur/policy'
23
+
24
+ module Conjur
25
+ class API
26
+ #@!group Policy management
27
+
28
+ # Append only.
29
+ POLICY_METHOD_POST = :post
30
+ # Allow explicit deletion statements, but don't delete implicitly delete data.
31
+ POLICY_METHOD_PATCH = :patch
32
+ # Replace the policy entirely, deleting any existing data that is not declared in the new policy.
33
+ POLICY_METHOD_PUT = :put
34
+
35
+ # Load a policy document into the server.
36
+ #
37
+ # The modes are support for policy loading:
38
+ #
39
+ # * POLICY_METHOD_POST Policy data will be added to the named policy. Deletions are not allowed.
40
+ # * POLICY_METHOD_PATCH Policy data can be added to or deleted from the named policy. Deletions
41
+ # are performed by an explicit `!delete` statement.
42
+ # * POLICY_METHOD_PUT The policy completely replaces the name policy. Policy data which is present
43
+ # in the server, but not present in the new policy definition, is deleted.
44
+ #
45
+ # @param id [String] id of the policy to load.
46
+ # @param policy [String] YAML-formatted policy definition.
47
+ # @param account [String] Conjur organization account
48
+ # @param method [Symbol] Policy load method to use: {POLICY_METHOD_POST} (default), {POLICY_METHOD_PATCH}, or {POLICY_METHOD_PUT}.
49
+ def load_policy id, policy, account: Conjur.configuration.account, method: POLICY_METHOD_POST
50
+ request = url_for(:policies_load_policy, credentials, account, id)
51
+ PolicyLoadResult.new JSON.parse(request.send(method, policy))
52
+ end
53
+
54
+ #@!endgroup
55
+ end
56
+ end
@@ -0,0 +1,53 @@
1
+ #
2
+ # Copyright 2013-2017 Conjur Inc
3
+ #
4
+ # Permission is hereby granted, free of charge, to any person obtaining a copy of
5
+ # this software and associated documentation files (the "Software"), to deal in
6
+ # the Software without restriction, including without limitation the rights to
7
+ # use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
8
+ # the Software, and to permit persons to whom the Software is furnished to do so,
9
+ # subject to the following conditions:
10
+ #
11
+ # The above copyright notice and this permission notice shall be included in all
12
+ # copies or substantial portions of the Software.
13
+ #
14
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
16
+ # FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
17
+ # COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
18
+ # IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
19
+ # CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
20
+ #
21
+
22
+ module Conjur
23
+
24
+ class API
25
+ class << self
26
+ # @!group Public Keys
27
+
28
+ # Fetch *all* public keys for the user. This method returns a newline delimited
29
+ # String for compatibility with the authorized_keys SSH format.
30
+ #
31
+ #
32
+ # If the given user does not exist, an empty String will be returned. This is to prevent attackers from determining whether
33
+ # a user exists.
34
+ #
35
+ # ## Permissions
36
+ # You do not need any special permissions to call this method, since public keys are, well, public.
37
+ #
38
+ #
39
+ # @example
40
+ # puts api.public_keys('jon')
41
+ # # ssh-rsa [big long string] jon@albert
42
+ # # ssh-rsa [big long string] jon@conjurops
43
+ #
44
+ # @param [String] username the *unqualified* Conjur username
45
+ # @return [String] newline delimited public keys
46
+ def public_keys username, account: Conjur.configuration.account
47
+ url_for(:public_keys_for_user, account, username).get
48
+ end
49
+
50
+ #@!endgroup
51
+ end
52
+ end
53
+ end