inspec 0.35.0 → 1.0.0.beta2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (56) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +83 -2
  3. data/Gemfile +6 -0
  4. data/Rakefile +3 -55
  5. data/docs/README.md +20 -0
  6. data/docs/cli.rst +6 -0
  7. data/docs/dsl_inspec.md +245 -0
  8. data/docs/dsl_resource.md +93 -0
  9. data/docs/inspec_and_friends.md +102 -0
  10. data/docs/matchers.md +136 -0
  11. data/docs/plugin_kitchen_inspec.html.md +55 -0
  12. data/docs/profiles.md +271 -0
  13. data/docs/resources.rst +1 -1
  14. data/docs/shell.md +150 -0
  15. data/inspec.gemspec +1 -1
  16. data/lib/bundles/inspec-compliance/api.rb +28 -18
  17. data/lib/bundles/inspec-compliance/cli.rb +19 -27
  18. data/lib/fetchers/git.rb +4 -0
  19. data/lib/fetchers/local.rb +16 -1
  20. data/lib/fetchers/mock.rb +4 -0
  21. data/lib/fetchers/url.rb +40 -12
  22. data/lib/inspec/base_cli.rb +4 -0
  23. data/lib/inspec/cli.rb +6 -8
  24. data/lib/inspec/control_eval_context.rb +8 -0
  25. data/lib/inspec/dependencies/{vendor_index.rb → cache.rb} +5 -4
  26. data/lib/inspec/dependencies/dependency_set.rb +8 -14
  27. data/lib/inspec/dependencies/requirement.rb +10 -20
  28. data/lib/inspec/dependencies/resolver.rb +2 -2
  29. data/lib/inspec/dsl.rb +9 -0
  30. data/lib/inspec/fetcher.rb +1 -1
  31. data/lib/inspec/objects/test.rb +8 -2
  32. data/lib/inspec/plugins/fetcher.rb +11 -12
  33. data/lib/inspec/plugins/resource.rb +3 -0
  34. data/lib/inspec/profile.rb +60 -14
  35. data/lib/inspec/profile_context.rb +28 -7
  36. data/lib/inspec/resource.rb +17 -2
  37. data/lib/inspec/rspec_json_formatter.rb +80 -35
  38. data/lib/inspec/runner.rb +42 -18
  39. data/lib/inspec/shell.rb +5 -16
  40. data/lib/inspec/version.rb +1 -1
  41. data/lib/resources/apache_conf.rb +1 -1
  42. data/lib/resources/gem.rb +1 -0
  43. data/lib/resources/oneget.rb +1 -0
  44. data/lib/resources/os.rb +1 -1
  45. data/lib/resources/package.rb +3 -1
  46. data/lib/resources/pip.rb +1 -1
  47. data/lib/resources/ssl.rb +9 -11
  48. metadata +15 -15
  49. data/docs/dsl_inspec.rst +0 -259
  50. data/docs/dsl_resource.rst +0 -90
  51. data/docs/inspec_and_friends.rst +0 -85
  52. data/docs/matchers.rst +0 -137
  53. data/docs/profiles.rst +0 -169
  54. data/docs/readme.rst +0 -105
  55. data/docs/shell.rst +0 -130
  56. data/docs/template.rst +0 -51
@@ -58,6 +58,10 @@ module Inspec
58
58
  desc: 'Use colors in output.'
59
59
  option :attrs, type: :array,
60
60
  desc: 'Load attributes file (experimental)'
61
+ option :cache, type: :string,
62
+ desc: 'Use the given path for caching dependencies. (default: ~/.inspec/cache)'
63
+ option :create_lockfile, type: :boolean, default: true,
64
+ desc: 'Write out a lockfile based on this execution (unless one already exists)'
61
65
  end
62
66
 
63
67
  private
data/lib/inspec/cli.rb CHANGED
@@ -102,8 +102,8 @@ class Inspec::InspecCLI < Inspec::BaseCLI # rubocop:disable Metrics/ClassLength
102
102
  desc 'vendor', 'Download all dependencies and generate a lockfile'
103
103
  def vendor(path = nil)
104
104
  configure_logger(opts)
105
- profile = Inspec::Profile.for_target('./', opts)
106
- lockfile = profile.generate_lockfile(path)
105
+ profile = Inspec::Profile.for_target('./', opts.merge(cache: Inspec::Cache.new(path)))
106
+ lockfile = profile.generate_lockfile
107
107
  File.write('inspec.lock', lockfile.to_yaml)
