machinery-tool 1.1.0 → 1.1.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/NEWS +6 -0
- data/lib/autoyast.rb +149 -0
- data/lib/cli.rb +37 -2
- data/lib/exceptions.rb +1 -1
- data/lib/{kiwi_export_task.rb → export_task.rb} +12 -9
- data/lib/kiwi_config.rb +6 -6
- data/lib/list_task.rb +38 -32
- data/lib/local_system.rb +7 -13
- data/lib/machinery.rb +51 -51
- data/lib/mountpoints.rb +15 -3
- data/lib/object.rb +10 -2
- data/lib/scope_mixin.rb +18 -0
- data/lib/system_description.rb +10 -20
- data/lib/upgrade_format_task.rb +5 -1
- data/lib/version.rb +1 -1
- data/plugins/docs/unmanaged_files.md +4 -3
- data/plugins/inspect/os_inspector.rb +7 -7
- data/plugins/inspect/unmanaged_files_inspector.rb +37 -17
- data/plugins/model/os_model.rb +112 -1
- data/plugins/model/services_model.rb +9 -0
- data/plugins/model/unmanaged_files_model.rb +9 -0
- data/plugins/show/config_files_renderer.rb +4 -2
- metadata +4 -4
- data/lib/os.rb +0 -90
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: c161742e300133d4d5a6514ddfe3e4284fc29b52
|
4
|
+
data.tar.gz: 28c974344534d7ad4df48e43dce31b60125bb1b1
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: ddd663cea68dfa8a41b8cd8921c91436a5e70a049439ee5b628b4d628f427ef4375923f9b33e967e4d6604ba487950cad0ebed0e2b62291ba66fed49ebfa1087
|
7
|
+
data.tar.gz: 285ed630148abb78038681ed823dd2079501a18ecd64d0882e642300c8d6f648b62dfb7f672e8efd4dcdfc1fc3131401cf82e88f09c6d3cdb6c886423f69302f
|
data/NEWS
CHANGED
@@ -1,6 +1,12 @@
|
|
1
1
|
# Machinery Release Notes
|
2
2
|
|
3
3
|
|
4
|
+
## Version 1.1.1 - Tue Dec 02 13:24:38 CET 2014 - thardeck@suse.de
|
5
|
+
|
6
|
+
* Skip Gnome Virtual File System mounts on inspection (issue #393)
|
7
|
+
* Skip special file systems like proc, devtmpfs and so on (issue #384)
|
8
|
+
* Show names of packages where changed config files come from (issue #392)
|
9
|
+
|
4
10
|
## Version 1.1.0 - Mon Nov 17 16:30:44 CET 2014 - thardeck@suse.de
|
5
11
|
|
6
12
|
* File extraction status is now shown in the comparison output
|
data/lib/autoyast.rb
ADDED
@@ -0,0 +1,149 @@
|
|
1
|
+
# Copyright (c) 2013-2014 SUSE LLC
|
2
|
+
#
|
3
|
+
# This program is free software; you can redistribute it and/or
|
4
|
+
# modify it under the terms of version 3 of the GNU General Public License as
|
5
|
+
# published by the Free Software Foundation.
|
6
|
+
#
|
7
|
+
# This program is distributed in the hope that it will be useful,
|
8
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
9
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
10
|
+
# GNU General Public License for more details.
|
11
|
+
#
|
12
|
+
# You should have received a copy of the GNU General Public License
|
13
|
+
# along with this program; if not, contact SUSE LLC.
|
14
|
+
#
|
15
|
+
# To contact SUSE about this file by physical or electronic mail,
|
16
|
+
# you may find current contact information at www.suse.com
|
17
|
+
|
18
|
+
class Autoyast
|
19
|
+
def initialize(description)
|
20
|
+
@system_description = description
|
21
|
+
end
|
22
|
+
|
23
|
+
def write(output_dir)
|
24
|
+
File.write(File.join(output_dir, "autoinst.xml"), profile)
|
25
|
+
end
|
26
|
+
|
27
|
+
def profile
|
28
|
+
builder = Nokogiri::XML::Builder.new do |xml|
|
29
|
+
xml.doc.create_internal_subset("profile", nil, nil)
|
30
|
+
xml.profile(
|
31
|
+
"xmlns" => "http://www.suse.com/1.0/yast2ns",
|
32
|
+
"xmlns:config" => "http://www.suse.com/1.0/configns"
|
33
|
+
) do
|
34
|
+
apply_repositories(xml)
|
35
|
+
xml.software do
|
36
|
+
apply_packages(xml)
|
37
|
+
apply_patterns(xml)
|
38
|
+
end
|
39
|
+
apply_users(xml)
|
40
|
+
apply_groups(xml)
|
41
|
+
apply_services(xml)
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
builder.to_xml
|
46
|
+
end
|
47
|
+
|
48
|
+
private
|
49
|
+
|
50
|
+
def apply_repositories(xml)
|
51
|
+
return if !@system_description.repositories
|
52
|
+
|
53
|
+
xml.send("add-on") do
|
54
|
+
xml.add_on_products("config:type" => "list") do
|
55
|
+
@system_description.repositories.each do |repository|
|
56
|
+
xml.listentry do
|
57
|
+
xml.media_url repository.url
|
58
|
+
xml.name repository.alias
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
63
|
+
end
|
64
|
+
|
65
|
+
def apply_packages(xml)
|
66
|
+
return if !@system_description.packages
|
67
|
+
|
68
|
+
xml.packages("config:type" => "list") do
|
69
|
+
@system_description.packages.each do |package|
|
70
|
+
xml.package package.name
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
def apply_patterns(xml)
|
76
|
+
return if !@system_description.patterns
|
77
|
+
|
78
|
+
xml.patterns("config:type" => "list") do
|
79
|
+
@system_description.patterns.each do |pattern|
|
80
|
+
xml.pattern pattern.name
|
81
|
+
end
|
82
|
+
end
|
83
|
+
end
|
84
|
+
|
85
|
+
def apply_users(xml)
|
86
|
+
return if !@system_description.users
|
87
|
+
|
88
|
+
xml.users("config:type" => "list") do
|
89
|
+
@system_description.users.each do |user|
|
90
|
+
xml.user do
|
91
|
+
xml.username user.name
|
92
|
+
xml.user_password user.encrypted_password
|
93
|
+
xml.encrypted "true", "config:type" => "boolean"
|
94
|
+
xml.uid user.uid
|
95
|
+
xml.gid user.gid
|
96
|
+
xml.home user.home
|
97
|
+
xml.shell user.shell
|
98
|
+
xml.fullname user.comment
|
99
|
+
xml.password_settings do
|
100
|
+
xml.min user.min_days
|
101
|
+
xml.max user.max_days
|
102
|
+
xml.warn user.warn_days
|
103
|
+
xml.inact user.disable_days
|
104
|
+
xml.expire user.disabled_date
|
105
|
+
end
|
106
|
+
end
|
107
|
+
end
|
108
|
+
end
|
109
|
+
end
|
110
|
+
|
111
|
+
def apply_groups(xml)
|
112
|
+
return if !@system_description.groups
|
113
|
+
|
114
|
+
xml.groups("config:type" => "list") do
|
115
|
+
@system_description.groups.each do |group|
|
116
|
+
xml.group do
|
117
|
+
xml.encrypted "true", "config:type" => "boolean"
|
118
|
+
xml.gid group.gid
|
119
|
+
xml.groupname group.name
|
120
|
+
xml.group_password group.password
|
121
|
+
xml.userlist group.users.join(",")
|
122
|
+
end
|
123
|
+
end
|
124
|
+
end
|
125
|
+
end
|
126
|
+
|
127
|
+
def apply_services(xml)
|
128
|
+
xml.send("services-manager") do
|
129
|
+
xml.services do
|
130
|
+
@system_description.services.services.each do |service|
|
131
|
+
# systemd service states like "masked" and "static" are
|
132
|
+
# not supported by Autoyast
|
133
|
+
if service.enabled?
|
134
|
+
xml.service do
|
135
|
+
xml.service_name service.name
|
136
|
+
xml.service_status "enable"
|
137
|
+
end
|
138
|
+
end
|
139
|
+
if service.disabled?
|
140
|
+
xml.service do
|
141
|
+
xml.service_name service.name
|
142
|
+
xml.service_status "disable"
|
143
|
+
end
|
144
|
+
end
|
145
|
+
end
|
146
|
+
end
|
147
|
+
end
|
148
|
+
end
|
149
|
+
end
|
data/lib/cli.rb
CHANGED
@@ -359,9 +359,42 @@ class Cli
|
|
359
359
|
name = shift_arg(args, "NAME")
|
360
360
|
store = SystemDescriptionStore.new
|
361
361
|
description = store.load(name)
|
362
|
+
exporter = KiwiConfig.new(description)
|
362
363
|
|
363
|
-
task =
|
364
|
-
task.export(
|
364
|
+
task = ExportTask.new(exporter)
|
365
|
+
task.export(
|
366
|
+
File.expand_path(options["kiwi-dir"]),
|
367
|
+
force: options[:force]
|
368
|
+
)
|
369
|
+
end
|
370
|
+
end
|
371
|
+
|
372
|
+
|
373
|
+
|
374
|
+
desc "Export system description as AutoYaST profile"
|
375
|
+
long_desc <<-LONGDESC
|
376
|
+
Export system description as AutoYaST profile
|
377
|
+
|
378
|
+
The profile will be placed in the location given by the 'autoyast-dir' option.
|
379
|
+
LONGDESC
|
380
|
+
arg "NAME"
|
381
|
+
command "export-autoyast" do |c|
|
382
|
+
c.flag ["autoyast-dir", :a], type: String, required: true,
|
383
|
+
desc: "Location where the autoyast profile will be stored", arg_name: "DIRECTORY"
|
384
|
+
c.switch :force, default_value: false, required: false, negatable: false,
|
385
|
+
desc: "Overwrite existing profile"
|
386
|
+
|
387
|
+
c.action do |_global_options, options, args|
|
388
|
+
name = shift_arg(args, "NAME")
|
389
|
+
store = SystemDescriptionStore.new
|
390
|
+
description = store.load(name)
|
391
|
+
exporter = Autoyast.new(description)
|
392
|
+
|
393
|
+
task = ExportTask.new(exporter)
|
394
|
+
task.export(
|
395
|
+
File.expand_path(options["autoyast-dir"]),
|
396
|
+
force: options[:force]
|
397
|
+
)
|
365
398
|
end
|
366
399
|
end
|
367
400
|
|
@@ -446,6 +479,8 @@ class Cli
|
|
446
479
|
command :list do |c|
|
447
480
|
c.switch :verbose, :required => false, :negatable => false,
|
448
481
|
:desc => "Display additional information about origin of scopes"
|
482
|
+
c.switch :quick, :required => false, :negatable => false,
|
483
|
+
:desc => "Show quick list without details"
|
449
484
|
|
450
485
|
c.action do |global_options,options,args|
|
451
486
|
store = SystemDescriptionStore.new
|
data/lib/exceptions.rb
CHANGED
@@ -103,7 +103,7 @@ module Machinery
|
|
103
103
|
class BuildFailed < MachineryError; end
|
104
104
|
class DeployFailed < MachineryError; end
|
105
105
|
class InspectionFailed < MachineryError; end
|
106
|
-
class
|
106
|
+
class ExportFailed < MachineryError; end
|
107
107
|
|
108
108
|
class SshConnectionFailed < MachineryError; end
|
109
109
|
class RsyncFailed < MachineryError; end
|
@@ -15,22 +15,25 @@
|
|
15
15
|
# To contact SUSE about this file by physical or electronic mail,
|
16
16
|
# you may find current contact information at www.suse.com
|
17
17
|
|
18
|
-
class
|
19
|
-
def
|
20
|
-
|
18
|
+
class ExportTask
|
19
|
+
def initialize(exporter)
|
20
|
+
@exporter = exporter
|
21
|
+
end
|
22
|
+
|
23
|
+
def export(output_dir, options)
|
24
|
+
if File.exists?(output_dir)
|
21
25
|
if options[:force]
|
22
|
-
FileUtils.rm_r(
|
26
|
+
FileUtils.rm_r(output_dir)
|
23
27
|
else
|
24
|
-
raise Machinery::Errors::
|
25
|
-
"The output directory '#{
|
28
|
+
raise Machinery::Errors::ExportFailed.new(
|
29
|
+
"The output directory '#{output_dir}' already exists." \
|
26
30
|
" You can force overwriting it with the '--force' option."
|
27
31
|
)
|
28
32
|
end
|
29
33
|
end
|
30
34
|
|
31
|
-
FileUtils.mkdir_p(
|
35
|
+
FileUtils.mkdir_p(output_dir) unless Dir.exists?(output_dir)
|
32
36
|
|
33
|
-
|
34
|
-
config.write(kiwi_dir)
|
37
|
+
@exporter.write(output_dir)
|
35
38
|
end
|
36
39
|
end
|
data/lib/kiwi_config.rb
CHANGED
@@ -140,7 +140,7 @@ suseSetupProduct
|
|
140
140
|
suseImportBuildKey
|
141
141
|
suseConfig
|
142
142
|
EOF
|
143
|
-
case @system_description.
|
143
|
+
case @system_description.os
|
144
144
|
when OsOpenSuse13_1
|
145
145
|
boot = "vmxboot/suse-13.1"
|
146
146
|
bootloader = "grub2"
|
@@ -151,9 +151,9 @@ EOF
|
|
151
151
|
boot = "vmxboot/suse-SLES11"
|
152
152
|
bootloader = "grub"
|
153
153
|
else
|
154
|
-
raise Machinery::Errors::
|
154
|
+
raise Machinery::Errors::ExportFailed.new(
|
155
155
|
"Building is not possible because the operating system " \
|
156
|
-
"'#{@system_description.
|
156
|
+
"'#{@system_description.os.canonical_name}' is not supported."
|
157
157
|
)
|
158
158
|
end
|
159
159
|
|
@@ -194,7 +194,7 @@ EOF
|
|
194
194
|
build_filter = YAML.load_file(File.join(
|
195
195
|
Machinery::ROOT, "helpers", "filter-packages-for-build.yaml")
|
196
196
|
)
|
197
|
-
filter = build_filter[@system_description.
|
197
|
+
filter = build_filter[@system_description.os.canonical_name] || []
|
198
198
|
|
199
199
|
xml.packages(type: "bootstrap") do
|
200
200
|
if @system_description.packages
|
@@ -298,7 +298,7 @@ EOF
|
|
298
298
|
# Don't do anything because these states are not supposed
|
299
299
|
# to be permanent.
|
300
300
|
else
|
301
|
-
raise Machinery::Errors::
|
301
|
+
raise Machinery::Errors::ExportFailed.new(
|
302
302
|
"The systemd unit state #{service.state} is unknown."
|
303
303
|
)
|
304
304
|
end
|
@@ -311,7 +311,7 @@ EOF
|
|
311
311
|
end
|
312
312
|
|
313
313
|
def enable_dhcp(output_location)
|
314
|
-
case @system_description.
|
314
|
+
case @system_description.os
|
315
315
|
when OsSles11
|
316
316
|
write_dhcp_network_config(output_location, "eth0")
|
317
317
|
when OsSles12
|
data/lib/list_task.rb
CHANGED
@@ -19,46 +19,52 @@ class ListTask
|
|
19
19
|
def list(store, options = {})
|
20
20
|
descriptions = store.list.sort
|
21
21
|
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
description = store.load(name)
|
26
|
-
rescue Machinery::Errors::SystemDescriptionError
|
27
|
-
Machinery::Ui.puts " #{name}:\n"
|
28
|
-
Machinery::Ui.puts " This description has an incompatible data format or is broken.\n" \
|
29
|
-
" Use `#{$0} validate #{name}` to see the error message.\n\n"
|
30
|
-
next
|
22
|
+
if options[:quick]
|
23
|
+
descriptions.each do |name|
|
24
|
+
Machinery::Ui.puts(" #{name}")
|
31
25
|
end
|
32
|
-
|
26
|
+
else
|
27
|
+
descriptions.each do |name|
|
28
|
+
name = File.basename(name)
|
29
|
+
begin
|
30
|
+
description = store.load(name)
|
31
|
+
rescue Machinery::Errors::SystemDescriptionError
|
32
|
+
Machinery::Ui.puts " #{name}:\n"
|
33
|
+
Machinery::Ui.puts " This description has an incompatible data format or is broken.\n" \
|
34
|
+
" Use `#{$0} validate #{name}` to see the error message.\n\n"
|
35
|
+
next
|
36
|
+
end
|
37
|
+
scopes = []
|
33
38
|
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
39
|
+
description.scopes.each do |scope|
|
40
|
+
entry = Machinery::Ui.internal_scope_list_to_string(scope)
|
41
|
+
if SystemDescription::EXTRACTABLE_SCOPES.include?(scope)
|
42
|
+
if description.scope_extracted?(scope)
|
43
|
+
entry += " (extracted)"
|
44
|
+
else
|
45
|
+
entry += " (not extracted)"
|
46
|
+
end
|
41
47
|
end
|
42
|
-
end
|
43
48
|
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
49
|
+
if options["verbose"]
|
50
|
+
meta = description[scope].meta
|
51
|
+
if meta
|
52
|
+
time = Time.parse(meta.modified).getlocal
|
53
|
+
date = time.strftime "%Y-%m-%d %H:%M:%S"
|
54
|
+
hostname = meta.hostname
|
55
|
+
else
|
56
|
+
date = "unknown"
|
57
|
+
hostname = "Unknown hostname"
|
58
|
+
end
|
59
|
+
entry += "\n Host: [#{hostname}]"
|
60
|
+
entry += "\n Date: (#{date})"
|
53
61
|
end
|
54
|
-
|
55
|
-
|
62
|
+
|
63
|
+
scopes << entry
|
56
64
|
end
|
57
65
|
|
58
|
-
scopes
|
66
|
+
Machinery::Ui.puts " #{name}:\n * " + scopes .join("\n * ") + "\n\n"
|
59
67
|
end
|
60
|
-
|
61
|
-
Machinery::Ui.puts " #{name}:\n * " + scopes .join("\n * ") + "\n\n"
|
62
68
|
end
|
63
69
|
end
|
64
70
|
end
|
data/lib/local_system.rb
CHANGED
@@ -17,18 +17,18 @@
|
|
17
17
|
|
18
18
|
class LocalSystem < System
|
19
19
|
class << self
|
20
|
-
def
|
20
|
+
def os
|
21
21
|
description = SystemDescription.new("localhost")
|
22
22
|
inspector = OsInspector.new
|
23
23
|
inspector.inspect(System.for("localhost"), description)
|
24
|
-
description.
|
24
|
+
description.os
|
25
25
|
end
|
26
26
|
|
27
27
|
def validate_existence_of_package(package)
|
28
28
|
begin
|
29
29
|
Cheetah.run("rpm", "-q", package)
|
30
30
|
rescue
|
31
|
-
needed_module =
|
31
|
+
needed_module = os.module_required_by_package(package)
|
32
32
|
if needed_module
|
33
33
|
raise(Machinery::Errors::MissingRequirement.new("You need the package '#{package}' from module '#{needed_module}'. You can install it as follows:\n" \
|
34
34
|
"If you haven't selected the module '#{needed_module}' before, run `yast2 scc` and choose 'Select Extensions' and activate '#{needed_module}'.\nRun `zypper install #{package}` to install the package."))
|
@@ -39,14 +39,8 @@ class LocalSystem < System
|
|
39
39
|
end
|
40
40
|
|
41
41
|
def validate_machinery_compatibility
|
42
|
-
|
43
|
-
|
44
|
-
rescue Machinery::Errors::SystemDescriptionError
|
45
|
-
os = nil
|
46
|
-
end
|
47
|
-
|
48
|
-
if !os || !os.can_run_machinery?
|
49
|
-
supported_oses = Os.supported_host_systems.map { |o| o.new.name }.
|
42
|
+
if !os.can_run_machinery?
|
43
|
+
supported_oses = Os.supported_host_systems.map { |o| o.canonical_name }.
|
50
44
|
sort.join(", ")
|
51
45
|
message = "Running Machinery is not supported on this system.\n" \
|
52
46
|
"Supported operating systems are: #{supported_oses}"
|
@@ -56,8 +50,8 @@ class LocalSystem < System
|
|
56
50
|
end
|
57
51
|
|
58
52
|
def validate_build_compatibility(system_description)
|
59
|
-
if !
|
60
|
-
message = "Building '#{system_description.
|
53
|
+
if !os.can_build?(system_description.os)
|
54
|
+
message = "Building '#{system_description.os.canonical_name}' images is " \
|
61
55
|
"not supported on this distribution.\n" \
|
62
56
|
"Check the 'BUILD SUPPORT MATRIX' section in our man page for " \
|
63
57
|
"further information which build targets are supported."
|
data/lib/machinery.rb
CHANGED
@@ -15,12 +15,12 @@
|
|
15
15
|
# To contact SUSE about this file by physical or electronic mail,
|
16
16
|
# you may find current contact information at www.suse.com
|
17
17
|
|
18
|
-
require
|
19
|
-
require
|
18
|
+
require "ostruct"
|
19
|
+
require "json"
|
20
20
|
require "abstract_method"
|
21
21
|
require "cheetah"
|
22
22
|
require "tmpdir"
|
23
|
-
require
|
23
|
+
require "tempfile"
|
24
24
|
require "time"
|
25
25
|
require "logger"
|
26
26
|
require "erb"
|
@@ -31,55 +31,55 @@ require "json-schema"
|
|
31
31
|
require "haml"
|
32
32
|
require "kramdown"
|
33
33
|
|
34
|
-
require_relative
|
35
|
-
require_relative
|
36
|
-
require_relative
|
37
|
-
require_relative
|
38
|
-
require_relative
|
39
|
-
require_relative
|
40
|
-
require_relative
|
41
|
-
require_relative
|
42
|
-
require_relative
|
43
|
-
require_relative
|
44
|
-
require_relative
|
45
|
-
require_relative
|
46
|
-
require_relative
|
47
|
-
require_relative
|
48
|
-
require_relative
|
49
|
-
require_relative
|
50
|
-
require_relative
|
51
|
-
require_relative
|
52
|
-
require_relative
|
53
|
-
require_relative
|
54
|
-
require_relative
|
55
|
-
require_relative
|
56
|
-
require_relative
|
57
|
-
require_relative
|
58
|
-
require_relative
|
59
|
-
require_relative
|
60
|
-
require_relative
|
61
|
-
require_relative
|
62
|
-
require_relative
|
63
|
-
require_relative
|
64
|
-
require_relative
|
65
|
-
require_relative
|
66
|
-
require_relative
|
67
|
-
require_relative
|
68
|
-
require_relative
|
69
|
-
require_relative
|
70
|
-
require_relative
|
71
|
-
require_relative
|
72
|
-
require_relative
|
73
|
-
require_relative
|
74
|
-
require_relative
|
75
|
-
require_relative
|
76
|
-
require_relative
|
77
|
-
require_relative
|
78
|
-
require_relative
|
79
|
-
require_relative
|
80
|
-
require_relative
|
34
|
+
require_relative "machinery_logger"
|
35
|
+
require_relative "zypper"
|
36
|
+
require_relative "rpm"
|
37
|
+
require_relative "array"
|
38
|
+
require_relative "object"
|
39
|
+
require_relative "constants"
|
40
|
+
require_relative "system_description"
|
41
|
+
require_relative "system_description_validator"
|
42
|
+
require_relative "version"
|
43
|
+
require_relative "tarball"
|
44
|
+
require_relative "exceptions"
|
45
|
+
require_relative "inspector"
|
46
|
+
require_relative "system"
|
47
|
+
require_relative "local_system"
|
48
|
+
require_relative "remote_system"
|
49
|
+
require_relative "current_user"
|
50
|
+
require_relative "inspect_task"
|
51
|
+
require_relative "inspector"
|
52
|
+
require_relative "build_task"
|
53
|
+
require_relative "kiwi_config"
|
54
|
+
require_relative "renderer"
|
55
|
+
require_relative "show_task"
|
56
|
+
require_relative "compare_task"
|
57
|
+
require_relative "remove_task"
|
58
|
+
require_relative "list_task"
|
59
|
+
require_relative "system_description_store"
|
60
|
+
require_relative "logged_cheetah"
|
61
|
+
require_relative "renderer_helper"
|
62
|
+
require_relative "changed_rpm_files_helper"
|
63
|
+
require_relative "export_task"
|
64
|
+
require_relative "helper"
|
65
|
+
require_relative "deploy_task"
|
66
|
+
require_relative "analyze_config_file_diffs_task"
|
67
|
+
require_relative "copy_task"
|
68
|
+
require_relative "scope_mixin"
|
69
|
+
require_relative "ui"
|
70
|
+
require_relative "validate_task"
|
71
|
+
require_relative "migration"
|
72
|
+
require_relative "upgrade_format_task"
|
73
|
+
require_relative "html"
|
74
|
+
require_relative "generate_html_task"
|
75
|
+
require_relative "hint"
|
76
|
+
require_relative "mountpoints"
|
77
|
+
require_relative "config_base"
|
78
|
+
require_relative "config"
|
79
|
+
require_relative "config_task"
|
80
|
+
require_relative "autoyast"
|
81
81
|
|
82
82
|
Dir[File.join(Machinery::ROOT, "plugins", "**", "*.rb")].each { |f| require(f) }
|
83
83
|
|
84
84
|
# this file needs be loaded last, because it immediately collects the loaded inspectors
|
85
|
-
require_relative
|
85
|
+
require_relative "cli"
|
data/lib/mountpoints.rb
CHANGED
@@ -24,6 +24,9 @@
|
|
24
24
|
# remote() returns an array containing the mount points of all mounted
|
25
25
|
# file systems that are remote file systems (e.g. nfs, cifs)
|
26
26
|
#
|
27
|
+
# special() returns an array containing the mount points of all mounted
|
28
|
+
# special file systems, e.g. /proc
|
29
|
+
#
|
27
30
|
# local() returns an array containing the mount points of all mounted
|
28
31
|
# local file systems with permanent data (e.g. ext3, btrfs, xfs)
|
29
32
|
|
@@ -31,17 +34,22 @@
|
|
31
34
|
class MountPoints
|
32
35
|
attr_reader :mounts
|
33
36
|
REMOTE_FILE_SYSTEMS = ["autofs", "cifs", "nfs", "nfs4"]
|
37
|
+
SPECIAL_FILE_SYSTEMS = ["proc", "sysfs", "devtmpfs", "tmpfs", "fuse.gvfs-fuse-daemon"]
|
34
38
|
LOCAL_FILE_SYSTEMS = ["ext2", "ext3", "ext4", "reiserfs", "btrfs", "vfat", "xfs", "jfs"]
|
35
39
|
def initialize(system)
|
36
40
|
@mounts = parse_mounts(system.read_file("/proc/mounts"))
|
37
41
|
end
|
38
42
|
|
43
|
+
def special
|
44
|
+
@mounts.select { |_fs_file, fs_vfstype| special_fs?(fs_vfstype) }.keys
|
45
|
+
end
|
46
|
+
|
39
47
|
def remote
|
40
|
-
@mounts.select { |
|
48
|
+
@mounts.select { |_fs_file, fs_vfstype| remote_fs?(fs_vfstype) }.keys
|
41
49
|
end
|
42
50
|
|
43
51
|
def local
|
44
|
-
@mounts.select { |
|
52
|
+
@mounts.select { |_fs_file, fs_vfstype| local_fs?(fs_vfstype) }.keys
|
45
53
|
end
|
46
54
|
|
47
55
|
def all
|
@@ -56,12 +64,16 @@ class MountPoints
|
|
56
64
|
# we store the latest entry only, because that's the relevant one
|
57
65
|
mounts = Hash.new
|
58
66
|
proc_mounts.each_line do |line|
|
59
|
-
|
67
|
+
_fs_spec, fs_file, fs_vfstype, _fs_mntops, _fs_freq, _fs_passno = line.split(" ")
|
60
68
|
mounts[fs_file] = fs_vfstype
|
61
69
|
end
|
62
70
|
mounts
|
63
71
|
end
|
64
72
|
|
73
|
+
def special_fs?(fs)
|
74
|
+
SPECIAL_FILE_SYSTEMS.include?(fs)
|
75
|
+
end
|
76
|
+
|
65
77
|
def remote_fs?(fs)
|
66
78
|
REMOTE_FILE_SYSTEMS.include?(fs)
|
67
79
|
end
|
data/lib/object.rb
CHANGED
@@ -23,7 +23,7 @@ module Machinery
|
|
23
23
|
@property_classes[name.to_sym] = options[:class]
|
24
24
|
end
|
25
25
|
|
26
|
-
def
|
26
|
+
def object_hash_from_json(json)
|
27
27
|
return nil unless json
|
28
28
|
|
29
29
|
entries = json.map do |key, value|
|
@@ -43,13 +43,21 @@ module Machinery
|
|
43
43
|
[key, value_converted]
|
44
44
|
end
|
45
45
|
|
46
|
-
|
46
|
+
Hash[entries]
|
47
|
+
end
|
48
|
+
|
49
|
+
def from_json(json)
|
50
|
+
new(object_hash_from_json(json))
|
47
51
|
end
|
48
52
|
end
|
49
53
|
|
50
54
|
attr_reader :attributes
|
51
55
|
|
52
56
|
def initialize(attrs = {})
|
57
|
+
set_attributes(attrs)
|
58
|
+
end
|
59
|
+
|
60
|
+
def set_attributes(attrs)
|
53
61
|
@attributes = attrs.inject({}) do |attributes, (key, value)|
|
54
62
|
key = key.to_sym if key.respond_to?(:to_sym)
|
55
63
|
|
data/lib/scope_mixin.rb
CHANGED
@@ -17,6 +17,24 @@
|
|
17
17
|
|
18
18
|
module Machinery
|
19
19
|
module ScopeMixin
|
20
|
+
def self.included(mod)
|
21
|
+
@scopes ||= []
|
22
|
+
@scopes.push(mod)
|
23
|
+
end
|
24
|
+
|
25
|
+
def self.all_scopes
|
26
|
+
@scopes
|
27
|
+
end
|
28
|
+
|
29
|
+
def self.class_for(scope_name)
|
30
|
+
all_scopes.each do |scope|
|
31
|
+
if scope.new.scope_name == scope_name
|
32
|
+
return scope
|
33
|
+
end
|
34
|
+
end
|
35
|
+
nil
|
36
|
+
end
|
37
|
+
|
20
38
|
attr_accessor :meta
|
21
39
|
|
22
40
|
def set_metadata(timestring, host)
|
data/lib/system_description.rb
CHANGED
@@ -62,7 +62,7 @@ class SystemDescription < Machinery::Object
|
|
62
62
|
end
|
63
63
|
|
64
64
|
begin
|
65
|
-
description = self.new(name,
|
65
|
+
description = self.new(name, create_scopes(json_hash), store)
|
66
66
|
rescue NameError
|
67
67
|
raise Machinery::Errors::SystemDescriptionIncompatible.new(name)
|
68
68
|
end
|
@@ -73,22 +73,22 @@ class SystemDescription < Machinery::Object
|
|
73
73
|
description
|
74
74
|
end
|
75
75
|
|
76
|
-
def
|
77
|
-
|
78
|
-
next if
|
76
|
+
def create_scopes(hash)
|
77
|
+
scopes = hash.map do |scope_name, scope_json|
|
78
|
+
next if scope_name == "meta"
|
79
79
|
|
80
|
-
|
81
|
-
|
80
|
+
scope_class = Machinery::ScopeMixin.class_for(scope_name)
|
81
|
+
scope_object = scope_class.from_json(scope_json)
|
82
82
|
|
83
83
|
# Set metadata
|
84
|
-
if hash["meta"] && hash["meta"][
|
85
|
-
|
84
|
+
if hash["meta"] && hash["meta"][scope_name]
|
85
|
+
scope_object.meta = Machinery::Object.from_json(hash["meta"][scope_name])
|
86
86
|
end
|
87
87
|
|
88
|
-
[
|
88
|
+
[scope_name, scope_object]
|
89
89
|
end.compact
|
90
90
|
|
91
|
-
Hash[
|
91
|
+
Hash[scopes]
|
92
92
|
end
|
93
93
|
|
94
94
|
private
|
@@ -172,16 +172,6 @@ class SystemDescription < Machinery::Object
|
|
172
172
|
self[scope] && self[scope].is_extractable? && self[scope].extracted
|
173
173
|
end
|
174
174
|
|
175
|
-
def os_object
|
176
|
-
assert_scopes("os")
|
177
|
-
|
178
|
-
begin
|
179
|
-
Os.for(self.os.name)
|
180
|
-
rescue Machinery::Errors::UnknownOs => e
|
181
|
-
raise Machinery::Errors::SystemDescriptionError.new(e)
|
182
|
-
end
|
183
|
-
end
|
184
|
-
|
185
175
|
def missing_files(scope, file_list)
|
186
176
|
file_list.map! { |file| File.join(file_store(scope), file) }
|
187
177
|
|
data/lib/upgrade_format_task.rb
CHANGED
@@ -49,7 +49,11 @@ class UpgradeFormatTask
|
|
49
49
|
Machinery::Ui.puts "No system descriptions were upgraded."
|
50
50
|
end
|
51
51
|
else
|
52
|
-
|
52
|
+
if migrations_done > 0
|
53
|
+
Machinery::Ui.puts "System description \"#{name}\" successfully upgraded."
|
54
|
+
else
|
55
|
+
Machinery::Ui.puts "System description \"#{name}\" is up to date, no upgrade necessary."
|
56
|
+
end
|
53
57
|
end
|
54
58
|
end
|
55
59
|
end
|
data/lib/version.rb
CHANGED
@@ -1,9 +1,10 @@
|
|
1
1
|
Contains the names and contents of all files which are not part of any RPM
|
2
2
|
package. The list of unmanaged files contains only plain files and
|
3
3
|
directories. Special files like device nodes, named pipes and Unix domain
|
4
|
-
sockets are ignored. The directories `/tmp`, `/var/tmp`,
|
5
|
-
|
6
|
-
list, no file or directory below it belongs to a
|
4
|
+
sockets are ignored. The directories `/tmp`, `/var/tmp`, `/.snapshots/`,
|
5
|
+
`/var/run` and special mounts like procfs and sysfs are ignored, too.
|
6
|
+
If a directory is in this list, no file or directory below it belongs to a
|
7
|
+
RPM package.
|
7
8
|
|
8
9
|
Meta data information of unmanaged files is only available if the files were
|
9
10
|
extracted during inspection.
|
@@ -47,8 +47,7 @@ class OsInspector < Inspector
|
|
47
47
|
os.version += get_additional_version(system)
|
48
48
|
summary = "Found operating system '#{os.name}' version '#{os.version}'."
|
49
49
|
else
|
50
|
-
|
51
|
-
summary = "Could not determine the operating system."
|
50
|
+
raise Machinery::Errors::UnknownOs
|
52
51
|
end
|
53
52
|
|
54
53
|
description.os = os
|
@@ -84,10 +83,9 @@ class OsInspector < Inspector
|
|
84
83
|
end
|
85
84
|
# return pretty_name as name as it contains the actual full length
|
86
85
|
# name instead of an abbreviation
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
)
|
86
|
+
os = Os.for(result["pretty_name"])
|
87
|
+
os.version = result["version"]
|
88
|
+
os
|
91
89
|
end
|
92
90
|
|
93
91
|
# checks for old suse standard: /etc/SuSE-release
|
@@ -111,6 +109,8 @@ class OsInspector < Inspector
|
|
111
109
|
if result["version"] && !patch.nil?
|
112
110
|
result["version"] = "#{result["version"]} SP#{patch}"
|
113
111
|
end
|
114
|
-
|
112
|
+
os = Os.for(result["name"])
|
113
|
+
os.version = result["version"]
|
114
|
+
os
|
115
115
|
end
|
116
116
|
end
|
@@ -154,14 +154,21 @@ class UnmanagedFilesInspector < Inspector
|
|
154
154
|
# "REPLACEMENT CHARACTER" (U+FFFD). That way we have both the raw data
|
155
155
|
# (which is needed in order to be able to access the files) and the cleaned
|
156
156
|
# string which can be safely used.
|
157
|
-
out =
|
158
|
-
|
159
|
-
|
160
|
-
|
161
|
-
:
|
162
|
-
:
|
163
|
-
|
164
|
-
|
157
|
+
out = ""
|
158
|
+
begin
|
159
|
+
out = system.run_command(
|
160
|
+
"/bin/bash",
|
161
|
+
stdin: cmd,
|
162
|
+
stdout: :capture,
|
163
|
+
disable_logging: true
|
164
|
+
).force_encoding("binary")
|
165
|
+
rescue Cheetah::ExecutionFailed => e
|
166
|
+
out = e.stdout
|
167
|
+
message = "Warning: The command find of the unmanaged-file inspector" \
|
168
|
+
" ran into an issue. The error output was:\n#{e.stderr}"
|
169
|
+
Machinery.logger.warn(message)
|
170
|
+
Machinery::Ui.warn(message)
|
171
|
+
end
|
165
172
|
|
166
173
|
|
167
174
|
# find creates three field per path
|
@@ -216,7 +223,7 @@ class UnmanagedFilesInspector < Inspector
|
|
216
223
|
|
217
224
|
tmp_file_store = "unmanaged_files.tmp"
|
218
225
|
final_file_store = "unmanaged_files"
|
219
|
-
|
226
|
+
mount_points = MountPoints.new(system)
|
220
227
|
|
221
228
|
ignore_list = [
|
222
229
|
"tmp",
|
@@ -226,7 +233,8 @@ class UnmanagedFilesInspector < Inspector
|
|
226
233
|
"var/lib/rpm",
|
227
234
|
".snapshots",
|
228
235
|
description.store.base_path.sub(/^\//, ""),
|
229
|
-
"proc"
|
236
|
+
"proc",
|
237
|
+
"boot"
|
230
238
|
]
|
231
239
|
|
232
240
|
# Information about users and groups are extracted by the according inspector
|
@@ -253,29 +261,38 @@ class UnmanagedFilesInspector < Inspector
|
|
253
261
|
|
254
262
|
rpm_files, rpm_dirs = extract_rpm_database(system)
|
255
263
|
|
256
|
-
mount_points = MountPoints.new(system)
|
257
264
|
mounts = mount_points.local
|
258
265
|
unmanaged_files = []
|
259
266
|
unmanaged_trees = []
|
260
267
|
excluded_files = []
|
261
268
|
unmanaged_links = {}
|
262
269
|
remote_dirs = mount_points.remote
|
270
|
+
special_dirs = mount_points.special
|
263
271
|
ignore_list.each do |ignore|
|
264
272
|
remote_dirs.delete_if { |e| e.start_with?(File.join("/", ignore, "/")) }
|
265
273
|
end
|
266
|
-
dirs_todo = [ "/" ]
|
267
|
-
start = start_depth
|
268
|
-
max = max_depth
|
269
|
-
find_count = 0
|
270
|
-
sub_tree_containing_remote_fs = []
|
271
274
|
excluded_files += remote_dirs
|
275
|
+
excluded_files += special_dirs
|
272
276
|
|
273
277
|
if !remote_dirs.empty?
|
274
|
-
warning = "The content of the following remote directories is ignored:
|
278
|
+
warning = "The content of the following remote directories is ignored:" \
|
279
|
+
"#{remote_dirs.uniq.join(", ")}."
|
280
|
+
Machinery.logger.warn(warning)
|
281
|
+
Machinery::Ui.warn(warning)
|
282
|
+
end
|
283
|
+
if !special_dirs.empty?
|
284
|
+
warning = "The content of the following special directories is ignored:" \
|
285
|
+
" #{special_dirs.uniq.join(", ")}."
|
275
286
|
Machinery.logger.warn(warning)
|
276
287
|
Machinery::Ui.warn(warning)
|
277
288
|
end
|
278
289
|
|
290
|
+
dirs_todo = ["/"]
|
291
|
+
start = start_depth
|
292
|
+
max = max_depth
|
293
|
+
find_count = 0
|
294
|
+
sub_tree_containing_remote_fs = []
|
295
|
+
|
279
296
|
while !dirs_todo.empty?
|
280
297
|
find_dir = dirs_todo.first
|
281
298
|
|
@@ -305,6 +322,9 @@ class UnmanagedFilesInspector < Inspector
|
|
305
322
|
while !unmanaged.empty?
|
306
323
|
dir = unmanaged.shift
|
307
324
|
|
325
|
+
# Ignore special mounts, e.g. procfs mounts in a chroot
|
326
|
+
next if special_dirs.include?(find_dir + dir)
|
327
|
+
|
308
328
|
# save into list of unmanaged trees
|
309
329
|
if !remote_dirs.include?(find_dir + dir)
|
310
330
|
unmanaged_trees << find_dir + dir
|
data/plugins/model/os_model.rb
CHANGED
@@ -15,6 +15,117 @@
|
|
15
15
|
# To contact SUSE about this file by physical or electronic mail,
|
16
16
|
# you may find current contact information at www.suse.com
|
17
17
|
|
18
|
-
class
|
18
|
+
class Os < Machinery::Object
|
19
19
|
include Machinery::ScopeMixin
|
20
|
+
|
21
|
+
def self.descendants
|
22
|
+
ObjectSpace.each_object(::Class).select { |klass| klass < self }
|
23
|
+
end
|
24
|
+
|
25
|
+
def self.for(os_name)
|
26
|
+
descendants.each do |os_class|
|
27
|
+
if os_name == os_class.canonical_name
|
28
|
+
os = os_class.new
|
29
|
+
os.name = os_name
|
30
|
+
return os
|
31
|
+
end
|
32
|
+
end
|
33
|
+
OsUnknown.new
|
34
|
+
end
|
35
|
+
|
36
|
+
def self.from_json(json)
|
37
|
+
scope_object = self.for(json["name"])
|
38
|
+
scope_object.set_attributes(object_hash_from_json(json))
|
39
|
+
scope_object
|
40
|
+
end
|
41
|
+
|
42
|
+
def scope_name
|
43
|
+
"os"
|
44
|
+
end
|
45
|
+
|
46
|
+
def self.buildable_systems
|
47
|
+
[]
|
48
|
+
end
|
49
|
+
|
50
|
+
def self.module_dependencies
|
51
|
+
{}
|
52
|
+
end
|
53
|
+
|
54
|
+
def self.can_run_machinery?
|
55
|
+
true
|
56
|
+
end
|
57
|
+
|
58
|
+
def self.supported_host_systems
|
59
|
+
descendants.select { |os| os.can_run_machinery? }
|
60
|
+
end
|
61
|
+
|
62
|
+
def can_run_machinery?
|
63
|
+
self.class.can_run_machinery?
|
64
|
+
end
|
65
|
+
|
66
|
+
def can_build?(os)
|
67
|
+
self.class.buildable_systems.include?(os.class)
|
68
|
+
end
|
69
|
+
|
70
|
+
def module_required_by_package(package)
|
71
|
+
self.class.module_dependencies[package]
|
72
|
+
end
|
73
|
+
|
74
|
+
def canonical_name
|
75
|
+
self.class.canonical_name
|
76
|
+
end
|
77
|
+
end
|
78
|
+
|
79
|
+
class OsUnknown < Os
|
80
|
+
def self.canonical_name
|
81
|
+
"Unknown OS"
|
82
|
+
end
|
83
|
+
|
84
|
+
def self.can_run_machinery?
|
85
|
+
false
|
86
|
+
end
|
87
|
+
end
|
88
|
+
|
89
|
+
class OsSles11 < Os
|
90
|
+
def self.canonical_name
|
91
|
+
"SUSE Linux Enterprise Server 11"
|
92
|
+
end
|
93
|
+
|
94
|
+
def self.can_run_machinery?
|
95
|
+
false
|
96
|
+
end
|
97
|
+
end
|
98
|
+
|
99
|
+
class OsSles12 < Os
|
100
|
+
def self.canonical_name
|
101
|
+
"SUSE Linux Enterprise Server 12"
|
102
|
+
end
|
103
|
+
|
104
|
+
def self.buildable_systems
|
105
|
+
[OsSles12]
|
106
|
+
end
|
107
|
+
|
108
|
+
def self.module_dependencies
|
109
|
+
{ "python-glanceclient" => "Public Cloud Module" }
|
110
|
+
end
|
111
|
+
end
|
112
|
+
|
113
|
+
class OsOpenSuse13_1 < Os
|
114
|
+
def self.canonical_name
|
115
|
+
"openSUSE 13.1 (Bottle)"
|
116
|
+
end
|
117
|
+
|
118
|
+
def self.buildable_systems
|
119
|
+
[OsSles11, OsOpenSuse13_1]
|
120
|
+
end
|
121
|
+
end
|
122
|
+
|
123
|
+
class OsOpenSuse13_2 < Os
|
124
|
+
def self.canonical_name
|
125
|
+
"openSUSE 13.2 (Harlequin)"
|
126
|
+
end
|
127
|
+
|
128
|
+
def self.buildable_systems
|
129
|
+
[OsSles11, OsOpenSuse13_1, OsOpenSuse13_2]
|
130
|
+
end
|
20
131
|
end
|
@@ -17,6 +17,15 @@
|
|
17
17
|
|
18
18
|
|
19
19
|
class Service < Machinery::Object
|
20
|
+
def enabled?
|
21
|
+
# systemd vs sysvinit
|
22
|
+
state == "enabled" || state == "on"
|
23
|
+
end
|
24
|
+
|
25
|
+
def disabled?
|
26
|
+
# systemd vs sysvinit
|
27
|
+
state == "disabled" || state == "off"
|
28
|
+
end
|
20
29
|
end
|
21
30
|
|
22
31
|
class ServiceList < Machinery::Array
|
@@ -54,4 +54,13 @@ end
|
|
54
54
|
class UnmanagedFilesScope < FileScope
|
55
55
|
include Machinery::ScopeMixin
|
56
56
|
has_property :files, class: UnmanagedFileList
|
57
|
+
|
58
|
+
def compare_with(other)
|
59
|
+
if extracted != other.extracted
|
60
|
+
Machinery::Ui.warn("Warning: Comparing extracted with unextracted" \
|
61
|
+
" unmanaged files. Only common attributes are considered.")
|
62
|
+
end
|
63
|
+
|
64
|
+
super
|
65
|
+
end
|
57
66
|
end
|
@@ -39,12 +39,14 @@ class ConfigFilesRenderer < Renderer
|
|
39
39
|
files = @system_description["config_files"].files
|
40
40
|
if files
|
41
41
|
files.each do |p|
|
42
|
+
item_content = "#{p.name} (#{p.package_name}-#{p.package_version}, " \
|
43
|
+
"#{p.changes.join(", ")})"
|
42
44
|
if @options[:show_diffs] && p.changes.include?("md5")
|
43
|
-
item
|
45
|
+
item item_content do
|
44
46
|
render_diff_file(diffs_dir, p.name)
|
45
47
|
end
|
46
48
|
else
|
47
|
-
item
|
49
|
+
item item_content
|
48
50
|
end
|
49
51
|
end
|
50
52
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: machinery-tool
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.1.
|
4
|
+
version: 1.1.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- SUSE
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2014-
|
11
|
+
date: 2014-12-03 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: cheetah
|
@@ -202,7 +202,6 @@ files:
|
|
202
202
|
- lib/logged_cheetah.rb
|
203
203
|
- lib/renderer.rb
|
204
204
|
- lib/remote_system.rb
|
205
|
-
- lib/kiwi_export_task.rb
|
206
205
|
- lib/kiwi_config.rb
|
207
206
|
- lib/upgrade_format_task.rb
|
208
207
|
- lib/tarball.rb
|
@@ -211,7 +210,6 @@ files:
|
|
211
210
|
- lib/renderer_helper.rb
|
212
211
|
- lib/analyze_config_file_diffs_task.rb
|
213
212
|
- lib/config.rb
|
214
|
-
- lib/os.rb
|
215
213
|
- lib/version.rb
|
216
214
|
- lib/system.rb
|
217
215
|
- lib/object.rb
|
@@ -219,6 +217,7 @@ files:
|
|
219
217
|
- lib/config_task.rb
|
220
218
|
- lib/remove_task.rb
|
221
219
|
- lib/system_description.rb
|
220
|
+
- lib/autoyast.rb
|
222
221
|
- lib/zypper.rb
|
223
222
|
- lib/constants.rb
|
224
223
|
- lib/mountpoints.rb
|
@@ -226,6 +225,7 @@ files:
|
|
226
225
|
- lib/rpm.rb
|
227
226
|
- lib/array.rb
|
228
227
|
- lib/changed_rpm_files_helper.rb
|
228
|
+
- lib/export_task.rb
|
229
229
|
- lib/copy_task.rb
|
230
230
|
- lib/build_task.rb
|
231
231
|
- lib/local_system.rb
|
data/lib/os.rb
DELETED
@@ -1,90 +0,0 @@
|
|
1
|
-
# Copyright (c) 2013-2014 SUSE LLC
|
2
|
-
#
|
3
|
-
# This program is free software; you can redistribute it and/or
|
4
|
-
# modify it under the terms of version 3 of the GNU General Public License as
|
5
|
-
# published by the Free Software Foundation.
|
6
|
-
#
|
7
|
-
# This program is distributed in the hope that it will be useful,
|
8
|
-
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
9
|
-
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
10
|
-
# GNU General Public License for more details.
|
11
|
-
#
|
12
|
-
# You should have received a copy of the GNU General Public License
|
13
|
-
# along with this program; if not, contact SUSE LLC.
|
14
|
-
#
|
15
|
-
# To contact SUSE about this file by physical or electronic mail,
|
16
|
-
# you may find current contact information at www.suse.com
|
17
|
-
|
18
|
-
class Os
|
19
|
-
attr_reader :can_build, :name
|
20
|
-
|
21
|
-
def self.descendants
|
22
|
-
ObjectSpace.each_object(::Class).select { |klass| klass < self }
|
23
|
-
end
|
24
|
-
|
25
|
-
def self.for(os_name)
|
26
|
-
descendants.each do |os_class|
|
27
|
-
os_object = os_class.new
|
28
|
-
if os_name == os_object.name
|
29
|
-
return os_object
|
30
|
-
end
|
31
|
-
end
|
32
|
-
raise Machinery::Errors::UnknownOs.new("Unknown OS: '#{os_name}'")
|
33
|
-
end
|
34
|
-
|
35
|
-
def self.supported_host_systems
|
36
|
-
descendants.select { |os| os.new.can_run_machinery? }
|
37
|
-
end
|
38
|
-
|
39
|
-
def can_build?(os)
|
40
|
-
if os.is_a?(Class)
|
41
|
-
return @can_build.include?(os)
|
42
|
-
else
|
43
|
-
return @can_build.include?(os.class)
|
44
|
-
end
|
45
|
-
end
|
46
|
-
|
47
|
-
def module_required_by_package(package)
|
48
|
-
if @module_required_by_package
|
49
|
-
return @module_required_by_package[package]
|
50
|
-
end
|
51
|
-
end
|
52
|
-
|
53
|
-
def can_run_machinery?
|
54
|
-
@can_run_machinery
|
55
|
-
end
|
56
|
-
end
|
57
|
-
|
58
|
-
class OsSles11 < Os
|
59
|
-
def initialize
|
60
|
-
@can_build = []
|
61
|
-
@name = "SUSE Linux Enterprise Server 11"
|
62
|
-
end
|
63
|
-
end
|
64
|
-
|
65
|
-
class OsSles12 < Os
|
66
|
-
def initialize
|
67
|
-
@can_build = [OsSles12]
|
68
|
-
@name = "SUSE Linux Enterprise Server 12"
|
69
|
-
@module_required_by_package = {
|
70
|
-
"python-glanceclient" => "Public Cloud Module"
|
71
|
-
}
|
72
|
-
@can_run_machinery = true
|
73
|
-
end
|
74
|
-
end
|
75
|
-
|
76
|
-
class OsOpenSuse13_1 < Os
|
77
|
-
def initialize
|
78
|
-
@can_build = [OsSles11, OsOpenSuse13_1]
|
79
|
-
@name = "openSUSE 13.1 (Bottle)"
|
80
|
-
@can_run_machinery = true
|
81
|
-
end
|
82
|
-
end
|
83
|
-
|
84
|
-
class OsOpenSuse13_2 < Os
|
85
|
-
def initialize
|
86
|
-
@can_build = [OsSles11, OsOpenSuse13_1, OsOpenSuse13_2]
|
87
|
-
@name = "openSUSE 13.2 (Harlequin)"
|
88
|
-
@can_run_machinery = true
|
89
|
-
end
|
90
|
-
end
|