conjur-api 5.0.0 → 5.1.0
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.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/CHANGELOG.md +6 -0
- data/Dockerfile +2 -0
- data/Jenkinsfile +2 -8
- data/README.md +85 -2
- data/Rakefile +9 -3
- data/ci/configure_v4.sh +12 -0
- data/ci/configure_v5.sh +14 -0
- data/conjur-api.gemspec +1 -1
- data/docker-compose.yml +47 -12
- data/example/demo_v4.rb +49 -0
- data/example/demo_v5.rb +57 -0
- data/features/authn_local.feature +32 -0
- data/features/support/env.rb +1 -0
- data/features/variable_value.feature +6 -13
- data/features_v4/authn_local.feature +27 -0
- data/features_v4/exists.feature +29 -0
- data/features_v4/host.feature +18 -0
- data/features_v4/host_factory_token.feature +49 -0
- data/features_v4/members.feature +39 -0
- data/features_v4/permitted.feature +15 -0
- data/features_v4/permitted_roles.feature +8 -0
- data/features_v4/resource_fields.feature +47 -0
- data/features_v4/rotate_api_key.feature +13 -0
- data/features_v4/step_definitions/api_steps.rb +17 -0
- data/features_v4/step_definitions/result_steps.rb +3 -0
- data/features_v4/support/env.rb +23 -0
- data/features_v4/support/policy.yml +34 -0
- data/features_v4/support/world.rb +12 -0
- data/features_v4/variable_fields.feature +11 -0
- data/features_v4/variable_value.feature +54 -0
- data/lib/conjur-api/version.rb +1 -1
- data/lib/conjur/acts_as_resource.rb +3 -17
- data/lib/conjur/acts_as_role.rb +2 -4
- data/lib/conjur/acts_as_user.rb +1 -2
- data/lib/conjur/api.rb +1 -0
- data/lib/conjur/api/authn.rb +22 -8
- data/lib/conjur/api/host_factories.rb +2 -5
- data/lib/conjur/api/policies.rb +1 -1
- data/lib/conjur/api/pubkeys.rb +1 -9
- data/lib/conjur/api/resources.rb +1 -6
- data/lib/conjur/api/router/v4.rb +149 -0
- data/lib/conjur/api/router/v5.rb +150 -0
- data/lib/conjur/api/variables.rb +2 -8
- data/lib/conjur/base.rb +61 -18
- data/lib/conjur/base_object.rb +1 -6
- data/lib/conjur/configuration.rb +26 -0
- data/lib/conjur/group.rb +7 -1
- data/lib/conjur/has_attributes.rb +11 -3
- data/lib/conjur/host_factory.rb +1 -1
- data/lib/conjur/routing.rb +29 -0
- data/lib/conjur/user.rb +7 -1
- data/lib/conjur/variable.rb +26 -11
- data/spec/has_attributes_spec.rb +4 -2
- data/test.sh +25 -11
- metadata +33 -12
- data/ci/wait_for_server.sh +0 -10
- data/dev/docker-compose.yml +0 -23
- data/dev/empty.yml +0 -2
- data/dev/start.sh +0 -15
- data/dev/stop.sh +0 -6
data/features/support/env.rb
CHANGED
@@ -7,6 +7,7 @@ require 'conjur/api'
|
|
7
7
|
|
8
8
|
Conjur.configuration.appliance_url = ENV['CONJUR_APPLIANCE_URL'] || 'http://localhost/api/v6'
|
9
9
|
Conjur.configuration.account = ENV['CONJUR_ACCOUNT'] || 'cucumber'
|
10
|
+
Conjur.configuration.authn_local_socket = "/run/authn-local-5/.socket"
|
10
11
|
|
11
12
|
$username = ENV['CONJUR_AUTHN_LOGIN'] || 'admin'
|
12
13
|
$password = ENV['CONJUR_AUTHN_API_KEY'] || 'secret'
|
@@ -12,26 +12,19 @@ Feature: Work with Variable values.
|
|
12
12
|
@variable_2 = $conjur.resource("cucumber:variable:#{@variable_id}-2")
|
13
13
|
"""
|
14
14
|
|
15
|
-
Scenario: Initially the variable has no values
|
16
|
-
When I run the code:
|
17
|
-
"""
|
18
|
-
@variable.version_count
|
19
|
-
"""
|
20
|
-
Then the result should be "0"
|
21
|
-
|
22
15
|
Scenario: Add a value, retrieve the variable metadata and the value.
|
23
|
-
|
16
|
+
When I run the code:
|
24
17
|
"""
|
18
|
+
@initial_count = @variable.version_count
|
25
19
|
@variable.add_value 'value-0'
|
26
20
|
"""
|
27
|
-
|
21
|
+
And I run the code:
|
28
22
|
"""
|
29
|
-
@variable.version_count
|
23
|
+
expect(@variable.version_count).to eq(@initial_count + 1)
|
30
24
|
"""
|
31
|
-
Then the result should be "1"
|
32
25
|
And I run the code:
|
33
26
|
"""
|
34
|
-
@variable.value
|
27
|
+
@variable.value(@variable.version_count)
|
35
28
|
"""
|
36
29
|
Then the result should be "value-0"
|
37
30
|
|
@@ -44,7 +37,7 @@ Feature: Work with Variable values.
|
|
44
37
|
"""
|
45
38
|
When I run the code:
|
46
39
|
"""
|
47
|
-
@variable.value(
|
40
|
+
@variable.value(@variable.version_count - 2)
|
48
41
|
"""
|
49
42
|
Then the result should be "value-0"
|
50
43
|
|
@@ -0,0 +1,27 @@
|
|
1
|
+
Feature: When co-located with the Conjur server, the API can use the authn-local service to authenticate.
|
2
|
+
|
3
|
+
Scenario: authn-local can be used to obtain an access token.
|
4
|
+
When I run the code:
|
5
|
+
"""
|
6
|
+
Conjur::API.authenticate_local "alice"
|
7
|
+
"""
|
8
|
+
Then the JSON should have "data"
|
9
|
+
|
10
|
+
Scenario: Conjur API supports construction from authn-local.
|
11
|
+
When I run the code:
|
12
|
+
"""
|
13
|
+
@api = Conjur::API.new_from_authn_local "alice"
|
14
|
+
@api.token
|
15
|
+
"""
|
16
|
+
Then the JSON should have "data"
|
17
|
+
|
18
|
+
Scenario: Conjur API will automatically refresh the token.
|
19
|
+
When I run the code:
|
20
|
+
"""
|
21
|
+
@api = Conjur::API.new_from_authn_local "alice"
|
22
|
+
@api.token
|
23
|
+
@api.force_token_refresh
|
24
|
+
@api.token
|
25
|
+
"""
|
26
|
+
Then the JSON should have "data"
|
27
|
+
And the JSON at "data" should be "alice"
|
@@ -0,0 +1,29 @@
|
|
1
|
+
Feature: Check if an object exists.
|
2
|
+
|
3
|
+
Scenario: A created group resource exists
|
4
|
+
When I run the code:
|
5
|
+
"""
|
6
|
+
$conjur.resource('cucumber:group:developers').exists?
|
7
|
+
"""
|
8
|
+
Then the result should be "true"
|
9
|
+
|
10
|
+
Scenario: An un-created resource doesn't exist
|
11
|
+
When I run the code:
|
12
|
+
"""
|
13
|
+
$conjur.resource('cucumber:food:bacon').exists?
|
14
|
+
"""
|
15
|
+
Then the result should be "false"
|
16
|
+
|
17
|
+
Scenario: A created group role exists
|
18
|
+
When I run the code:
|
19
|
+
"""
|
20
|
+
$conjur.role('cucumber:group:developers').exists?
|
21
|
+
"""
|
22
|
+
Then the result should be "true"
|
23
|
+
|
24
|
+
Scenario: An un-created role doesn't exist
|
25
|
+
When I run the code:
|
26
|
+
"""
|
27
|
+
$conjur.role('cucumber:food:bacon').exists?
|
28
|
+
"""
|
29
|
+
Then the result should be "false"
|
@@ -0,0 +1,18 @@
|
|
1
|
+
Feature: Display Host object fields.
|
2
|
+
|
3
|
+
Background:
|
4
|
+
Given a new host
|
5
|
+
|
6
|
+
Scenario: API key of a newly created host is available and valid.
|
7
|
+
Then I run the code:
|
8
|
+
"""
|
9
|
+
expect(@host.exists?).to be(true)
|
10
|
+
expect(@host.api_key).to be
|
11
|
+
"""
|
12
|
+
|
13
|
+
Scenario: API key of a a host can be rotated.
|
14
|
+
Then I run the code:
|
15
|
+
"""
|
16
|
+
api_key = @host.rotate_api_key
|
17
|
+
Conjur::API.new_from_key("host/#{@host.id.identifier}", api_key).token
|
18
|
+
"""
|
@@ -0,0 +1,49 @@
|
|
1
|
+
Feature: Working with host factory tokens.
|
2
|
+
|
3
|
+
Background:
|
4
|
+
Given I run the code:
|
5
|
+
"""
|
6
|
+
@expiration = (DateTime.now + 1.hour).change(sec: 0)
|
7
|
+
"""
|
8
|
+
|
9
|
+
|
10
|
+
Scenario: Create a new host factory token.
|
11
|
+
When I run the code:
|
12
|
+
"""
|
13
|
+
@token = $host_factory.create_token(@expiration)
|
14
|
+
"""
|
15
|
+
Then I can run the code:
|
16
|
+
"""
|
17
|
+
expect(@token).to be_instance_of(Conjur::HostFactoryToken)
|
18
|
+
expect(@token.token).to be_instance_of(String)
|
19
|
+
expiration = @token.expiration
|
20
|
+
expiration = expiration.change(sec: 0)
|
21
|
+
expect(expiration).to eq(@expiration)
|
22
|
+
"""
|
23
|
+
|
24
|
+
Scenario: Create multiple new host factory tokens.
|
25
|
+
When I run the code:
|
26
|
+
"""
|
27
|
+
$host_factory.create_tokens @expiration, count: 2
|
28
|
+
"""
|
29
|
+
Then the JSON should have 2 items
|
30
|
+
|
31
|
+
Scenario: Revoke a host factory token using the token object.
|
32
|
+
When I run the code:
|
33
|
+
"""
|
34
|
+
@token = $host_factory.create_token @expiration
|
35
|
+
"""
|
36
|
+
Then I can run the code:
|
37
|
+
"""
|
38
|
+
@token.revoke
|
39
|
+
"""
|
40
|
+
|
41
|
+
Scenario: Revoke a host factory token using the API.
|
42
|
+
When I run the code:
|
43
|
+
"""
|
44
|
+
@token = $host_factory.create_token @expiration
|
45
|
+
"""
|
46
|
+
Then I can run the code:
|
47
|
+
"""
|
48
|
+
$conjur.revoke_host_factory_token @token.token
|
49
|
+
"""
|
@@ -0,0 +1,39 @@
|
|
1
|
+
Feature: Display role members and memberships.
|
2
|
+
|
3
|
+
Scenario: Show a role's members.
|
4
|
+
When I run the code:
|
5
|
+
"""
|
6
|
+
$conjur.role('cucumber:group:everyone').members.map(&:as_json)
|
7
|
+
"""
|
8
|
+
Then the JSON should be:
|
9
|
+
"""
|
10
|
+
[
|
11
|
+
{
|
12
|
+
"admin_option": false,
|
13
|
+
"member": "cucumber:group:developers",
|
14
|
+
"role": "cucumber:group:everyone"
|
15
|
+
},
|
16
|
+
{
|
17
|
+
"admin_option": true,
|
18
|
+
"member": "cucumber:group:security_admin",
|
19
|
+
"role": "cucumber:group:everyone"
|
20
|
+
}
|
21
|
+
]
|
22
|
+
"""
|
23
|
+
|
24
|
+
Scenario: Show a role's memberships.
|
25
|
+
When I run the code:
|
26
|
+
"""
|
27
|
+
$conjur.role('cucumber:group:developers').memberships.map(&:as_json)
|
28
|
+
"""
|
29
|
+
Then the JSON should be:
|
30
|
+
"""
|
31
|
+
[
|
32
|
+
{
|
33
|
+
"id": "cucumber:group:developers"
|
34
|
+
},
|
35
|
+
{
|
36
|
+
"id": "cucumber:group:everyone"
|
37
|
+
}
|
38
|
+
]
|
39
|
+
"""
|
@@ -0,0 +1,15 @@
|
|
1
|
+
Feature: Check if a role has permission on a resource.
|
2
|
+
|
3
|
+
Scenario: Check if the current user has the privilege.
|
4
|
+
When I run the code:
|
5
|
+
"""
|
6
|
+
$conjur.resource('cucumber:variable:db-password').permitted? 'execute'
|
7
|
+
"""
|
8
|
+
Then the result should be "true"
|
9
|
+
|
10
|
+
Scenario: Check if a different user has the privilege.
|
11
|
+
When I run the code:
|
12
|
+
"""
|
13
|
+
$conjur.resource('cucumber:variable:db-password').permitted? 'execute', role: "cucumber:user:bob"
|
14
|
+
"""
|
15
|
+
Then the result should be "false"
|
@@ -0,0 +1,8 @@
|
|
1
|
+
Feature: Enumerate roles which have a permission on a resource.
|
2
|
+
|
3
|
+
Scenario: Permitted roles can be enumerated.
|
4
|
+
When I run the code:
|
5
|
+
"""
|
6
|
+
$conjur.resource('cucumber:variable:db-password').permitted_roles 'execute'
|
7
|
+
"""
|
8
|
+
Then the JSON should include "cucumber:layer:myapp"
|
@@ -0,0 +1,47 @@
|
|
1
|
+
Feature: Display basic resource fields.
|
2
|
+
|
3
|
+
Scenario: Group exposes id, kind, identifier, and gidnumber.
|
4
|
+
When I run the code:
|
5
|
+
"""
|
6
|
+
resource = $conjur.resource('cucumber:group:developers')
|
7
|
+
[ resource.id, resource.account, resource.kind, resource.identifier, resource.gidnumber ]
|
8
|
+
"""
|
9
|
+
Then the JSON should be:
|
10
|
+
"""
|
11
|
+
[
|
12
|
+
"cucumber:group:developers",
|
13
|
+
"cucumber",
|
14
|
+
"group",
|
15
|
+
"developers",
|
16
|
+
2000
|
17
|
+
]
|
18
|
+
"""
|
19
|
+
|
20
|
+
Scenario: User exposes id, kind, identifier, and uidnumber.
|
21
|
+
When I run the code:
|
22
|
+
"""
|
23
|
+
resource = $conjur.resource('cucumber:user:alice')
|
24
|
+
[ resource.id, resource.account, resource.kind, resource.identifier, resource.uidnumber ]
|
25
|
+
"""
|
26
|
+
Then the JSON should be:
|
27
|
+
"""
|
28
|
+
[
|
29
|
+
"cucumber:user:alice",
|
30
|
+
"cucumber",
|
31
|
+
"user",
|
32
|
+
"alice",
|
33
|
+
2000
|
34
|
+
]
|
35
|
+
"""
|
36
|
+
|
37
|
+
Scenario: Resource#owner is the owner object
|
38
|
+
When I run the code:
|
39
|
+
"""
|
40
|
+
$conjur.resource('cucumber:group:developers').owner.id
|
41
|
+
"""
|
42
|
+
Then the result should be "cucumber:group:security_admin"
|
43
|
+
And I run the code:
|
44
|
+
"""
|
45
|
+
$conjur.resource('cucumber:group:developers').class
|
46
|
+
"""
|
47
|
+
Then the result should be "Conjur::Group"
|
@@ -0,0 +1,13 @@
|
|
1
|
+
Feature: Rotate the API key.
|
2
|
+
|
3
|
+
Scenario: Logged-in user can rotate the API key.
|
4
|
+
When I run the code:
|
5
|
+
"""
|
6
|
+
$conjur.role('cucumber:user:alice').rotate_api_key
|
7
|
+
"""
|
8
|
+
Then I can run the code:
|
9
|
+
"""
|
10
|
+
@api_key = @result.strip
|
11
|
+
@conjur = Conjur::API.new_from_key 'alice', @api_key
|
12
|
+
@conjur.token
|
13
|
+
"""
|
@@ -0,0 +1,17 @@
|
|
1
|
+
Given(/^a new host$/) do
|
2
|
+
@host_id = "app-#{random_hex}"
|
3
|
+
host = Conjur::API.host_factory_create_host($token, @host_id)
|
4
|
+
@host_api_key = host.api_key
|
5
|
+
expect(@host_api_key).to be
|
6
|
+
|
7
|
+
@host = $conjur.resource("cucumber:host:#{@host_id}")
|
8
|
+
@host.attributes['api_key'] = @host_api_key
|
9
|
+
end
|
10
|
+
|
11
|
+
When(/^I(?: can)? run the code:$/) do |code|
|
12
|
+
@result = eval(code).tap do |result|
|
13
|
+
if ENV['DEBUG']
|
14
|
+
puts result
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
require 'simplecov'
|
2
|
+
|
3
|
+
SimpleCov.start
|
4
|
+
|
5
|
+
require 'json_spec/cucumber'
|
6
|
+
require 'conjur/api'
|
7
|
+
|
8
|
+
Conjur.configuration.appliance_url = ENV['CONJUR_APPLIANCE_URL'] || 'https://conjur_4/api'
|
9
|
+
Conjur.configuration.account = ENV['CONJUR_ACCOUNT'] || 'cucumber'
|
10
|
+
Conjur.configuration.cert_file = "./tmp/conjur.pem"
|
11
|
+
Conjur.configuration.authn_local_socket = "/run/authn-local-4/.socket"
|
12
|
+
Conjur.configuration.version = 4
|
13
|
+
|
14
|
+
Conjur.configuration.apply_cert_config!
|
15
|
+
|
16
|
+
$username = ENV['CONJUR_AUTHN_LOGIN'] || 'admin'
|
17
|
+
$password = ENV['CONJUR_AUTHN_API_KEY'] || 'secret'
|
18
|
+
|
19
|
+
$api_key = Conjur::API.login $username, $password
|
20
|
+
$conjur = Conjur::API.new_from_key $username, $api_key
|
21
|
+
|
22
|
+
$host_factory = $conjur.resource('cucumber:host_factory:myapp')
|
23
|
+
$token = $host_factory.create_token(Time.now + 1.hour)
|
@@ -0,0 +1,34 @@
|
|
1
|
+
- !user
|
2
|
+
id: alice
|
3
|
+
uidnumber: 2000
|
4
|
+
|
5
|
+
- !group
|
6
|
+
id: developers
|
7
|
+
gidnumber: 2000
|
8
|
+
|
9
|
+
- !group everyone
|
10
|
+
|
11
|
+
- !grant
|
12
|
+
role: !group everyone
|
13
|
+
member: !group developers
|
14
|
+
|
15
|
+
- !variable db-password
|
16
|
+
|
17
|
+
- !variable ssh-key
|
18
|
+
|
19
|
+
- !variable
|
20
|
+
id: ssl-certificate
|
21
|
+
kind: SSL certificate
|
22
|
+
mime_type: application/x-pem-file
|
23
|
+
|
24
|
+
- !layer myapp
|
25
|
+
|
26
|
+
- !host-factory
|
27
|
+
id: myapp
|
28
|
+
layers: [ !layer myapp ]
|
29
|
+
|
30
|
+
- !permit
|
31
|
+
role: !layer myapp
|
32
|
+
privileges: [ read, execute ]
|
33
|
+
resources:
|
34
|
+
- !variable db-password
|
@@ -0,0 +1,11 @@
|
|
1
|
+
Feature: Display Variable fields.
|
2
|
+
|
3
|
+
Background:
|
4
|
+
When I run the code:
|
5
|
+
"""
|
6
|
+
$conjur.resource('cucumber:variable:ssl-certificate')
|
7
|
+
"""
|
8
|
+
|
9
|
+
Scenario: Display MIME type and kind
|
10
|
+
Then the JSON at "mime_type" should be "application/x-pem-file"
|
11
|
+
And the JSON at "kind" should be "SSL certificate"
|
@@ -0,0 +1,54 @@
|
|
1
|
+
Feature: Work with Variable values.
|
2
|
+
Background:
|
3
|
+
Given I run the code:
|
4
|
+
"""
|
5
|
+
@variable = $conjur.resource("cucumber:variable:db-password")
|
6
|
+
@variable_2 = $conjur.resource("cucumber:variable:ssh-key")
|
7
|
+
"""
|
8
|
+
|
9
|
+
Scenario: Add a value, retrieve the variable metadata and the value.
|
10
|
+
Given I run the code:
|
11
|
+
"""
|
12
|
+
@initial_count = @variable.version_count
|
13
|
+
@variable.add_value 'value-0'
|
14
|
+
"""
|
15
|
+
When I run the code:
|
16
|
+
"""
|
17
|
+
expect(@variable.version_count).to eq(@initial_count + 1)
|
18
|
+
"""
|
19
|
+
And I run the code:
|
20
|
+
"""
|
21
|
+
@variable.value
|
22
|
+
"""
|
23
|
+
Then the result should be "value-0"
|
24
|
+
|
25
|
+
Scenario: Retrieve a historical value.
|
26
|
+
Given I run the code:
|
27
|
+
"""
|
28
|
+
@variable.add_value 'value-0'
|
29
|
+
@variable.add_value 'value-1'
|
30
|
+
@variable.add_value 'value-2'
|
31
|
+
"""
|
32
|
+
When I run the code:
|
33
|
+
"""
|
34
|
+
@variable.value(@variable.version_count - 2)
|
35
|
+
"""
|
36
|
+
Then the result should be "value-0"
|
37
|
+
|
38
|
+
Scenario: Retrieve multiple values in a batch
|
39
|
+
Given I run the code:
|
40
|
+
"""
|
41
|
+
@variable.add_value 'value-0'
|
42
|
+
@variable_2.add_value 'value-2'
|
43
|
+
"""
|
44
|
+
When I run the code:
|
45
|
+
"""
|
46
|
+
$conjur.variable_values([ @variable, @variable_2 ].map(&:id))
|
47
|
+
"""
|
48
|
+
Then the JSON should be:
|
49
|
+
"""
|
50
|
+
{
|
51
|
+
"db-password": "value-0",
|
52
|
+
"ssh-key": "value-2"
|
53
|
+
}
|
54
|
+
"""
|