108
108
  end
109
109
 
@@ -213,13 +213,11 @@ class Inspec::InspecCLI < Inspec::BaseCLI # rubocop:disable Metrics/ClassLength
213
213
 
214
214
  def run_command(opts)
215
215
  runner = Inspec::Runner.new(opts)
216
- ctx = runner.create_context(opts)
217
- res = ctx.load(opts[:command])
216
+ res = runner.eval_with_virtual_profile(opts[:command])
217
+ runner.load
218
218
 
219
- return :ruby_eval, res if ctx.rules.empty?
220
-
221
- runner.register_rules(ctx)
222
- return :rspec_run, runner.run # rubocop:disable Style/RedundantReturn
219
+ return :ruby_eval, res if runner.all_rules.empty?
220
+ return :rspec_run, runner.run_tests # rubocop:disable Style/RedundantReturn
223
221
  end
224
222
  end
225
223
 
@@ -92,6 +92,14 @@ module Inspec
92
92
  res
93
93
  end
94
94
 
95
+ define_method :add_resource do |name, new_res|
96
+ resources_dsl.module_exec do
97
+ define_method name.to_sym do |*args|
98
+ new_res.new(@backend, name.to_s, *args)
99
+ end
100
+ end
101
+ end
102
+
95
103
  define_method :add_resources do |context|
96
104
  self.class.class_eval do
97
105
  include context.to_resources_dsl
@@ -4,7 +4,7 @@ require 'fileutils'
4
4
 
5
5
  module Inspec
6
6
  #
7
- # VendorIndex manages an on-disk cache of inspec profiles. The
7
+ # Inspec::Cache manages an on-disk cache of inspec profiles. The
8
8
  # cache can contain:
9
9
  #
10
10
  # - .tar.gz profile archives
@@ -16,7 +16,7 @@ module Inspec
16
16
  # sources.
17
17
  #
18
18
  #
19
- class VendorIndex
19
+ class Cache
20
20
  attr_reader :path
21
21
  def initialize(path = nil)
22
22
  @path = path || File.join(Dir.home, '.inspec', 'cache')
@@ -43,19 +43,20 @@ module Inspec
43
43
 
44
44
  #
45
45
  # For a given name and source_url, return true if the
46
- # profile exists in the VendorIndex.
46
+ # profile exists in the Cache.
47
47
  #
48
48
  # @param [String] name
49
49
  # @param [String] source_url
50
50
  # @return [Boolean]
51
51
  #
52
52
  def exists?(key)
53
+ return false if key.nil? || key.empty?
53
54
  path = base_path_for(key)
54
55
  File.directory?(path) || File.exist?("#{path}.tar.gz") || File.exist?("#{path}.zip")
55
56
  end
56
57
 
57
58
  #
58
- # Return the path to given profile in the vendor index.
59
+ # Return the path to given profile in the cache.
59
60
  #
60
61
  # The `source_url` parameter should be a URI-like string that
61
62
  # fully specifies the source of the exact version we want to pull
@@ -1,5 +1,4 @@
1
1
  # encoding: utf-8
2
- require 'inspec/dependencies/vendor_index'
3
2
  require 'inspec/dependencies/requirement'
4
3
  require 'inspec/dependencies/resolver'
5
4
 
@@ -7,9 +6,6 @@ module Inspec
7
6
  #
8
7
  # A DependencySet manages a list of dependencies for a profile.
9
8
  #
10
- # Currently this class is a thin wrapper interface to coordinate the
11
- # VendorIndex and the Resolver.
12
- #
13
9
  class DependencySet
14
10
  #
15
11
  # Return a dependency set given a lockfile.
@@ -18,22 +14,21 @@ module Inspec
18
14
  # @param cwd [String] Current working directory for relative path includes
19
15
  # @param vendor_path [String] Path to the vendor directory
20
16
  #
21
- def self.from_lockfile(lockfile, cwd, vendor_path, backend)
22
- vendor_index = VendorIndex.new(vendor_path)
17
+ def self.from_lockfile(lockfile, cwd, cache, backend)
23
18
  dep_tree = lockfile.deps.map do |dep|
24
- Inspec::Requirement.from_lock_entry(dep, cwd, vendor_index, backend)
19
+ Inspec::Requirement.from_lock_entry(dep, cwd, cache, backend)
25
20
  end
