train 0.12.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.rubocop.yml +71 -0
- data/CHANGELOG.md +308 -0
- data/Gemfile +30 -0
- data/LICENSE +201 -0
- data/README.md +156 -0
- data/Rakefile +148 -0
- data/lib/train.rb +117 -0
- data/lib/train/errors.rb +23 -0
- data/lib/train/extras.rb +17 -0
- data/lib/train/extras/command_wrapper.rb +148 -0
- data/lib/train/extras/file_aix.rb +20 -0
- data/lib/train/extras/file_common.rb +161 -0
- data/lib/train/extras/file_linux.rb +16 -0
- data/lib/train/extras/file_unix.rb +79 -0
- data/lib/train/extras/file_windows.rb +91 -0
- data/lib/train/extras/linux_lsb.rb +60 -0
- data/lib/train/extras/os_common.rb +136 -0
- data/lib/train/extras/os_detect_darwin.rb +32 -0
- data/lib/train/extras/os_detect_linux.rb +148 -0
- data/lib/train/extras/os_detect_unix.rb +99 -0
- data/lib/train/extras/os_detect_windows.rb +57 -0
- data/lib/train/extras/stat.rb +133 -0
- data/lib/train/options.rb +80 -0
- data/lib/train/plugins.rb +40 -0
- data/lib/train/plugins/base_connection.rb +86 -0
- data/lib/train/plugins/transport.rb +49 -0
- data/lib/train/transports/docker.rb +103 -0
- data/lib/train/transports/local.rb +52 -0
- data/lib/train/transports/local_file.rb +90 -0
- data/lib/train/transports/local_os.rb +51 -0
- data/lib/train/transports/mock.rb +147 -0
- data/lib/train/transports/ssh.rb +163 -0
- data/lib/train/transports/ssh_connection.rb +225 -0
- data/lib/train/transports/winrm.rb +184 -0
- data/lib/train/transports/winrm_connection.rb +194 -0
- data/lib/train/version.rb +7 -0
- data/test/integration/.kitchen.yml +43 -0
- data/test/integration/Berksfile +3 -0
- data/test/integration/bootstrap.sh +17 -0
- data/test/integration/chefignore +1 -0
- data/test/integration/cookbooks/test/metadata.rb +1 -0
- data/test/integration/cookbooks/test/recipes/default.rb +100 -0
- data/test/integration/cookbooks/test/recipes/prep_files.rb +47 -0
- data/test/integration/docker_run.rb +153 -0
- data/test/integration/docker_test.rb +24 -0
- data/test/integration/docker_test_container.rb +24 -0
- data/test/integration/helper.rb +61 -0
- data/test/integration/sudo/customcommand.rb +15 -0
- data/test/integration/sudo/nopasswd.rb +16 -0
- data/test/integration/sudo/passwd.rb +21 -0
- data/test/integration/sudo/reqtty.rb +17 -0
- data/test/integration/sudo/run_as.rb +12 -0
- data/test/integration/test-travis-1.yaml +13 -0
- data/test/integration/test-travis-2.yaml +13 -0
- data/test/integration/test_local.rb +19 -0
- data/test/integration/test_ssh.rb +39 -0
- data/test/integration/tests/path_block_device_test.rb +74 -0
- data/test/integration/tests/path_character_device_test.rb +74 -0
- data/test/integration/tests/path_file_test.rb +79 -0
- data/test/integration/tests/path_folder_test.rb +90 -0
- data/test/integration/tests/path_missing_test.rb +77 -0
- data/test/integration/tests/path_pipe_test.rb +78 -0
- data/test/integration/tests/path_symlink_test.rb +95 -0
- data/test/integration/tests/run_command_test.rb +28 -0
- data/test/unit/extras/command_wrapper_test.rb +78 -0
- data/test/unit/extras/file_common_test.rb +180 -0
- data/test/unit/extras/linux_file_test.rb +167 -0
- data/test/unit/extras/os_common_test.rb +269 -0
- data/test/unit/extras/os_detect_linux_test.rb +189 -0
- data/test/unit/extras/os_detect_windows_test.rb +99 -0
- data/test/unit/extras/stat_test.rb +148 -0
- data/test/unit/extras/windows_file_test.rb +44 -0
- data/test/unit/helper.rb +7 -0
- data/test/unit/plugins/connection_test.rb +44 -0
- data/test/unit/plugins/transport_test.rb +111 -0
- data/test/unit/plugins_test.rb +22 -0
- data/test/unit/train_test.rb +156 -0
- data/test/unit/transports/local_file_test.rb +184 -0
- data/test/unit/transports/local_test.rb +87 -0
- data/test/unit/transports/mock_test.rb +87 -0
- data/test/unit/transports/ssh_test.rb +109 -0
- data/test/unit/version_test.rb +8 -0
- data/test/windows/local_test.rb +46 -0
- data/test/windows/winrm_test.rb +52 -0
- data/train.gemspec +38 -0
- metadata +295 -0
@@ -0,0 +1,43 @@
|
|
1
|
+
---
|
2
|
+
driver:
|
3
|
+
name: vagrant
|
4
|
+
|
5
|
+
provisioner:
|
6
|
+
name: chef_solo
|
7
|
+
data_path: ../../.
|
8
|
+
|
9
|
+
platforms:
|
10
|
+
- name: centos-7.1
|
11
|
+
- name: centos-6.7
|
12
|
+
- name: centos-6.7-i386
|
13
|
+
- name: centos-5.11
|
14
|
+
- name: centos-5.11-i386
|
15
|
+
- name: debian-6.0.10
|
16
|
+
- name: debian-6.0.10-i386
|
17
|
+
- name: debian-7.8
|
18
|
+
- name: debian-7.8-i386
|
19
|
+
- name: debian-8.1
|
20
|
+
- name: debian-8.1-i386
|
21
|
+
- name: fedora-21
|
22
|
+
- name: fedora-21-i386
|
23
|
+
- name: fedora-22
|
24
|
+
- name: freebsd-9.3
|
25
|
+
- name: freebsd-10.2
|
26
|
+
- name: opensuse-13.2-x86_64
|
27
|
+
- name: opensuse-13.2-i386
|
28
|
+
- name: ubuntu-14.04
|
29
|
+
- name: ubuntu-14.04-i386
|
30
|
+
- name: ubuntu-12.04
|
31
|
+
- name: ubuntu-12.04-i386
|
32
|
+
- name: ubuntu-10.04
|
33
|
+
- name: ubuntu-10.04-i386
|
34
|
+
|
35
|
+
suites:
|
36
|
+
- name: default
|
37
|
+
run_list:
|
38
|
+
- recipe[sudo]
|
39
|
+
- recipe[test]
|
40
|
+
attributes:
|
41
|
+
authorization:
|
42
|
+
sudo:
|
43
|
+
include_sudoers_d: true
|
@@ -0,0 +1,17 @@
|
|
1
|
+
#!/bin/sh
|
2
|
+
test ! -e /tmp/folder && \
|
3
|
+
mkdir /tmp/folder
|
4
|
+
chmod 0567 /tmp/folder
|
5
|
+
|
6
|
+
echo -n 'hello world' > /tmp/file
|
7
|
+
test ! -e /tmp/symlink && \
|
8
|
+
ln -s /tmp/file /tmp/symlink
|
9
|
+
chmod 0777 /tmp/symlink
|
10
|
+
chmod 0765 /tmp/file
|
11
|
+
|
12
|
+
test ! -e /tmp/pipe && \
|
13
|
+
mkfifo /tmp/pipe
|
14
|
+
|
15
|
+
test ! -e /tmp/block_device && \
|
16
|
+
mknod /tmp/block_device b 7 7
|
17
|
+
chmod 0666 /tmp/block_device
|
@@ -0,0 +1 @@
|
|
1
|
+
.kitchen
|
@@ -0,0 +1 @@
|
|
1
|
+
name 'test'
|
@@ -0,0 +1,100 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
# author: Dominik Richter
|
3
|
+
#
|
4
|
+
# Helper recipe to create create a few files in the operating
|
5
|
+
# systems, which the runner will test against.
|
6
|
+
# It also initializes the runner inside the machines
|
7
|
+
# and makes sure all dependencies are ready to go.
|
8
|
+
#
|
9
|
+
# Finally (for now), it actually executes the all tests with
|
10
|
+
# the local execution backend
|
11
|
+
|
12
|
+
include_recipe('test::prep_files')
|
13
|
+
|
14
|
+
# prepare ssh for backend
|
15
|
+
execute 'create ssh key' do
|
16
|
+
command 'ssh-keygen -t rsa -b 2048 -f /root/.ssh/id_rsa -N ""'
|
17
|
+
not_if 'test -e /root/.ssh/id_rsa'
|
18
|
+
end
|
19
|
+
|
20
|
+
execute 'add ssh key to vagrant user' do
|
21
|
+
command 'cat /root/.ssh/id_rsa.pub >> /home/vagrant/.ssh/authorized_keys'
|
22
|
+
end
|
23
|
+
|
24
|
+
execute 'test ssh connection' do
|
25
|
+
command 'ssh -o StrictHostKeyChecking=no -i /root/.ssh/id_rsa vagrant@localhost "echo 1"'
|
26
|
+
end
|
27
|
+
|
28
|
+
# prepare a few users
|
29
|
+
%w{ nopasswd passwd nosudo reqtty customcommand }.each do |name|
|
30
|
+
user name do
|
31
|
+
password '$1$7MCNTXPI$r./jqCEoVlLlByYKSL3sZ.'
|
32
|
+
manage_home true
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
%w{nopasswd vagrant}.each do |name|
|
37
|
+
sudo name do
|
38
|
+
user '%'+name
|
39
|
+
nopasswd true
|
40
|
+
defaults ['!requiretty']
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
sudo 'passwd' do
|
45
|
+
user 'passwd'
|
46
|
+
nopasswd false
|
47
|
+
defaults ['!requiretty']
|
48
|
+
end
|
49
|
+
|
50
|
+
sudo 'reqtty' do
|
51
|
+
user 'reqtty'
|
52
|
+
nopasswd true
|
53
|
+
defaults ['requiretty']
|
54
|
+
end
|
55
|
+
|
56
|
+
sudo 'customcommand' do
|
57
|
+
user 'customcommand'
|
58
|
+
nopasswd true
|
59
|
+
defaults ['!requiretty']
|
60
|
+
end
|
61
|
+
|
62
|
+
# execute tests
|
63
|
+
execute 'bundle install' do
|
64
|
+
command '/opt/chef/embedded/bin/bundle install --without integration tools'
|
65
|
+
cwd '/tmp/kitchen/data'
|
66
|
+
end
|
67
|
+
|
68
|
+
execute 'run local tests' do
|
69
|
+
command '/opt/chef/embedded/bin/ruby -I lib test/integration/test_local.rb test/integration/tests/*_test.rb'
|
70
|
+
cwd '/tmp/kitchen/data'
|
71
|
+
end
|
72
|
+
|
73
|
+
execute 'run ssh tests' do
|
74
|
+
command '/opt/chef/embedded/bin/ruby -I lib test/integration/test_ssh.rb test/integration/tests/*_test.rb'
|
75
|
+
cwd '/tmp/kitchen/data'
|
76
|
+
end
|
77
|
+
|
78
|
+
%w{passwd nopasswd reqtty customcommand}.each do |name|
|
79
|
+
execute "run local sudo tests as #{name}" do
|
80
|
+
command "/opt/chef/embedded/bin/ruby -I lib test/integration/sudo/#{name}.rb"
|
81
|
+
cwd '/tmp/kitchen/data'
|
82
|
+
user name
|
83
|
+
end
|
84
|
+
end
|
85
|
+
|
86
|
+
execute 'fix sudoers for reqtty' do
|
87
|
+
command 'chef-apply contrib/fixup_requiretty.rb'
|
88
|
+
cwd '/tmp/kitchen/data'
|
89
|
+
environment(
|
90
|
+
'TRAIN_SUDO_USER' => 'reqtty',
|
91
|
+
'TRAIN_SUDO_VERY_MUCH' => 'yes',
|
92
|
+
)
|
93
|
+
end
|
94
|
+
|
95
|
+
# if it's fixed, it should behave like user 'nopasswd'
|
96
|
+
execute 'run local sudo tests as reqtty, no longer requiring a tty' do
|
97
|
+
command "/opt/chef/embedded/bin/ruby -I lib test/integration/sudo/nopasswd.rb"
|
98
|
+
cwd '/tmp/kitchen/data'
|
99
|
+
user 'reqtty'
|
100
|
+
end
|
@@ -0,0 +1,47 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
# author: Dominik Richter
|
3
|
+
# author: Christoph Hartmann
|
4
|
+
#
|
5
|
+
# Helper recipe to create create a few files in the operating
|
6
|
+
# systems, which the runner will test against.
|
7
|
+
|
8
|
+
gid = 'root'
|
9
|
+
gid = 'wheel' if node['platform_family'] == 'freebsd'
|
10
|
+
gid = 'system' if node['platform_family'] == 'aix'
|
11
|
+
|
12
|
+
file '/tmp/file' do
|
13
|
+
mode '0765'
|
14
|
+
owner 'root'
|
15
|
+
group gid
|
16
|
+
content 'hello world'
|
17
|
+
end
|
18
|
+
|
19
|
+
directory '/tmp/folder' do
|
20
|
+
mode '0567'
|
21
|
+
owner 'root'
|
22
|
+
group gid
|
23
|
+
end
|
24
|
+
|
25
|
+
link '/tmp/symlink' do
|
26
|
+
to '/tmp/file'
|
27
|
+
owner 'root'
|
28
|
+
group gid
|
29
|
+
mode '0777'
|
30
|
+
end
|
31
|
+
|
32
|
+
link '/usr/bin/allyourbase' do
|
33
|
+
to '/usr/bin/sudo'
|
34
|
+
owner 'root'
|
35
|
+
group gid
|
36
|
+
mode '0777'
|
37
|
+
end
|
38
|
+
|
39
|
+
execute 'create pipe/fifo' do
|
40
|
+
command 'mkfifo /tmp/pipe'
|
41
|
+
not_if 'test -e /tmp/pipe'
|
42
|
+
end
|
43
|
+
|
44
|
+
execute 'create block_device' do
|
45
|
+
command "mknod /tmp/block_device b 7 7 && chmod 0666 /tmp/block_device && chown root:#{gid} /tmp/block_device"
|
46
|
+
not_if 'test -e /tmp/block_device'
|
47
|
+
end
|
@@ -0,0 +1,153 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
# author: Dominik Richter
|
3
|
+
|
4
|
+
require 'docker'
|
5
|
+
require 'yaml'
|
6
|
+
require 'concurrent'
|
7
|
+
|
8
|
+
class DockerRunner
|
9
|
+
def initialize(conf_path = nil)
|
10
|
+
@conf_path = conf_path || ENV['config']
|
11
|
+
unless File.file?(@conf_path)
|
12
|
+
fail "Can't find configuration in #{@conf_path}"
|
13
|
+
end
|
14
|
+
|
15
|
+
@conf = YAML.load_file(@conf_path)
|
16
|
+
if @conf.nil? or @conf.empty?
|
17
|
+
fail "Can't read coniguration in #{@conf_path}"
|
18
|
+
end
|
19
|
+
if @conf['images'].nil?
|
20
|
+
fail "You must configure test images in your #{@conf_path}"
|
21
|
+
end
|
22
|
+
|
23
|
+
@images = docker_images_by_tag
|
24
|
+
@image_pull_tickets = Concurrent::Semaphore.new(2)
|
25
|
+
@docker_run_tickets = Concurrent::Semaphore.new(5)
|
26
|
+
end
|
27
|
+
|
28
|
+
def run_all(&block)
|
29
|
+
fail 'You must provide a block for run_all' unless block_given?
|
30
|
+
|
31
|
+
promises = @conf['images'].map do |id|
|
32
|
+
run_on_target(id, &block)
|
33
|
+
end
|
34
|
+
|
35
|
+
# wait for all tests to be finished
|
36
|
+
sleep(0.1) until promises.all?(&:fulfilled?)
|
37
|
+
|
38
|
+
# return resulting values
|
39
|
+
promises.map(&:value)
|
40
|
+
end
|
41
|
+
|
42
|
+
def run_on_target(name, &block)
|
43
|
+
pr = Concurrent::Promise.new {
|
44
|
+
begin
|
45
|
+
container = start_container(name)
|
46
|
+
res = block.call(name, container)
|
47
|
+
# special rescue block to handle not implemented error
|
48
|
+
rescue NotImplementedError => err
|
49
|
+
raise err.message
|
50
|
+
end
|
51
|
+
# always stop the container
|
52
|
+
stop_container(container)
|
53
|
+
res
|
54
|
+
}.execute
|
55
|
+
|
56
|
+
# failure handling
|
57
|
+
pr.rescue do |err|
|
58
|
+
msg = "\033[31;1m#{err.message}\033[0m"
|
59
|
+
puts msg
|
60
|
+
msg + "\n" + err.backtrace.join("\n")
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
64
|
+
def provision_image(image, prov, files)
|
65
|
+
tries ||= 3
|
66
|
+
return image if prov['script'].nil?
|
67
|
+
path = File.join(File.dirname(@conf_path), prov['script'])
|
68
|
+
unless File.file?(path)
|
69
|
+
puts "Can't find script file #{path}"
|
70
|
+
return image
|
71
|
+
end
|
72
|
+
puts " script #{path}"
|
73
|
+
dst = "/bootstrap#{files.length}.sh"
|
74
|
+
files.push(dst)
|
75
|
+
image.insert_local('localPath' => path, 'outputPath' => dst)
|
76
|
+
rescue StandardError => _
|
77
|
+
retry unless (tries -= 1).zero?
|
78
|
+
end
|
79
|
+
|
80
|
+
def bootstrap_image(name, image)
|
81
|
+
files = []
|
82
|
+
provisions = Array(@conf['provision'])
|
83
|
+
puts "--> provision docker #{name}" unless provisions.empty?
|
84
|
+
provisions.each do |prov|
|
85
|
+
image = provision_image(image, prov, files)
|
86
|
+
end
|
87
|
+
[image, files]
|
88
|
+
end
|
89
|
+
|
90
|
+
def start_container(name, version = nil)
|
91
|
+
unless name.include?(':')
|
92
|
+
version ||= 'latest'
|
93
|
+
name = "#{name}:#{version}"
|
94
|
+
end
|
95
|
+
puts "--> schedule docker #{name}"
|
96
|
+
|
97
|
+
image = @images[name]
|
98
|
+
if image.nil?
|
99
|
+
puts "\033[35;1m--> pull docker images #{name} "\
|
100
|
+
"(this may take a while)\033[0m"
|
101
|
+
|
102
|
+
@image_pull_tickets.acquire(1)
|
103
|
+
puts "... start pull image #{name}"
|
104
|
+
image = Docker::Image.create('fromImage' => name)
|
105
|
+
@image_pull_tickets.release(1)
|
106
|
+
|
107
|
+
unless image.nil?
|
108
|
+
puts "\033[35;1m--> pull docker images finished for #{name}\033[0m"
|
109
|
+
end
|
110
|
+
end
|
111
|
+
|
112
|
+
fail "Can't find nor pull docker image #{name}" if image.nil?
|
113
|
+
|
114
|
+
@docker_run_tickets.acquire(1)
|
115
|
+
|
116
|
+
image, scripts = bootstrap_image(name, image)
|
117
|
+
|
118
|
+
puts "--> start docker #{name}"
|
119
|
+
container = Docker::Container.create(
|
120
|
+
'Cmd' => %w{sleep 3600},
|
121
|
+
'Image' => image.id,
|
122
|
+
'OpenStdin' => true,
|
123
|
+
)
|
124
|
+
container.start
|
125
|
+
|
126
|
+
scripts.each do |script|
|
127
|
+
container.exec(%w{chmod +x}.push(script))
|
128
|
+
container.exec(%w{sh -c}.push(script))
|
129
|
+
end
|
130
|
+
|
131
|
+
container
|
132
|
+
end
|
133
|
+
|
134
|
+
def stop_container(container)
|
135
|
+
@docker_run_tickets.release(1)
|
136
|
+
puts "--> killrm docker #{container.id}"
|
137
|
+
container.kill
|
138
|
+
container.delete(force: true)
|
139
|
+
end
|
140
|
+
|
141
|
+
private
|
142
|
+
|
143
|
+
# get all docker image tags
|
144
|
+
def docker_images_by_tag
|
145
|
+
images = {}
|
146
|
+
Docker::Image.all.map do |img|
|
147
|
+
Array(img.info['RepoTags']).each do |tag|
|
148
|
+
images[tag] = img
|
149
|
+
end
|
150
|
+
end
|
151
|
+
images
|
152
|
+
end
|
153
|
+
end
|
@@ -0,0 +1,24 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
require_relative 'docker_run'
|
3
|
+
tests = ARGV
|
4
|
+
|
5
|
+
def test_container(container, tests)
|
6
|
+
puts "--> run test on docker #{container.id}"
|
7
|
+
pid = Process.fork do
|
8
|
+
ENV['CONTAINER'] = container.id
|
9
|
+
require_relative 'docker_test_container.rb'
|
10
|
+
Process.exit
|
11
|
+
end
|
12
|
+
|
13
|
+
_, status = Process.waitpid2(pid)
|
14
|
+
status.exitstatus == 0
|
15
|
+
end
|
16
|
+
|
17
|
+
results = DockerRunner.new.run_all do |name, container|
|
18
|
+
status = test_container(container, tests)
|
19
|
+
status ? nil : "Failed to run tests on #{name}"
|
20
|
+
end
|
21
|
+
|
22
|
+
failures = results.compact
|
23
|
+
failures.each { |f| puts "\033[31;1m#{f}\033[0m\n\n" }
|
24
|
+
failures.empty? or fail 'Test failures'
|
@@ -0,0 +1,24 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
# author: Dominik Richter
|
3
|
+
|
4
|
+
require 'train'
|
5
|
+
require_relative 'helper'
|
6
|
+
|
7
|
+
container_id = ENV['CONTAINER'] or
|
8
|
+
fail 'You must provide a container ID via CONTAINER env'
|
9
|
+
|
10
|
+
tests = ARGV
|
11
|
+
puts ['Running tests:', tests].flatten.join("\n- ")
|
12
|
+
puts ''
|
13
|
+
|
14
|
+
backends = {}
|
15
|
+
backends[:docker] = proc { |*args|
|
16
|
+
opt = Train.target_config({ host: container_id })
|
17
|
+
Train.create('docker', opt).connection(args[0])
|
18
|
+
}
|
19
|
+
|
20
|
+
backends.each do |type, get_backend|
|
21
|
+
tests.each do |test|
|
22
|
+
instance_eval(File.read(test), test, 1)
|
23
|
+
end
|
24
|
+
end
|
@@ -0,0 +1,61 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
# author: Dominik Richter
|
3
|
+
|
4
|
+
require 'minitest/autorun'
|
5
|
+
require 'minitest/spec'
|
6
|
+
|
7
|
+
# Tests configuration:
|
8
|
+
module Test
|
9
|
+
class << self
|
10
|
+
# MTime tracks the maximum range of modification time in seconds.
|
11
|
+
# i.e. MTime == 60*60*1 is 1 hour of modification time range,
|
12
|
+
# which translates to a modification time range of:
|
13
|
+
# [ now-1hour, now ]
|
14
|
+
def mtime
|
15
|
+
60 * 60 * 24 * 1
|
16
|
+
end
|
17
|
+
|
18
|
+
def dup(o)
|
19
|
+
Marshal.load(Marshal.dump(o))
|
20
|
+
end
|
21
|
+
|
22
|
+
def root_group(os)
|
23
|
+
case os[:family]
|
24
|
+
when 'freebsd'
|
25
|
+
'wheel'
|
26
|
+
when 'aix'
|
27
|
+
'system'
|
28
|
+
else
|
29
|
+
'root'
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
def selinux_label(backend, path = nil)
|
34
|
+
return nil if backend.class.to_s =~ /docker/i
|
35
|
+
|
36
|
+
os = backend.os
|
37
|
+
labels = {}
|
38
|
+
|
39
|
+
h = {}
|
40
|
+
h.default = Hash.new(nil)
|
41
|
+
h['redhat'] = {}
|
42
|
+
h['redhat'].default = 'unconfined_u:object_r:user_tmp_t:s0'
|
43
|
+
h['redhat']['5.11'] = 'user_u:object_r:tmp_t'
|
44
|
+
h['centos'] = h['fedora'] = h['redhat']
|
45
|
+
labels.default = dup(h)
|
46
|
+
|
47
|
+
h['redhat'].default = 'unconfined_u:object_r:tmp_t:s0'
|
48
|
+
labels['/tmp/block_device'] = dup(h)
|
49
|
+
|
50
|
+
h = {}
|
51
|
+
h.default = Hash.new(nil)
|
52
|
+
h['redhat'] = {}
|
53
|
+
h['redhat'].default = 'system_u:object_r:null_device_t:s0'
|
54
|
+
h['redhat']['5.11'] = 'system_u:object_r:null_device_t'
|
55
|
+
h['centos'] = h['fedora'] = h['redhat']
|
56
|
+
labels['/dev/null'] = dup(h)
|
57
|
+
|
58
|
+
labels[path][os[:family]][os[:release]]
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|