train 2.1.7 → 2.1.13
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/lib/train.rb +20 -20
- data/lib/train/errors.rb +1 -1
- data/lib/train/extras.rb +2 -2
- data/lib/train/extras/command_wrapper.rb +24 -24
- data/lib/train/extras/stat.rb +27 -27
- data/lib/train/file.rb +30 -30
- data/lib/train/file/local.rb +8 -8
- data/lib/train/file/local/unix.rb +5 -5
- data/lib/train/file/local/windows.rb +1 -1
- data/lib/train/file/remote.rb +8 -8
- data/lib/train/file/remote/aix.rb +1 -1
- data/lib/train/file/remote/linux.rb +2 -2
- data/lib/train/file/remote/qnx.rb +8 -8
- data/lib/train/file/remote/unix.rb +10 -14
- data/lib/train/file/remote/windows.rb +5 -5
- data/lib/train/globals.rb +1 -1
- data/lib/train/options.rb +8 -8
- data/lib/train/platforms.rb +8 -8
- data/lib/train/platforms/common.rb +1 -1
- data/lib/train/platforms/detect/helpers/os_common.rb +36 -32
- data/lib/train/platforms/detect/helpers/os_linux.rb +12 -12
- data/lib/train/platforms/detect/helpers/os_windows.rb +27 -29
- data/lib/train/platforms/detect/scanner.rb +4 -4
- data/lib/train/platforms/detect/specifications/api.rb +8 -8
- data/lib/train/platforms/detect/specifications/os.rb +252 -252
- data/lib/train/platforms/detect/uuid.rb +5 -7
- data/lib/train/platforms/platform.rb +9 -5
- data/lib/train/plugin_test_helper.rb +12 -12
- data/lib/train/plugins.rb +5 -5
- data/lib/train/plugins/base_connection.rb +13 -13
- data/lib/train/plugins/transport.rb +7 -7
- data/lib/train/transports/azure.rb +23 -23
- data/lib/train/transports/cisco_ios_connection.rb +20 -20
- data/lib/train/transports/clients/azure/graph_rbac.rb +2 -2
- data/lib/train/transports/clients/azure/vault.rb +4 -4
- data/lib/train/transports/docker.rb +4 -10
- data/lib/train/transports/gcp.rb +23 -23
- data/lib/train/transports/helpers/azure/file_credentials.rb +8 -8
- data/lib/train/transports/helpers/azure/file_parser.rb +1 -1
- data/lib/train/transports/helpers/azure/subscription_number_file_parser.rb +1 -1
- data/lib/train/transports/local.rb +22 -22
- data/lib/train/transports/mock.rb +33 -35
- data/lib/train/transports/ssh.rb +47 -47
- data/lib/train/transports/ssh_connection.rb +28 -28
- data/lib/train/transports/vmware.rb +32 -34
- data/lib/train/transports/winrm.rb +37 -37
- data/lib/train/transports/winrm_connection.rb +12 -12
- data/lib/train/version.rb +1 -1
- metadata +2 -2
@@ -1,6 +1,6 @@
|
|
1
1
|
# encoding: utf-8
|
2
2
|
|
3
|
-
require
|
3
|
+
require "azure_graph_rbac"
|
4
4
|
|
5
5
|
# Wrapper class for ::Azure::GraphRbac::Profiles::Latest::Client allowing custom configuration,
|
6
6
|
# for example, defining additional settings for the ::MsRestAzure::ApplicationTokenProvider.
|
@@ -20,7 +20,7 @@ class GraphRbac
|
|
20
20
|
credentials[:tenant_id],
|
21
21
|
credentials[:client_id],
|
22
22
|
credentials[:client_secret],
|
23
|
-
settings
|
23
|
+
settings
|
24
24
|
)
|
25
25
|
end
|
26
26
|
|
@@ -1,15 +1,15 @@
|
|
1
1
|
# encoding: utf-8
|
2
2
|
|
3
|
-
require
|
3
|
+
require "azure_mgmt_key_vault"
|
4
4
|
|
5
5
|
# Wrapper class for ::Azure::KeyVault::Profiles::Latest::Mgmt::Client allowing custom configuration,
|
6
6
|
# for example, defining additional settings for the ::MsRestAzure::ApplicationTokenProvider.
|
7
7
|
class Vault
|
8
8
|
AUTH_ENDPOINT = MsRestAzure::AzureEnvironments::AzureCloud.active_directory_endpoint_url
|
9
|
-
RESOURCE_ENDPOINT =
|
9
|
+
RESOURCE_ENDPOINT = "https://vault.azure.net".freeze
|
10
10
|
|
11
11
|
def self.client(vault_name, credentials)
|
12
|
-
raise ::Train::UserError,
|
12
|
+
raise ::Train::UserError, "Vault Name cannot be nil" if vault_name.nil?
|
13
13
|
|
14
14
|
credentials[:credentials] = ::MsRest::TokenCredentials.new(provider(credentials))
|
15
15
|
credentials[:base_url] = api_endpoint(vault_name)
|
@@ -22,7 +22,7 @@ class Vault
|
|
22
22
|
credentials[:tenant_id],
|
23
23
|
credentials[:client_id],
|
24
24
|
credentials[:client_secret],
|
25
|
-
settings
|
25
|
+
settings
|
26
26
|
)
|
27
27
|
end
|
28
28
|
|
@@ -1,13 +1,8 @@
|
|
1
|
-
|
2
|
-
#
|
3
|
-
# Author:: Dominik Richter
|
4
|
-
# Author:: Christoph Hartmann
|
5
|
-
|
6
|
-
require 'docker'
|
1
|
+
require "docker"
|
7
2
|
|
8
3
|
module Train::Transports
|
9
4
|
class Docker < Train.plugin(1)
|
10
|
-
name
|
5
|
+
name "docker"
|
11
6
|
|
12
7
|
include_options Train::Extras::CommandWrapper
|
13
8
|
option :host, required: true
|
@@ -59,10 +54,9 @@ class Train::Transports::Docker
|
|
59
54
|
super(conf)
|
60
55
|
@id = options[:host]
|
61
56
|
@container = ::Docker::Container.get(@id) ||
|
62
|
-
|
57
|
+
raise("Can't find Docker container #{@id}")
|
63
58
|
@cmd_wrapper = nil
|
64
59
|
@cmd_wrapper = CommandWrapper.load(self, @options)
|
65
|
-
self
|
66
60
|
end
|
67
61
|
|
68
62
|
def close
|
@@ -93,7 +87,7 @@ class Train::Transports::Docker
|
|
93
87
|
cmd = @cmd_wrapper.run(cmd) unless @cmd_wrapper.nil?
|
94
88
|
stdout, stderr, exit_status = @container.exec(
|
95
89
|
[
|
96
|
-
|
90
|
+
"/bin/sh", "-c", cmd
|
97
91
|
])
|
98
92
|
CommandResult.new(stdout.join, stderr.join, exit_status)
|
99
93
|
rescue ::Docker::Error::DockerError => _
|
data/lib/train/transports/gcp.rb
CHANGED
@@ -1,21 +1,21 @@
|
|
1
1
|
# encoding: utf-8
|
2
2
|
|
3
|
-
require
|
4
|
-
require
|
5
|
-
require
|
6
|
-
require
|
7
|
-
require
|
8
|
-
require
|
9
|
-
require
|
10
|
-
require
|
3
|
+
require "train/plugins"
|
4
|
+
require "google/apis"
|
5
|
+
require "google/apis/cloudresourcemanager_v1"
|
6
|
+
require "google/apis/compute_v1"
|
7
|
+
require "google/apis/storage_v1"
|
8
|
+
require "google/apis/iam_v1"
|
9
|
+
require "google/apis/admin_directory_v1"
|
10
|
+
require "googleauth"
|
11
11
|
|
12
12
|
module Train::Transports
|
13
13
|
class Gcp < Train.plugin(1)
|
14
|
-
name
|
14
|
+
name "gcp"
|
15
15
|
|
16
16
|
# GCP will look automatically for the below env var for service accounts etc. :
|
17
17
|
option :google_application_credentials, required: false do
|
18
|
-
ENV[
|
18
|
+
ENV["GOOGLE_APPLICATION_CREDENTIALS"]
|
19
19
|
end
|
20
20
|
# see https://cloud.google.com/docs/authentication/production#providing_credentials_to_your_application
|
21
21
|
# In the absence of this, the client is expected to have already set up local credentials via:
|
@@ -25,10 +25,10 @@ module Train::Transports
|
|
25
25
|
# https://cloud.google.com/compute/docs/regions-zones/changing-default-zone-region
|
26
26
|
# can also specify project via env var:
|
27
27
|
option :google_cloud_project, required: false do
|
28
|
-
ENV[
|
28
|
+
ENV["GOOGLE_CLOUD_PROJECT"]
|
29
29
|
end
|
30
30
|
option :google_super_admin_email, required: false do
|
31
|
-
ENV[
|
31
|
+
ENV["GOOGLE_SUPER_ADMIN_EMAIL"]
|
32
32
|
end
|
33
33
|
|
34
34
|
def connection(_ = nil)
|
@@ -40,7 +40,7 @@ module Train::Transports
|
|
40
40
|
super(options)
|
41
41
|
|
42
42
|
# additional GCP platform metadata
|
43
|
-
release = Gem.loaded_specs[
|
43
|
+
release = Gem.loaded_specs["google-api-client"].version
|
44
44
|
@platform_details = { release: "google-api-client-v#{release}" }
|
45
45
|
|
46
46
|
# Initialize the client object cache
|
@@ -51,7 +51,7 @@ module Train::Transports
|
|
51
51
|
end
|
52
52
|
|
53
53
|
def platform
|
54
|
-
force_platform!(
|
54
|
+
force_platform!("gcp", @platform_details)
|
55
55
|
end
|
56
56
|
|
57
57
|
# Instantiate some named classes for ease of use
|
@@ -72,7 +72,7 @@ module Train::Transports
|
|
72
72
|
end
|
73
73
|
|
74
74
|
def gcp_admin_client
|
75
|
-
scopes = [
|
75
|
+
scopes = ["https://www.googleapis.com/auth/admin.directory.user.readonly"]
|
76
76
|
authorization = Google::Auth.get_application_default(scopes).dup
|
77
77
|
# Use of the Admin API requires delegation (impersonation). An email address of a Super Admin in
|
78
78
|
# the G Suite account may be required.
|
@@ -88,13 +88,13 @@ module Train::Transports
|
|
88
88
|
end
|
89
89
|
|
90
90
|
def connect
|
91
|
-
ENV[
|
92
|
-
ENV[
|
91
|
+
ENV["GOOGLE_APPLICATION_CREDENTIALS"] = @options[:google_application_credentials] if @options[:google_application_credentials]
|
92
|
+
ENV["GOOGLE_CLOUD_PROJECT"] = @options[:google_cloud_project] if @options[:google_cloud_project]
|
93
93
|
# GCP initialization
|
94
|
-
scopes = [
|
95
|
-
|
94
|
+
scopes = ["https://www.googleapis.com/auth/cloud-platform",
|
95
|
+
"https://www.googleapis.com/auth/compute"]
|
96
96
|
authorization = Google::Auth.get_application_default(scopes)
|
97
|
-
Google::Apis::ClientOptions.default.application_name =
|
97
|
+
Google::Apis::ClientOptions.default.application_name = "chef-inspec-train"
|
98
98
|
Google::Apis::ClientOptions.default.application_version = Train::VERSION
|
99
99
|
Google::Apis::RequestOptions.default.authorization = authorization
|
100
100
|
end
|
@@ -104,11 +104,11 @@ module Train::Transports
|
|
104
104
|
end
|
105
105
|
|
106
106
|
def unique_identifier
|
107
|
-
unique_id =
|
107
|
+
unique_id = "default"
|
108
108
|
# use auth client_id for users (issuer is nil)
|
109
|
-
unique_id=gcp_iam_client.request_options.authorization.client_id unless gcp_iam_client.request_options.authorization.client_id.nil?
|
109
|
+
unique_id = gcp_iam_client.request_options.authorization.client_id unless gcp_iam_client.request_options.authorization.client_id.nil?
|
110
110
|
# for service account credentials (client_id is nil)
|
111
|
-
unique_id=gcp_iam_client.request_options.authorization.issuer unless gcp_iam_client.request_options.authorization.issuer.nil?
|
111
|
+
unique_id = gcp_iam_client.request_options.authorization.issuer unless gcp_iam_client.request_options.authorization.issuer.nil?
|
112
112
|
unique_id
|
113
113
|
end
|
114
114
|
end
|
@@ -1,9 +1,9 @@
|
|
1
1
|
# encoding: utf-8
|
2
2
|
|
3
|
-
require
|
4
|
-
require
|
5
|
-
require
|
6
|
-
require
|
3
|
+
require "inifile"
|
4
|
+
require "train/transports/helpers/azure/file_parser"
|
5
|
+
require "train/transports/helpers/azure/subscription_number_file_parser"
|
6
|
+
require "train/transports/helpers/azure/subscription_id_file_parser"
|
7
7
|
|
8
8
|
module Train::Transports
|
9
9
|
module Helpers
|
@@ -13,7 +13,7 @@ module Train::Transports
|
|
13
13
|
return {} if credentials_file.nil?
|
14
14
|
return {} unless ::File.readable?(credentials_file)
|
15
15
|
credentials = IniFile.load(::File.expand_path(credentials_file))
|
16
|
-
subscription_id = parser(subscription_id, ENV[
|
16
|
+
subscription_id = parser(subscription_id, ENV["AZURE_SUBSCRIPTION_NUMBER"], credentials).subscription_id
|
17
17
|
creds(subscription_id, credentials)
|
18
18
|
end
|
19
19
|
|
@@ -30,9 +30,9 @@ module Train::Transports
|
|
30
30
|
def self.creds(subscription_id, credentials)
|
31
31
|
{
|
32
32
|
subscription_id: subscription_id,
|
33
|
-
tenant_id:
|
34
|
-
client_id:
|
35
|
-
client_secret:
|
33
|
+
tenant_id: credentials[subscription_id]["tenant_id"],
|
34
|
+
client_id: credentials[subscription_id]["client_id"],
|
35
|
+
client_secret: credentials[subscription_id]["client_secret"],
|
36
36
|
}
|
37
37
|
end
|
38
38
|
end
|
@@ -13,7 +13,7 @@ module Train::Transports
|
|
13
13
|
def validate!
|
14
14
|
return if @credentials.sections.count == 1
|
15
15
|
|
16
|
-
raise
|
16
|
+
raise "Credentials file must have one entry. Check your credentials file. If you have more than one entry set AZURE_SUBSCRIPTION_ID environment variable."
|
17
17
|
end
|
18
18
|
|
19
19
|
def subscription_id
|
@@ -3,13 +3,13 @@
|
|
3
3
|
# author: Dominik Richter
|
4
4
|
# author: Christoph Hartmann
|
5
5
|
|
6
|
-
require
|
7
|
-
require
|
8
|
-
require
|
6
|
+
require "train/plugins"
|
7
|
+
require "train/errors"
|
8
|
+
require "mixlib/shellout"
|
9
9
|
|
10
10
|
module Train::Transports
|
11
11
|
class Local < Train.plugin(1)
|
12
|
-
name
|
12
|
+
name "local"
|
13
13
|
|
14
14
|
class PipeError < Train::TransportError; end
|
15
15
|
|
@@ -33,7 +33,7 @@ module Train::Transports
|
|
33
33
|
end
|
34
34
|
|
35
35
|
def uri
|
36
|
-
|
36
|
+
"local://"
|
37
37
|
end
|
38
38
|
|
39
39
|
private
|
@@ -41,10 +41,10 @@ module Train::Transports
|
|
41
41
|
def select_runner(options)
|
42
42
|
if os.windows?
|
43
43
|
# Force a 64 bit poweshell if needed
|
44
|
-
if RUBY_PLATFORM ==
|
44
|
+
if RUBY_PLATFORM == "i386-mingw32" && os.arch == "x86_64"
|
45
45
|
powershell_cmd = "#{ENV['SystemRoot']}\\sysnative\\WindowsPowerShell\\v1.0\\powershell.exe"
|
46
46
|
else
|
47
|
-
powershell_cmd =
|
47
|
+
powershell_cmd = "powershell"
|
48
48
|
end
|
49
49
|
|
50
50
|
# Attempt to use a named pipe but fallback to ShellOut if that fails
|
@@ -67,7 +67,7 @@ module Train::Transports
|
|
67
67
|
when :windows_shell
|
68
68
|
WindowsShellRunner.new
|
69
69
|
else
|
70
|
-
|
70
|
+
raise "Runner type `#{command_runner}` not supported"
|
71
71
|
end
|
72
72
|
end
|
73
73
|
|
@@ -82,7 +82,7 @@ module Train::Transports
|
|
82
82
|
res.run_command
|
83
83
|
Local::CommandResult.new(res.stdout, res.stderr, res.exitstatus)
|
84
84
|
rescue Errno::ENOENT => _
|
85
|
-
CommandResult.new(
|
85
|
+
CommandResult.new("", "", 1)
|
86
86
|
end
|
87
87
|
|
88
88
|
def file_via_connection(path)
|
@@ -112,10 +112,10 @@ module Train::Transports
|
|
112
112
|
end
|
113
113
|
|
114
114
|
class WindowsShellRunner
|
115
|
-
require
|
116
|
-
require
|
115
|
+
require "json"
|
116
|
+
require "base64"
|
117
117
|
|
118
|
-
def initialize(powershell_cmd =
|
118
|
+
def initialize(powershell_cmd = "powershell")
|
119
119
|
@powershell_cmd = powershell_cmd
|
120
120
|
end
|
121
121
|
|
@@ -124,7 +124,7 @@ module Train::Transports
|
|
124
124
|
script = "$ProgressPreference='SilentlyContinue';" + script
|
125
125
|
|
126
126
|
# Encode script so PowerShell can use it
|
127
|
-
script = script.encode(
|
127
|
+
script = script.encode("UTF-16LE", "UTF-8")
|
128
128
|
base64_script = Base64.strict_encode64(script)
|
129
129
|
|
130
130
|
cmd = "#{@powershell_cmd} -NoProfile -EncodedCommand #{base64_script}"
|
@@ -136,14 +136,14 @@ module Train::Transports
|
|
136
136
|
end
|
137
137
|
|
138
138
|
class WindowsPipeRunner
|
139
|
-
require
|
140
|
-
require
|
141
|
-
require
|
139
|
+
require "json"
|
140
|
+
require "base64"
|
141
|
+
require "securerandom"
|
142
142
|
|
143
|
-
def initialize(powershell_cmd =
|
143
|
+
def initialize(powershell_cmd = "powershell")
|
144
144
|
@powershell_cmd = powershell_cmd
|
145
145
|
@pipe = acquire_pipe
|
146
|
-
|
146
|
+
raise PipeError if @pipe.nil?
|
147
147
|
end
|
148
148
|
|
149
149
|
def run_command(cmd)
|
@@ -167,7 +167,7 @@ module Train::Transports
|
|
167
167
|
# PowerShell needs time to create pipe.
|
168
168
|
100.times do
|
169
169
|
begin
|
170
|
-
pipe = open("//./pipe/#{pipe_name}",
|
170
|
+
pipe = open("//./pipe/#{pipe_name}", "r+")
|
171
171
|
break
|
172
172
|
rescue
|
173
173
|
sleep 0.1
|
@@ -178,7 +178,7 @@ module Train::Transports
|
|
178
178
|
end
|
179
179
|
|
180
180
|
def start_pipe_server(pipe_name)
|
181
|
-
require
|
181
|
+
require "win32/process"
|
182
182
|
|
183
183
|
script = <<-EOF
|
184
184
|
$ErrorActionPreference = 'Stop'
|
@@ -213,14 +213,14 @@ module Train::Transports
|
|
213
213
|
}
|
214
214
|
EOF
|
215
215
|
|
216
|
-
utf8_script = script.encode(
|
216
|
+
utf8_script = script.encode("UTF-16LE", "UTF-8")
|
217
217
|
base64_script = Base64.strict_encode64(utf8_script)
|
218
218
|
cmd = "#{@powershell_cmd} -NoProfile -ExecutionPolicy bypass -NonInteractive -EncodedCommand #{base64_script}"
|
219
219
|
|
220
220
|
server_pid = Process.create(command_line: cmd).process_id
|
221
221
|
|
222
222
|
# Ensure process is killed when the Train process exits
|
223
|
-
at_exit { Process.kill(
|
223
|
+
at_exit { Process.kill("KILL", server_pid) }
|
224
224
|
end
|
225
225
|
end
|
226
226
|
end
|
@@ -1,11 +1,9 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
require 'train/plugins'
|
4
|
-
require 'digest'
|
1
|
+
require "train/plugins"
|
2
|
+
require "digest"
|
5
3
|
|
6
4
|
module Train::Transports
|
7
5
|
class Mock < Train.plugin(1)
|
8
|
-
name
|
6
|
+
name "mock"
|
9
7
|
|
10
8
|
def initialize(conf = nil)
|
11
9
|
@conf = conf || {}
|
@@ -17,39 +15,39 @@ module Train::Transports
|
|
17
15
|
end
|
18
16
|
|
19
17
|
def to_s
|
20
|
-
|
18
|
+
"Mock Transport"
|
21
19
|
end
|
22
20
|
|
23
21
|
private
|
24
22
|
|
25
23
|
def trace_calls
|
26
24
|
interface_methods = {
|
27
|
-
|
25
|
+
"Train::Transports::Mock" =>
|
28
26
|
Train::Transports::Mock.instance_methods(false),
|
29
|
-
|
27
|
+
"Train::Transports::Mock::Connection" =>
|
30
28
|
Connection.instance_methods(false),
|
31
|
-
|
29
|
+
"Train::Transports::Mock::Connection::File" =>
|
32
30
|
Connection::FileCommon.instance_methods(false),
|
33
|
-
|
31
|
+
"Train::Transports::Mock::Connection::OS" =>
|
34
32
|
Train::Platform.instance_methods(false),
|
35
33
|
}
|
36
34
|
|
37
35
|
# rubocop:disable Metrics/ParameterLists
|
38
36
|
# rubocop:disable Lint/Eval
|
39
|
-
set_trace_func
|
40
|
-
unless classname.to_s.start_with?(
|
41
|
-
|
42
|
-
|
37
|
+
set_trace_func(proc { |event, _file, _line, id, binding, classname|
|
38
|
+
unless classname.to_s.start_with?("Train::Transports::Mock") &&
|
39
|
+
(event == "call") &&
|
40
|
+
interface_methods[classname.to_s].include?(id)
|
43
41
|
next
|
44
42
|
end
|
45
43
|
# kindly borrowed from the wonderful simple-tracer by matugm
|
46
44
|
arg_names = eval(
|
47
|
-
|
45
|
+
"method(__method__).parameters.map { |arg| arg[1].to_s }",
|
48
46
|
binding)
|
49
|
-
args = eval("#{arg_names}.map { |arg| eval(arg) }", binding).join(
|
50
|
-
prefix =
|
47
|
+
args = eval("#{arg_names}.map { |arg| eval(arg) }", binding).join(", ")
|
48
|
+
prefix = "-" * (classname.to_s.count(":") - 2) + "> "
|
51
49
|
puts("#{prefix}#{id} #{args}")
|
52
|
-
}
|
50
|
+
})
|
53
51
|
# rubocop:enable all
|
54
52
|
end
|
55
53
|
end
|
@@ -67,14 +65,14 @@ class Train::Transports::Mock
|
|
67
65
|
end
|
68
66
|
|
69
67
|
def uri
|
70
|
-
|
68
|
+
"mock://"
|
71
69
|
end
|
72
70
|
|
73
71
|
def mock_os(value = {})
|
74
72
|
# if a user passes a nil value, set to an empty hash so the merge still succeeds
|
75
73
|
value ||= {}
|
76
|
-
value.each { |k, v| value[k] =
|
77
|
-
value = { name:
|
74
|
+
value.each { |k, v| value[k] = "unknown" if v.nil? }
|
75
|
+
value = { name: "mock", family: "mock", release: "unknown", arch: "unknown" }.merge(value)
|
78
76
|
|
79
77
|
platform = Train::Platforms.name(value[:name])
|
80
78
|
platform.find_family_hierarchy
|
@@ -100,26 +98,26 @@ class Train::Transports::Mock
|
|
100
98
|
end
|
101
99
|
|
102
100
|
def mock_command(cmd, stdout = nil, stderr = nil, exit_status = 0)
|
103
|
-
@cache[:command][cmd] = Command.new(stdout ||
|
101
|
+
@cache[:command][cmd] = Command.new(stdout || "", stderr || "", exit_status)
|
104
102
|
end
|
105
103
|
|
106
104
|
def command_not_found(cmd)
|
107
105
|
if @options[:verbose]
|
108
|
-
|
109
|
-
|
110
|
-
|
106
|
+
$stderr.puts("Command not mocked:")
|
107
|
+
$stderr.puts(" " + cmd.to_s.split("\n").join("\n "))
|
108
|
+
$stderr.puts(" SHA: " + Digest::SHA256.hexdigest(cmd.to_s))
|
111
109
|
end
|
112
110
|
# return a non-zero exit code
|
113
111
|
mock_command(cmd, nil, nil, 1)
|
114
112
|
end
|
115
113
|
|
116
114
|
def file_not_found(path)
|
117
|
-
|
115
|
+
$stderr.puts("File not mocked: " + path.to_s) if @options[:verbose]
|
118
116
|
File.new(self, path)
|
119
117
|
end
|
120
118
|
|
121
119
|
def to_s
|
122
|
-
|
120
|
+
"Mock Connection"
|
123
121
|
end
|
124
122
|
|
125
123
|
private
|
@@ -142,23 +140,23 @@ end
|
|
142
140
|
class Train::Transports::Mock::Connection
|
143
141
|
class File < Train::File
|
144
142
|
def self.from_json(json)
|
145
|
-
res = new(json[
|
146
|
-
json[
|
147
|
-
json[
|
148
|
-
res.type = json[
|
143
|
+
res = new(json["backend"],
|
144
|
+
json["path"],
|
145
|
+
json["follow_symlink"])
|
146
|
+
res.type = json["type"]
|
149
147
|
Train::File::DATA_FIELDS.each do |f|
|
150
|
-
m = (f.tr(
|
148
|
+
m = (f.tr("?", "") + "=").to_sym
|
151
149
|
res.method(m).call(json[f])
|
152
150
|
end
|
153
151
|
res
|
154
152
|
end
|
155
153
|
|
156
154
|
Train::File::DATA_FIELDS.each do |m|
|
157
|
-
attr_accessor m.tr(
|
158
|
-
next unless m.include?(
|
155
|
+
attr_accessor m.tr("?", "").to_sym
|
156
|
+
next unless m.include?("?")
|
159
157
|
|
160
158
|
define_method m.to_sym do
|
161
|
-
method(m.tr(
|
159
|
+
method(m.tr("?", "").to_sym).call
|
162
160
|
end
|
163
161
|
end
|
164
162
|
attr_accessor :type
|