26
21
 
27
22
  dep_list = flatten_dep_tree(dep_tree)
28
- new(cwd, vendor_path, dep_list, backend)
23
+ new(cwd, cache, dep_list, backend)
29
24
  end
30
25
 
31
- def self.from_array(dependencies, cwd, vendor_path, backend)
26
+ def self.from_array(dependencies, cwd, cache, backend)
32
27
  dep_list = {}
33
28
  dependencies.each do |d|
34
29
  dep_list[d.name] = d
35
30
  end
36
- new(cwd, vendor_path, dep_list, backend)
31
+ new(cwd, cache, dep_list, backend)
37
32
  end
38
33
 
39
34
  # This is experimental code to test the working of the
@@ -58,9 +53,9 @@ module Inspec
58
53
  # @param cwd [String] current working directory for relative path includes
59
54
  # @param vendor_path [String] path which contains vendored dependencies
60
55
  # @return [dependencies] this
61
- def initialize(cwd, vendor_path, dep_list, backend)
56
+ def initialize(cwd, cache, dep_list, backend)
62
57
  @cwd = cwd
63
- @vendor_path = vendor_path
58
+ @cache = cache
64
59
  @dep_list = dep_list
65
60
  @backend = backend
66
61
  end
@@ -91,8 +86,7 @@ module Inspec
91
86
  #
92
87
  def vendor(dependencies)
93
88
  return nil if dependencies.nil? || dependencies.empty?
94
- @vendor_index ||= VendorIndex.new(@vendor_path)
95
- @dep_list = Resolver.resolve(dependencies, @vendor_index, @cwd, @backend)
89
+ @dep_list = Resolver.resolve(dependencies, @cache, @cwd, @backend)
96
90
  end
97
91
  end
98
92
  end
@@ -9,31 +9,31 @@ module Inspec
9
9
  # appropriate we delegate to Inspec::Profile directly.
10
10
  #
11
11
  class Requirement
12
- def self.from_metadata(dep, vendor_index, opts)
12
+ def self.from_metadata(dep, cache, opts)
13
13
  fail 'Cannot load empty dependency.' if dep.nil? || dep.empty?
14
- new(dep[:name], dep[:version], vendor_index, opts[:cwd], opts.merge(dep))
14
+ new(dep[:name], dep[:version], cache, opts[:cwd], opts.merge(dep))
15
15
  end
16
16
 
17
- def self.from_lock_entry(entry, cwd, vendor_index, backend)
17
+ def self.from_lock_entry(entry, cwd, cache, backend)
18
18
  req = new(entry[:name],
19
19
  entry[:version_constraints],
20
- vendor_index,
20
+ cache,
21
21
  cwd,
22
22
  entry[:resolved_source].merge(backend: backend))
23
23
 
24
24
  locked_deps = []
25
25
  Array(entry[:dependencies]).each do |dep_entry|
26
- locked_deps << Inspec::Requirement.from_lock_entry(dep_entry, cwd, vendor_index, backend)
26
+ locked_deps << Inspec::Requirement.from_lock_entry(dep_entry, cwd, cache, backend)
27
27
  end
28
28
  req.lock_deps(locked_deps)
29
29
  req
30
30
  end
31
31
 
32
32
  attr_reader :cwd, :opts, :required_version
33
- def initialize(name, version_constraints, vendor_index, cwd, opts)
33
+ def initialize(name, version_constraints, cache, cwd, opts)
34
34
  @name = name
35
35
  @required_version = Gem::Requirement.new(Array(version_constraints))
36
- @vendor_index = vendor_index
36
+ @cache = cache
37
37
  @backend = opts[:backend]
38
38
  @opts = opts
39
39
  @cwd = cwd
@@ -74,7 +74,6 @@ module Inspec
74
74
  h['dependencies'] = dependencies.map(&:to_hash)
75
75
  end
76
76
 
77
- h['content_hash'] = content_hash if content_hash
78
77
  h
79
78
  end
80
79
 
@@ -82,15 +81,6 @@ module Inspec
82
81
  @dependencies = dep_array
83
82
  end
84
83
 
