ansible_spec 0.2.23 → 0.3.2
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 +5 -5
- data/.travis.yml +7 -4
- data/CHANGELOG.md +19 -0
- data/Gemfile +5 -0
- data/README.md +1 -1
- data/ansible_spec.gemspec +2 -1
- data/lib/ansible_spec/load_ansible.rb +106 -9
- data/lib/ansible_spec/version.rb +1 -1
- data/lib/src/spec/spec_helper.rb +5 -4
- data/spec/case/get_variable/empty_group/group_vars/group_a.yml +2 -0
- data/spec/case/get_variable/empty_group/group_vars/group_b.yml +2 -0
- data/spec/case/get_variable/empty_group/hosts +3 -0
- data/spec/case/get_variable/empty_group/site.yml +9 -0
- data/spec/case/get_variable/group_each_vars_parent_child/group_vars/all.yml +6 -0
- data/spec/case/get_variable/group_each_vars_parent_child/group_vars/group1/vars +4 -0
- data/spec/case/get_variable/group_each_vars_parent_child/group_vars/group2/vars +4 -0
- data/spec/case/get_variable/group_each_vars_parent_child/group_vars/parentgroup/vars +5 -0
- data/spec/case/get_variable/group_each_vars_parent_child/hosts +13 -0
- data/spec/case/get_variable/group_each_vars_parent_child/site.yml +6 -0
- data/spec/case/get_variable/group_each_vars_parent_child/site1.yml +6 -0
- data/spec/case/get_variable/group_each_vars_parent_child/site2.yml +6 -0
- data/spec/case/get_variable/group_each_vars_parent_child/site3.yml +6 -0
- data/spec/case/get_variable/resolve_variables/group_vars/all.yml +24 -0
- data/spec/case/get_variable/resolve_variables/hosts +5 -0
- data/spec/case/get_variable/resolve_variables/site.yml +3 -0
- data/spec/case/load_vars_file/vault_dir/ansible.cfg +2 -0
- data/spec/case/load_vars_file/vault_dir/group_vars/all/vault_file +6 -0
- data/spec/case/load_vars_file/vault_dir/vault-password-file +1 -0
- data/spec/get_variable_spec.rb +239 -25
- data/spec/load_ansible_spec.rb +303 -4
- metadata +80 -29
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
|
-
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: d77ce9fa38453ab6f652cc6c20a79509c722d615790cb49b59ec8e37154aad7b
|
4
|
+
data.tar.gz: 27384622e2d91ad928ee5b37fa061efa3b80af5baad5b887823ec3df7e83dded
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 2591637e35a8fa5fe8f2add17e24d5f32844030d9fd1f268ec4a0e607bb4f2500ef8a75c166c337d20c8e97c8db979dc1bdf317f64f5f93095493699bef37665
|
7
|
+
data.tar.gz: e1124d4328dc3430545f94a87306fc9148f3b91bc5074d84180edac293966115b15794e5ecd142335a2c972415143f7893bf6516d951bfb4b4ffd1f2855d561d
|
data/.travis.yml
CHANGED
@@ -1,12 +1,15 @@
|
|
1
1
|
language: ruby
|
2
|
+
dist: trusty # work at Ubuntu 14.04 for install Ruby 1.9.3
|
2
3
|
sudo: false
|
3
4
|
rvm:
|
4
5
|
- 1.9.3
|
5
6
|
- 2.0.0
|
6
7
|
- 2.1.10
|
7
|
-
- 2.2.
|
8
|
-
- 2.3.
|
9
|
-
- 2.4.
|
10
|
-
- 2.5.
|
8
|
+
- 2.2.10
|
9
|
+
- 2.3.8
|
10
|
+
- 2.4.10
|
11
|
+
- 2.5.8
|
12
|
+
- 2.6.6
|
13
|
+
- 2.7.1
|
11
14
|
script:
|
12
15
|
- rspec spec
|
data/CHANGELOG.md
CHANGED
@@ -1,3 +1,22 @@
|
|
1
|
+
# v0.3.2
|
2
|
+
- Merge [#135 Fix wrong index by empty group](https://github.com/volanja/ansible_spec/pull/135) by [mamiya312](https://github.com/mamiya312)
|
3
|
+
|
4
|
+
# v0.3.1
|
5
|
+
- Fix [#126 no implicit conversion of nil into Array Error when process get_parent](https://github.com/volanja/ansible_spec/issues/126) by [shogos3](https://github.com/shogos3)
|
6
|
+
|
7
|
+
# v0.3
|
8
|
+
- Support Ansible Vault (Run Ruby 2.1.0 and higher.)
|
9
|
+
- Merge [#116 Feature ansible vault](https://github.com/volanja/ansible_spec/pull/116) by [RebelCodeBase](https://github.com/RebelCodeBase)
|
10
|
+
- Merge [#123 skip test at unsupported version ref ansible vault](https://github.com/volanja/ansible_spec/pull/123) by volanja
|
11
|
+
|
12
|
+
And Some Bug Fixed. See [Milestone v0.3](https://github.com/volanja/ansible_spec/milestone/13?closed=1)
|
13
|
+
|
14
|
+
# v0.2.25
|
15
|
+
- Merge [#118 Incorporate group parent child relationships into variable assignment hierarchy](https://github.com/volanja/ansible_spec/pull/118) by [rbramwell](https://github.com/rbramwell)
|
16
|
+
|
17
|
+
# v0.2.24
|
18
|
+
- Merge [#117 Feature resolve variables](https://github.com/volanja/ansible_spec/pull/117) by [RebelCodeBase](https://github.com/RebelCodeBase)
|
19
|
+
|
1
20
|
# v0.2.23
|
2
21
|
- Merge [#115 Support import_playbook](https://github.com/volanja/ansible_spec/pull/115) by [seiji](https://github.com/seiji)
|
3
22
|
- Merge [#113 Make ENV variables override SSH config file options](https://github.com/volanja/ansible_spec/pull/113) by [Jonnymcc](https://github.com/Jonnymcc)
|
data/Gemfile
CHANGED
@@ -13,3 +13,8 @@ if Gem::Version.new(RUBY_VERSION.dup) <= Gem::Version.new('1.9.3')
|
|
13
13
|
# winrm 2.1.1 dropped Ruby 1.9 support.
|
14
14
|
gem 'winrm', '< 2.1.1'
|
15
15
|
end
|
16
|
+
|
17
|
+
if Gem::Version.new(RUBY_VERSION.dup) >= Gem::Version.new('2.1')
|
18
|
+
# Ansible::Vault support Ruby 2.1.0 and higher.
|
19
|
+
gem 'ansible-vault'
|
20
|
+
end
|
data/README.md
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
# ansible_spec
|
2
2
|
|
3
|
-
[](
|
3
|
+
[](https://badge.fury.io/rb/ansible_spec)
|
4
4
|
[](https://travis-ci.org/volanja/ansible_spec)
|
5
5
|
|
6
6
|
This is a Ruby gem that implements an Ansible Config Parser for Serverspec.
|
data/ansible_spec.gemspec
CHANGED
@@ -18,7 +18,7 @@ Gem::Specification.new do |gem|
|
|
18
18
|
gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
|
19
19
|
gem.require_paths = ["lib"]
|
20
20
|
|
21
|
-
gem.add_development_dependency "bundler"
|
21
|
+
gem.add_development_dependency "bundler"
|
22
22
|
gem.add_development_dependency "rake"
|
23
23
|
gem.add_development_dependency "diff-lcs"
|
24
24
|
gem.add_development_dependency "simplecov"
|
@@ -28,5 +28,6 @@ Gem::Specification.new do |gem|
|
|
28
28
|
gem.add_runtime_dependency "oj"
|
29
29
|
gem.add_runtime_dependency "winrm"
|
30
30
|
gem.add_runtime_dependency "inifile"
|
31
|
+
gem.add_runtime_dependency "ansible-vault"
|
31
32
|
|
32
33
|
end
|
@@ -5,12 +5,21 @@ require 'open3'
|
|
5
5
|
require 'yaml'
|
6
6
|
require 'inifile'
|
7
7
|
require 'ansible_spec/vendor/hash'
|
8
|
+
if Gem::Version.new(RUBY_VERSION.dup) >= Gem::Version.new('2.1')
|
9
|
+
require 'ansible/vault'
|
10
|
+
end
|
8
11
|
|
9
12
|
module AnsibleSpec
|
10
13
|
# param: inventory file of Ansible
|
14
|
+
# param: return_type 'groups' or 'groups_parent_child_relationships'
|
11
15
|
# return: Hash {"group" => ["192.168.0.1","192.168.0.2"]}
|
12
16
|
# return: Hash {"group" => [{"name" => "192.168.0.1","uri" => "192.168.0.1", "port" => 22},...]}
|
13
|
-
|
17
|
+
# return: Hash {"pg" => ["server", "databases"]}
|
18
|
+
def self.load_targets(file, return_type = 'groups')
|
19
|
+
if not ['groups', 'groups_parent_child_relationships'].include?(return_type)
|
20
|
+
raise ArgumentError, "Variable return_type must be value 'groups' or 'groups_parent_child_relationships'"
|
21
|
+
end
|
22
|
+
|
14
23
|
if File.executable?(file)
|
15
24
|
return get_dynamic_inventory(file)
|
16
25
|
end
|
@@ -20,7 +29,7 @@ module AnsibleSpec
|
|
20
29
|
hosts = Hash.new
|
21
30
|
hosts.default = Hash.new
|
22
31
|
f.each_line{|line|
|
23
|
-
line = line.
|
32
|
+
line = line.strip
|
24
33
|
# skip
|
25
34
|
next if line.start_with?('#') #comment
|
26
35
|
next if line.empty? == true #null
|
@@ -67,8 +76,12 @@ module AnsibleSpec
|
|
67
76
|
|
68
77
|
# parse children [group:children]
|
69
78
|
search = Regexp.new(":children".to_s)
|
79
|
+
groups_parent_child_relationships = Hash.new
|
70
80
|
groups.keys.each{|k|
|
71
81
|
unless (k =~ search).nil?
|
82
|
+
# get parent child relationships
|
83
|
+
k_parent = k.gsub(search,'')
|
84
|
+
groups_parent_child_relationships["#{k_parent}"] = groups["#{k}"]
|
72
85
|
# get group parent & merge parent
|
73
86
|
groups.merge!(get_parent(groups,search,k))
|
74
87
|
# delete group children
|
@@ -77,7 +90,15 @@ module AnsibleSpec
|
|
77
90
|
end
|
78
91
|
end
|
79
92
|
}
|
80
|
-
|
93
|
+
|
94
|
+
return_value = groups # default
|
95
|
+
if return_type == 'groups'
|
96
|
+
return_value = groups
|
97
|
+
elsif return_type == 'groups_parent_child_relationships'
|
98
|
+
return_value = groups_parent_child_relationships
|
99
|
+
end
|
100
|
+
|
101
|
+
return return_value
|
81
102
|
end
|
82
103
|
|
83
104
|
# param hash {"server"=>["192.168.0.103"], "databases"=>["192.168.0.104"], "pg:children"=>["server", "databases"]}
|
@@ -140,6 +161,7 @@ module AnsibleSpec
|
|
140
161
|
# 初期値
|
141
162
|
host['name'] = line
|
142
163
|
host['port'] = 22
|
164
|
+
host['connection'] = "ssh"
|
143
165
|
if line.include?(":") # 192.168.0.1:22
|
144
166
|
host['uri'] = line.split(":")[0]
|
145
167
|
host['port'] = line.split(":")[1].to_i
|
@@ -347,15 +369,39 @@ module AnsibleSpec
|
|
347
369
|
if File.directory?(vars_file)
|
348
370
|
Dir.glob(File.join(vars_file, '*')).each { |f|
|
349
371
|
vars = load_vars_file(vars, f)
|
350
|
-
|
372
|
+
}
|
351
373
|
else
|
352
|
-
|
353
|
-
|
374
|
+
# you can use Ansible::Vault when use ruby 2.1.0 and higher.
|
375
|
+
# Ansible::Vault support Ruby 2.1.0 and higher.
|
376
|
+
if Gem::Version.new(RUBY_VERSION.dup) >= Gem::Version.new('2.1')
|
377
|
+
if Ansible::Vault.encrypted?(vars_file)
|
378
|
+
yaml = load_encrypted_file(vars_file)
|
379
|
+
else
|
380
|
+
yaml = YAML.load_file(vars_file)
|
381
|
+
end
|
382
|
+
vars = merge_variables(vars, yaml)
|
383
|
+
else
|
384
|
+
# Ruby 1.9 and 2.0
|
385
|
+
yaml = YAML.load_file(vars_file)
|
386
|
+
vars = merge_variables(vars, yaml)
|
387
|
+
end
|
354
388
|
end
|
355
389
|
end
|
356
390
|
return vars
|
357
391
|
end
|
358
392
|
|
393
|
+
# param: variable file
|
394
|
+
# return: be merged hash
|
395
|
+
def self.load_encrypted_file(vars_file)
|
396
|
+
cfg = AnsibleSpec::AnsibleCfg.new
|
397
|
+
vault_password_file = cfg.get('defaults', 'vault_password_file')
|
398
|
+
if vault_password_file
|
399
|
+
vault_password = File.open(vault_password_file).read.chomp
|
400
|
+
yaml = YAML.load(Ansible::Vault.read(path: vars_file, password: vault_password))
|
401
|
+
end
|
402
|
+
return yaml
|
403
|
+
end
|
404
|
+
|
359
405
|
# param: target hash
|
360
406
|
# param: be merged hash
|
361
407
|
def self.merge_variables(vars, hash)
|
@@ -431,9 +477,46 @@ module AnsibleSpec
|
|
431
477
|
target_host.keys[0]
|
432
478
|
end
|
433
479
|
|
480
|
+
# query replace jinja2 templates with target values
|
481
|
+
# param: hash (cf. result self.get_variables)
|
482
|
+
# param: number of iterations if found_template
|
483
|
+
# return: hash
|
484
|
+
def self.resolve_variables(vars, max_level=100)
|
485
|
+
vars_yaml = vars.to_yaml
|
486
|
+
level = 0
|
487
|
+
begin
|
488
|
+
found_template = false
|
489
|
+
level += 1
|
490
|
+
|
491
|
+
# query replace jinja2 templates in yaml
|
492
|
+
# replace in-place (gsub!)
|
493
|
+
# use non-greedy regex (.*?)
|
494
|
+
vars_yaml.gsub!(/{{.*?}}/) do |template|
|
495
|
+
|
496
|
+
# grab target variable
|
497
|
+
# ignore whitespaces (\s*)
|
498
|
+
# use non-greedy regex (.*?)
|
499
|
+
target = template.gsub(/{{\s*(.*?)\s*}}/, '\1')
|
500
|
+
|
501
|
+
# lookup value of target variable
|
502
|
+
value = vars[target]
|
503
|
+
|
504
|
+
# return lookup value if it exists
|
505
|
+
# or leave template alone
|
506
|
+
if value.nil?
|
507
|
+
template
|
508
|
+
else
|
509
|
+
found_template = true
|
510
|
+
value
|
511
|
+
end
|
512
|
+
end
|
513
|
+
end while found_template and level <= max_level
|
514
|
+
return YAML.load(vars_yaml)
|
515
|
+
end
|
516
|
+
|
434
517
|
def self.get_variables(host, group_idx, hosts=nil)
|
435
518
|
vars = {}
|
436
|
-
p = self.get_properties
|
519
|
+
p = self.get_properties.compact.reject{|e| e["hosts"].length == 0}
|
437
520
|
|
438
521
|
# roles default
|
439
522
|
p[group_idx]['roles'].each do |role|
|
@@ -451,7 +534,21 @@ module AnsibleSpec
|
|
451
534
|
|
452
535
|
# each group vars
|
453
536
|
if p[group_idx].has_key?('group')
|
454
|
-
|
537
|
+
# get groups parent child relationships
|
538
|
+
playbook, inventoryfile = load_ansiblespec
|
539
|
+
groups_rels = load_targets(inventoryfile, return_type='groups_parent_child_relationships')
|
540
|
+
# get parental lineage
|
541
|
+
g = p[group_idx]['group']
|
542
|
+
groups_stack = Array.new
|
543
|
+
groups_stack << g
|
544
|
+
groups_rels.keys.each{|k|
|
545
|
+
groups_stack << k if (groups_rels[k].include?(g))
|
546
|
+
}
|
547
|
+
# get vars from parents groups then child group
|
548
|
+
groups_parents_then_child = groups_stack.reverse.flatten
|
549
|
+
groups_parents_then_child.each{|group|
|
550
|
+
vars = load_vars_file(vars ,"#{vars_dirs_path}group_vars/#{group}", true)
|
551
|
+
}
|
455
552
|
end
|
456
553
|
|
457
554
|
# each host vars
|
@@ -479,7 +576,7 @@ module AnsibleSpec
|
|
479
576
|
end
|
480
577
|
end
|
481
578
|
|
482
|
-
return vars
|
579
|
+
return resolve_variables(vars)
|
483
580
|
|
484
581
|
end
|
485
582
|
|
data/lib/ansible_spec/version.rb
CHANGED
data/lib/src/spec/spec_helper.rb
CHANGED
@@ -23,15 +23,16 @@ when 'ssh'
|
|
23
23
|
#
|
24
24
|
set :backend, :ssh
|
25
25
|
|
26
|
+
# Ansible use `BECOME`, But Serverspec use `SUDO`.
|
26
27
|
if ENV['ASK_BECOME_PASSWORD']
|
27
28
|
begin
|
28
29
|
require 'highline/import'
|
29
30
|
rescue LoadError
|
30
31
|
fail "highline is not available. Try installing it."
|
31
32
|
end
|
32
|
-
set :
|
33
|
+
set :sudo_password, ask("Enter become password: ") { |q| q.echo = false }
|
33
34
|
else
|
34
|
-
set :
|
35
|
+
set :sudo_password, ENV['BECOME_PASSWORD']
|
35
36
|
end
|
36
37
|
|
37
38
|
options = Net::SSH::Config.for(host)
|
@@ -48,8 +49,8 @@ when 'ssh'
|
|
48
49
|
set :host, options[:host_name] || host
|
49
50
|
set :ssh_options, options
|
50
51
|
|
51
|
-
# Disable become
|
52
|
-
# set :
|
52
|
+
# Disable become (Serverspec use sudo)
|
53
|
+
# set :disable_sudo, true
|
53
54
|
|
54
55
|
|
55
56
|
# Set environment variables
|
@@ -0,0 +1,24 @@
|
|
1
|
+
---
|
2
|
+
var_nested_one_1: 'val_nested_one'
|
3
|
+
var_nested_one_2: "{{ var_nested_one_1 }}"
|
4
|
+
|
5
|
+
var_nested_two_1: 'val_nested_two'
|
6
|
+
var_nested_two_2: "{{ var_nested_two_1 }}"
|
7
|
+
var_nested_two_3: "{{ var_nested_two_2 }}"
|
8
|
+
|
9
|
+
var_nested_hash_1: 'val_hash'
|
10
|
+
var_nested_hash_2:
|
11
|
+
key: "{{ var_nested_hash_1 }}"
|
12
|
+
|
13
|
+
var_nested_array_1: 'val_array'
|
14
|
+
var_nested_array_2:
|
15
|
+
- "{{ var_nested_array_1 }}"
|
16
|
+
|
17
|
+
var_nested_array_hash_1: 'val_array_hash'
|
18
|
+
var_nested_array_hash_2:
|
19
|
+
- key: "{{ var_nested_array_hash_1 }}"
|
20
|
+
|
21
|
+
var_nested_whitespace_1: val_nested_whitespace
|
22
|
+
var_nested_whitespace_2: "{{var_nested_whitespace_1 }}"
|
23
|
+
|
24
|
+
var_missingtarget_2: "{{ var_missingtarget_1 }}"
|