85
- def content_hash
86
- @content_hash ||= begin
87
- archive_path = @vendor_index.archive_entry_for(fetcher.cache_key) || fetcher.archive_path
88
- if archive_path && File.file?(archive_path)
89
- Digest::SHA256.hexdigest File.read(archive_path)
90
- end
91
- end
92
- end
93
-
94
84
  def fetcher
95
85
  @fetcher ||= Inspec::Fetcher.resolve(opts)
96
86
  fail "No fetcher for #{name} (options: #{opts})" if @fetcher.nil?
@@ -99,7 +89,7 @@ module Inspec
99
89
 
100
90
  def dependencies
101
91
  @dependencies ||= profile.metadata.dependencies.map do |r|
102
- Inspec::Requirement.from_metadata(r, @vendor_index, cwd: @cwd, backend: @backend)
92
+ Inspec::Requirement.from_metadata(r, @cache, cwd: @cwd, backend: @backend)
103
93
  end
104
94
  end
105
95
 
@@ -109,10 +99,10 @@ module Inspec
109
99
 
110
100
  def profile
111
101
  opts = @opts.dup
112
- opts[:cache] = @vendor_index
102
+ opts[:cache] = @cache
113
103
  opts[:backend] = @backend
114
104
  if !@dependencies.nil?
115
- opts[:dependencies] = Inspec::DependencySet.from_array(@dependencies, @cwd, @vendor_index, @backend)
105
+ opts[:dependencies] = Inspec::DependencySet.from_array(@dependencies, @cwd, @cache, @backend)
116
106
  end
117
107
  @profile ||= Inspec::Profile.for_target(opts, opts)
118
108
  end
@@ -23,9 +23,9 @@ module Inspec
23
23
  # implementation of the fetcher being used.
24
24
  #
25
25
  class Resolver
26
- def self.resolve(dependencies, vendor_index, working_dir, backend)
26
+ def self.resolve(dependencies, cache, working_dir, backend)
27
27
  reqs = dependencies.map do |dep|
28
- req = Inspec::Requirement.from_metadata(dep, vendor_index, cwd: working_dir, backend: backend)
28
+ req = Inspec::Requirement.from_metadata(dep, cache, cwd: working_dir, backend: backend)
29
29
  req || fail("Cannot initialize dependency: #{req}")
30
30
  end
31
31
  new.resolve(reqs)
data/lib/inspec/dsl.rb CHANGED
@@ -18,6 +18,15 @@ module Inspec::DSL
18
18
  alias require_rules require_controls
19
19
  alias include_rules include_controls
20
20
 
21
+ def require_resource(options = {})
22
+ fail 'You must specify a specific resource name when calling require_resource()' if options[:resource].nil?
23
+
24
+ from_profile = options[:profile] || profile_name
25
+ target_name = options[:as] || options[:resource]
26
+ res = resource_class(from_profile, options[:resource])
27
+ add_resource(target_name, res)
28
+ end
29
+
21
30
  def self.load_spec_files_for_profile(bind_context, opts, &block)
22
31
  dependencies = opts[:dependencies]
23
32
  profile_id = opts[:profile_id]
@@ -16,7 +16,7 @@ module Inspec
16
16
  end
17
17
  end
18
18
 
19
- NON_FETCHER_KEYS = [:name, :version_constraint, :cwd, :backend, :cache].freeze
19
+ NON_FETCHER_KEYS = [:name, :version_constraint, :cwd, :backend, :cache, :sha256].freeze
20
20
  def fetcher_specified?(target)
21
21
  # Only set a default for Hash-based (i.e. from
22
22
  # inspec.yml/inspec.lock) targets
@@ -66,8 +66,14 @@ module Inspec
66
66
  res, xtra = describe_chain
67
67
  itsy = xtra.nil? ? 'it' : 'its(' + xtra.to_s.inspect + ')'
68
68
  naughty = @negated ? '_not' : ''
69
- xpect = defined?(@expectation) ? expectation.inspect+' ' : ''
70
- format("%sdescribe %s do\n %s { should%s %s %s}\nend",
69
+ xpect = defined?(@expectation) ? expectation.inspect : ''
70
+ if matcher == 'match'
71
+ # without this, xpect values like / \/zones\// will not be parsed properly
72
+ xpect = "(#{xpect})"
73
+ elsif xpect != ''
74
+ xpect = ' ' + xpect
75
+ end
76
+ format("%sdescribe %s do\n %s { should%s %s%s }\nend",
71
77
  vars, res, itsy, naughty, matcher, xpect)
72
78
  end
73
79
 
@@ -24,6 +24,10 @@ module Inspec
24
24
  Inspec::Fetcher
25
25
  end
26
26
 
27
+ def writable?
28
+ false
29
+ end
30
+
27
31
  #
28
32
  # The path to the archive on disk. This can be passed to a
29
33
  # FileProvider to get access to the files in the fetched
@@ -56,6 +60,13 @@ module Inspec
56
60
  fail "Fetcher #{self} does not implement `resolved_source()`. This is required for terminal fetchers."
57
61
  end
58
62
 
63
+ #
64
+ # The unique key based on the content of the remote archive.
65
+ #
66
+ def cache_key
67
+ fail "Fetcher #{self} does not implement `cache_key()`. This is required for terminal fetchers."
68
+ end
69
+
59
70
  #
60
71
  # relative_target is provided to keep compatibility with 3rd
61
72
  # party plugins.
@@ -69,18 +80,6 @@ module Inspec
69
80
  file_provider = Inspec::FileProvider.for_path(archive_path)
70
81
  file_provider.relative_provider
71
82
  end
72
-
73
- #
74
- # A string based on the components of the resolved source,
75
- # suitable for constructing per-source file names.
76
- #
77
- def cache_key
78
- key = ''
79
- resolved_source.each do |k, v|
80
- key << "#{k}:#{v}"
81
- end
82
- Digest::SHA256.hexdigest key
83
- end
84
83
  end
85
84
  end
86
85
  end
@@ -72,6 +72,9 @@ module Inspec
72
72
  end
73
73
 
74
74
  # rubocop:enable Lint/NestedMethodDefinition
75
+ if __resource_registry.key?(name)
76
+ Inspec::Log.warn("Overwriting resource #{name}. To reference a specific version of #{name} use the resource() method")
77
+ end
75
78
  __resource_registry[name] = cl
76
79
  end
77
80
  end
@@ -13,7 +13,7 @@ require 'inspec/backend'
13
13
  require 'inspec/rule'
14
14
  require 'inspec/log'
15
15
  require 'inspec/profile_context'
16
- require 'inspec/dependencies/vendor_index'
16
+ require 'inspec/dependencies/cache'
17
17
  require 'inspec/dependencies/lockfile'
18
18
  require 'inspec/dependencies/dependency_set'
19
19
 
@@ -21,19 +21,44 @@ module Inspec
21
21
  class Profile # rubocop:disable Metrics/ClassLength
22
22
  extend Forwardable
23
23
 
24
+ #
25
+ # TODO: This function is getting pretty gross.
26
+ #
24
27
  def self.resolve_target(target, cache = nil)
25
- cache ||= VendorIndex.new
28
+ cache ||= Cache.new
26
29
  fetcher = Inspec::Fetcher.resolve(target)
30
+
27
31
  if fetcher.nil?
28
32
  fail("Could not fetch inspec profile in #{target.inspect}.")
29
33
  end
30
34
 
31
- if cache.exists?(fetcher.cache_key)
35
+ cache_key = if target.is_a?(Hash)
36
+ target[:sha256] || target[:ref] || fetcher.cache_key
37
+ else
38
+ fetcher.cache_key
39
+ end
40
+
41
+ if cache.exists?(cache_key)
32
42
  Inspec::Log.debug "Using cached dependency for #{target}"
33
- cache.prefered_entry_for(fetcher.cache_key)
43
+ [cache.prefered_entry_for(cache_key), false]
34
44
  else
35
45
  fetcher.fetch(cache.base_path_for(fetcher.cache_key))
36
- fetcher.archive_path
46
+ if target.respond_to?(:key?) && target.key?(:sha256)
47
+ if fetcher.resolved_source[:sha256] != target[:sha256]
48
+ fail <<EOF
49
+ The remote source #{fetcher} no longer has the requested content:
50
+
51
+ Request Content Hash: #{target[:sha256]}
52
+ Actual Content Hash: #{fetcher.resolved_source[:sha256]}
53
+
54
+ For URL, supermarket, compliance, and other sources that do not
55
+ provide versioned artifacts, this likely means that the remote source
56
+ has changed since your lockfile was generated.
57
+ EOF
58
+ end
59
+ end
60
+
61
+ [fetcher.archive_path, fetcher.writable?]
37
62
  end
38
63
  end
39
64
 
@@ -48,7 +73,8 @@ module Inspec
48
73
  end
49
74
 
50
75
  def self.for_target(target, opts = {})
51
- for_path(resolve_target(target, opts[:cache]), opts.merge(target: target))
76
+ path, writable = resolve_target(target, opts[:cache])
77
+ for_path(path, opts.merge(target: target, writable: writable))
52
78
  end
53
79
 
54
80
  attr_reader :source_reader, :backend, :runner_context
@@ -62,10 +88,13 @@ module Inspec
62
88
  @logger = options[:logger] || Logger.new(nil)
63
89
  @locked_dependencies = options[:dependencies]
64
90
  @controls = options[:controls] || []
91
+ @writable = options[:writable] || false
65
92
  @profile_id = options[:id]
93
+ @cache = options[:cache] || Cache.new
66
94
  @backend = options[:backend] || Inspec::Backend.create(options)
67
95
  @source_reader = source_reader
68
96
  @tests_collected = false
97
+ @libraries_loaded = false
69
98
  Metadata.finalize(@source_reader.metadata, @profile_id)
70
99
  @runner_context = options[:profile_context] || Inspec::ProfileContext.for_profile(self,
71
100
  @backend,
@@ -80,6 +109,10 @@ module Inspec
80
109
  metadata.params[:version]
81
110
  end
82
111
 
112
+ def writable? # rubocop:disable Style/TrivialAccessors
113
+ @writable
114
+ end
115
+
83
116
  #
84
117
  # Is this profile is supported on the current platform of the
85
118
  # backend machine and the current inspec version.
@@ -125,6 +158,8 @@ module Inspec
125
158
  end
126
159
 
127
160
  def load_libraries
161
+ return @runner_context if @libraries_loaded
162
+
128
163
  locked_dependencies.each do |d|
129
164
  c = d.load_libraries
130
165
  @runner_context.add_resources(c)
@@ -135,6 +170,7 @@ module Inspec
135
170
  end
136
171
 
137
172
  @runner_context.load_libraries(libs)
173
+ @libraries_loaded = true
138
174
  @runner_context
139
175
  end
140
176
 
@@ -142,19 +178,29 @@ module Inspec
142
178
  "Inspec::Profile<#{name}>"
143
179
  end
144
180
 
145
- def info
146
- res = params.dup
181
+ # return info using uncached params
182
+ def info!
183
+ info(load_params.dup)
184
+ end
185
+
186
+ def info(res = params.dup)
147
187
  # add information about the controls
148
- controls = res[:controls].map do |id, rule|
188
+ res[:controls] = res[:controls].map do |id, rule|
149
189
  next if id.to_s.empty?
150
190
  data = rule.dup
151
191
  data.delete(:checks)
152
192
  data[:impact] ||= 0.5
153
193
  data[:impact] = 1.0 if data[:impact] > 1.0
154
194
  data[:impact] = 0.0 if data[:impact] < 0.0
155
- [id, data]
195
+ data[:id] = id
196
+ data
197
+ end.compact
198
+
199
+ # resolve hash structure in groups
200
+ res[:groups] = res[:groups].map do |id, group|
201
+ group[:id] = id
202
+ group
156
203
  end
157
- res[:controls] = Hash[controls.compact]
158
204
 
159
205
  # add information about the required attributes
160
206
  res[:attributes] = res[:attributes].map(&:to_hash) unless res[:attributes].nil? || res[:attributes].empty?
@@ -329,14 +375,14 @@ module Inspec
329
375
  # @param vendor_path [String] Path to the on-disk vendor dir
330
376
  # @return [Inspec::Lockfile]
331
377
  #
332
- def generate_lockfile(vendor_path = nil)
333
- res = Inspec::DependencySet.new(cwd, vendor_path, nil, @backend)
378
+ def generate_lockfile
379
+ res = Inspec::DependencySet.new(cwd, @cache, nil, @backend)
334
380
  res.vendor(metadata.dependencies)
335
381
  Inspec::Lockfile.from_dependency_set(res)
336
382
  end
337
383
 
338
384
  def load_dependencies
339
- Inspec::DependencySet.from_lockfile(lockfile, cwd, nil, @backend)
385
+ Inspec::DependencySet.from_lockfile(lockfile, cwd, @cache, @backend)
340
386
  end
341
387
 
342
388
  private