chefspec-chef 9.3.4

Sign up to get free protection for your applications and to get access to all the features.
Files changed (120) hide show
  1. checksums.yaml +7 -0
  2. data/Gemfile +30 -0
  3. data/LICENSE +22 -0
  4. data/Rakefile +85 -0
  5. data/chefspec-chef.gemspec +30 -0
  6. data/lib/chefspec/api/core.rb +217 -0
  7. data/lib/chefspec/api/described.rb +53 -0
  8. data/lib/chefspec/api/do_nothing.rb +26 -0
  9. data/lib/chefspec/api/include_any_recipe.rb +24 -0
  10. data/lib/chefspec/api/include_recipe.rb +28 -0
  11. data/lib/chefspec/api/link.rb +28 -0
  12. data/lib/chefspec/api/notifications.rb +40 -0
  13. data/lib/chefspec/api/reboot.rb +14 -0
  14. data/lib/chefspec/api/render_file.rb +37 -0
  15. data/lib/chefspec/api/state_attrs.rb +30 -0
  16. data/lib/chefspec/api/stubs.rb +183 -0
  17. data/lib/chefspec/api/stubs_for.rb +139 -0
  18. data/lib/chefspec/api/subscriptions.rb +37 -0
  19. data/lib/chefspec/api/user.rb +230 -0
  20. data/lib/chefspec/api.rb +39 -0
  21. data/lib/chefspec/berkshelf.rb +63 -0
  22. data/lib/chefspec/cacher.rb +64 -0
  23. data/lib/chefspec/coverage/filters.rb +82 -0
  24. data/lib/chefspec/coverage.rb +247 -0
  25. data/lib/chefspec/deprecations.rb +46 -0
  26. data/lib/chefspec/errors.rb +48 -0
  27. data/lib/chefspec/expect_exception.rb +51 -0
  28. data/lib/chefspec/extensions/chef/client.rb +21 -0
  29. data/lib/chefspec/extensions/chef/conditional.rb +16 -0
  30. data/lib/chefspec/extensions/chef/cookbook/gem_installer.rb +33 -0
  31. data/lib/chefspec/extensions/chef/cookbook_loader.rb +14 -0
  32. data/lib/chefspec/extensions/chef/cookbook_uploader.rb +12 -0
  33. data/lib/chefspec/extensions/chef/data_query.rb +49 -0
  34. data/lib/chefspec/extensions/chef/lwrp_base.rb +29 -0
  35. data/lib/chefspec/extensions/chef/provider.rb +39 -0
  36. data/lib/chefspec/extensions/chef/resource/freebsd_package.rb +17 -0
  37. data/lib/chefspec/extensions/chef/resource.rb +188 -0
  38. data/lib/chefspec/extensions/chef/run_context/cookbook_compiler.rb +84 -0
  39. data/lib/chefspec/extensions/chef/securable.rb +19 -0
  40. data/lib/chefspec/extensions/ohai/system.rb +11 -0
  41. data/lib/chefspec/extensions.rb +21 -0
  42. data/lib/chefspec/file_cache_path_proxy.rb +15 -0
  43. data/lib/chefspec/formatter.rb +282 -0
  44. data/lib/chefspec/librarian.rb +51 -0
  45. data/lib/chefspec/matchers/do_nothing_matcher.rb +52 -0
  46. data/lib/chefspec/matchers/include_any_recipe_matcher.rb +51 -0
  47. data/lib/chefspec/matchers/include_recipe_matcher.rb +46 -0
  48. data/lib/chefspec/matchers/link_to_matcher.rb +37 -0
  49. data/lib/chefspec/matchers/notifications_matcher.rb +143 -0
  50. data/lib/chefspec/matchers/render_file_matcher.rb +140 -0
  51. data/lib/chefspec/matchers/resource_matcher.rb +175 -0
  52. data/lib/chefspec/matchers/state_attrs_matcher.rb +71 -0
  53. data/lib/chefspec/matchers/subscribes_matcher.rb +72 -0
  54. data/lib/chefspec/matchers.rb +13 -0
  55. data/lib/chefspec/mixins/normalize.rb +22 -0
  56. data/lib/chefspec/policyfile.rb +69 -0
  57. data/lib/chefspec/renderer.rb +145 -0
  58. data/lib/chefspec/rspec.rb +21 -0
  59. data/lib/chefspec/runner.rb +8 -0
  60. data/lib/chefspec/server.rb +4 -0
  61. data/lib/chefspec/server_methods.rb +173 -0
  62. data/lib/chefspec/server_runner.rb +76 -0
  63. data/lib/chefspec/solo_runner.rb +516 -0
  64. data/lib/chefspec/stubs/command_registry.rb +11 -0
  65. data/lib/chefspec/stubs/command_stub.rb +37 -0
  66. data/lib/chefspec/stubs/data_bag_item_registry.rb +13 -0
  67. data/lib/chefspec/stubs/data_bag_item_stub.rb +25 -0
  68. data/lib/chefspec/stubs/data_bag_registry.rb +13 -0
  69. data/lib/chefspec/stubs/data_bag_stub.rb +23 -0
  70. data/lib/chefspec/stubs/registry.rb +32 -0
  71. data/lib/chefspec/stubs/search_registry.rb +13 -0
  72. data/lib/chefspec/stubs/search_stub.rb +25 -0
  73. data/lib/chefspec/stubs/stub.rb +38 -0
  74. data/lib/chefspec/util.rb +58 -0
  75. data/lib/chefspec/version.rb +3 -0
  76. data/lib/chefspec/zero_server.rb +142 -0
  77. data/lib/chefspec.rb +75 -0
  78. data/spec/spec_helper.rb +12 -0
  79. data/spec/support/hash.rb +35 -0
  80. data/spec/unit/cacher_spec.rb +70 -0
  81. data/spec/unit/coverage/filters_spec.rb +60 -0
  82. data/spec/unit/deprecations_spec.rb +52 -0
  83. data/spec/unit/errors_spec.rb +57 -0
  84. data/spec/unit/expect_exception_spec.rb +32 -0
  85. data/spec/unit/macros_spec.rb +119 -0
  86. data/spec/unit/matchers/do_nothing_matcher.rb +5 -0
  87. data/spec/unit/matchers/include_any_recipe_matcher_spec.rb +52 -0
  88. data/spec/unit/matchers/include_recipe_matcher_spec.rb +38 -0
  89. data/spec/unit/matchers/link_to_matcher_spec.rb +55 -0
  90. data/spec/unit/matchers/notifications_matcher_spec.rb +39 -0
  91. data/spec/unit/matchers/render_file_matcher_spec.rb +68 -0
  92. data/spec/unit/matchers/resource_matcher_spec.rb +5 -0
  93. data/spec/unit/matchers/state_attrs_matcher_spec.rb +68 -0
  94. data/spec/unit/matchers/subscribes_matcher_spec.rb +63 -0
  95. data/spec/unit/renderer_spec.rb +69 -0
  96. data/spec/unit/server_runner_spec.rb +28 -0
  97. data/spec/unit/solo_runner_spec.rb +171 -0
  98. data/spec/unit/stubs/command_registry_spec.rb +27 -0
  99. data/spec/unit/stubs/command_stub_spec.rb +61 -0
  100. data/spec/unit/stubs/data_bag_item_registry_spec.rb +39 -0
  101. data/spec/unit/stubs/data_bag_item_stub_spec.rb +36 -0
  102. data/spec/unit/stubs/data_bag_registry_spec.rb +39 -0
  103. data/spec/unit/stubs/data_bag_stub_spec.rb +35 -0
  104. data/spec/unit/stubs/registry_spec.rb +29 -0
  105. data/spec/unit/stubs/search_registry_spec.rb +39 -0
  106. data/spec/unit/stubs/search_stub_spec.rb +36 -0
  107. data/spec/unit/stubs/stub_spec.rb +64 -0
  108. data/templates/coverage/human.erb +22 -0
  109. data/templates/coverage/json.erb +8 -0
  110. data/templates/coverage/table.erb +14 -0
  111. data/templates/errors/cookbook_path_not_found.erb +3 -0
  112. data/templates/errors/erb_template_parse_error.erb +5 -0
  113. data/templates/errors/gem_load_error.erb +7 -0
  114. data/templates/errors/invalid_berkshelf_options.erb +4 -0
  115. data/templates/errors/may_need_to_specify_platform.erb +25 -0
  116. data/templates/errors/no_conversion_error.erb +1 -0
  117. data/templates/errors/not_stubbed.erb +7 -0
  118. data/templates/errors/shell_out_not_stubbed.erb +10 -0
  119. data/templates/errors/template_not_found.erb +9 -0
  120. metadata +221 -0
@@ -0,0 +1,21 @@
1
+ RSpec.configure do |config|
2
+ unless ENV["CHEFSPEC_NO_INCLUDE"]
3
+ config.include(ChefSpec::API)
4
+ end
5
+
6
+ config.add_setting :berkshelf_options, default: {}
7
+ config.add_setting :policyfile_path
8
+ config.add_setting :file_cache_path
9
+ config.add_setting :cookbook_root
10
+ config.add_setting :cookbook_path
11
+ config.add_setting :role_path
12
+ config.add_setting :environment_path
13
+ config.add_setting :file_cache_path
14
+ config.add_setting :log_level, default: :warn
15
+ config.add_setting :path
16
+ config.add_setting :platform
17
+ config.add_setting :version
18
+ config.add_setting :server_runner_data_store, default: :in_memory
19
+ config.add_setting :server_runner_clear_cookbooks, default: true
20
+ config.add_setting :server_runner_port, default: (8889..8899)
21
+ end
@@ -0,0 +1,8 @@
1
+ require_relative "solo_runner"
2
+
3
+ module ChefSpec
4
+ # As we start to migrate back to only SoloRunner, include this alias for now.
5
+ #
6
+ # @since 7.3
7
+ Runner = SoloRunner
8
+ end
@@ -0,0 +1,4 @@
1
+ # @todo Remove in v5.0.0
2
+ require_relative "deprecations"
3
+ deprecated "require 'chefspec/server' is no longer required and " \
4
+ "will be removed in the next major release."
@@ -0,0 +1,173 @@
1
+ module ChefSpec
2
+ # This module contains the list of methods that are specific to creating and
3
+ # managing resources within an Chef Zero instance. It is designed to be
4
+ # included in a class which exposes a `server` instance variable or method
5
+ # that returns a {ChefZero::Server} instance.
6
+ module ServerMethods
7
+ #
8
+ # The actual Chef Zero Server object.
9
+ #
10
+ # @return [ChefZero::Server]
11
+ #
12
+ def server
13
+ ChefSpec::ZeroServer.server
14
+ end
15
+
16
+ #
17
+ # @macro entity
18
+ # @method create_$1(name, data = {})
19
+ # Create a new $1 on the Chef Server
20
+ #
21
+ # @param [String] name
22
+ # the name of the $1
23
+ # @param [Hash] data
24
+ # the list of data to load
25
+ #
26
+ #
27
+ # @method $1(name)
28
+ # Find a $1 at the given name
29
+ #
30
+ # @param [String] name
31
+ # the name of the $1
32
+ #
33
+ # @return [$2, nil]
34
+ #
35
+ #
36
+ # @method $3
37
+ # The list of $1 on the Chef Server
38
+ #
39
+ # @return [Array<Hash>]
40
+ # all the $1 on the Chef Server
41
+ #
42
+ #
43
+ # @method has_$1?(name)
44
+ # Determine if the Chef Server has the given $1
45
+ #
46
+ # @param [String] name
47
+ # the name of the $1 to find
48
+ #
49
+ # @return [true, false]
50
+ #
51
+ def self.entity(method, klass, key)
52
+ class_eval <<-EOH, __FILE__, __LINE__ + 1
53
+ def create_#{method}(name, data = {})
54
+ # Automatically set the "name" if no explicit one was given
55
+ data[:name] ||= name
56
+
57
+ # Convert it to JSON
58
+ data = JSON.fast_generate(data)
59
+
60
+ load_data(name, '#{key}', data)
61
+ end
62
+
63
+ def get_#{method}(name)
64
+ data = get('#{key}', name)
65
+ json = JSON.parse(data)
66
+
67
+ case
68
+ when #{klass}.respond_to?(:json_create)
69
+ #{klass}.json_create(json)
70
+ when #{klass}.respond_to?(:from_hash)
71
+ #{klass}.from_hash(json)
72
+ else
73
+ #{klass}.new(json)
74
+ end
75
+ rescue ChefZero::DataStore::DataNotFoundError
76
+ nil
77
+ end
78
+
79
+ def get_#{key}
80
+ get('#{key}')
81
+ end
82
+
83
+ def has_#{method}?(name)
84
+ !get('#{key}', name).nil?
85
+ rescue ChefZero::DataStore::DataNotFoundError
86
+ false
87
+ end
88
+ EOH
89
+ end
90
+
91
+ entity :client, Chef::Client, "clients"
92
+ entity :data_bag, Chef::DataBag, "data"
93
+ entity :environment, Chef::Environment, "environments"
94
+ entity :node, Chef::Node, "nodes"
95
+ entity :role, Chef::Role, "roles"
96
+
97
+ #
98
+ # Create a new data_bag on the Chef Server. This overrides the method
99
+ # created by {entity}
100
+ #
101
+ # @param [String] name
102
+ # the name of the data bag
103
+ # @param [Hash] data
104
+ # the data to load into the data bag
105
+ #
106
+ def create_data_bag(name, data = {})
107
+ load_data(name, "data", data)
108
+ end
109
+
110
+ #
111
+ # Create a new node on the Chef Server. This overrides the method created
112
+ # by {entity}, permitting users to pass a raw +Chef::Node+ object in
113
+ # addition to a hash.
114
+ #
115
+ # @example Create a node from a hash
116
+ #
117
+ # create_node('bacon', attribute: 'value')
118
+ #
119
+ # @example Create a node from a +Chef::Node+ object
120
+ #
121
+ # node = stub_node('bacon', platform: 'ubuntu', version: '18.04')
122
+ # create_node(node)
123
+ #
124
+ # @param [String, Chef::Node] object
125
+ # the object to create; this can be the name of the node, or an actual
126
+ # +Chef::Node+ object
127
+ # @param [Hash] data
128
+ # the list of data to populate the node with; this is ignored if an
129
+ # actual node object is given
130
+ #
131
+ def create_node(object, data = {})
132
+ if object.is_a?(Chef::Node)
133
+ name = object.name
134
+ data = object.to_json
135
+ else
136
+ name = object.to_s
137
+ data[:name] ||= name
138
+ data = JSON.fast_generate(data)
139
+ end
140
+
141
+ load_data(name, "nodes", data)
142
+ end
143
+ alias_method :update_node, :create_node
144
+
145
+ #
146
+ # Shortcut method for loading data into Chef Zero.
147
+ #
148
+ # @param [String] name
149
+ # the name or id of the item to load
150
+ # @param [String, Symbol] key
151
+ # the key to load
152
+ # @param [Hash] data
153
+ # the data for the object, which will be converted to JSON and uploaded
154
+ # to the server
155
+ #
156
+ def load_data(name, key, data = {})
157
+ ChefSpec::ZeroServer.load_data(name, key, data)
158
+ end
159
+
160
+ #
161
+ # Get the path to an item in the data store.
162
+ #
163
+ def get(*args)
164
+ args.unshift("organizations", "chef")
165
+
166
+ if args.size == 3
167
+ server.data_store.list(args)
168
+ else
169
+ server.data_store.get(args)
170
+ end
171
+ end
172
+ end
173
+ end
@@ -0,0 +1,76 @@
1
+ require "chef/cookbook_loader"
2
+ require "chef/cookbook_uploader"
3
+
4
+ require_relative "zero_server"
5
+ require_relative "file_cache_path_proxy"
6
+ require_relative "server_methods"
7
+ require_relative "solo_runner"
8
+
9
+ module ChefSpec
10
+ class ServerRunner < SoloRunner
11
+ include ChefSpec::ServerMethods
12
+
13
+ # @see (SoloRunner#initialize)
14
+ def initialize(options = {})
15
+ # Unlike the SoloRunner, the file_cache_path needs to remain consistent
16
+ # for every Chef run or else the Chef client tries to loads the same
17
+ # cookbook multiple times and will encounter deprecated logic when
18
+ # creating LWRPs. It also slows down the entire process.
19
+ options[:file_cache_path] ||= RSpec.configuration.file_cache_path ||
20
+ ChefSpec::FileCachePathProxy.instance.file_cache_path
21
+
22
+ # Call super, but do not pass in the block because we want to customize
23
+ # our yielding.
24
+ super(options, &nil)
25
+
26
+ # Unlike the SoloRunner, the node AND server object are yielded for
27
+ # customization
28
+ yield node, self if block_given?
29
+ end
30
+
31
+ # @see (SoloRunner#converge)
32
+ def converge(*recipe_names)
33
+ ChefSpec::ZeroServer.upload_cookbooks!
34
+
35
+ super do
36
+ yield if block_given?
37
+
38
+ # Save the node back to the server for searching purposes
39
+ client.register
40
+ node.save
41
+ end
42
+ end
43
+
44
+ private
45
+
46
+ #
47
+ # The path to the insecure Chef Zero private key on disk. Because Chef
48
+ # requires the path to a file instead of the contents of the key (why),
49
+ # this method dynamically writes the +ChefZero::PRIVATE_KEY+ to disk and
50
+ # then returns that path.
51
+ #
52
+ # @return [String]
53
+ # the path to the client key on disk
54
+ #
55
+ def client_key
56
+ tmp = Dir.mktmpdir
57
+ path = File.join(tmp, "client.pem")
58
+ File.open(path, "wb") { |f| f.write(ChefZero::PRIVATE_KEY) }
59
+ at_exit { FileUtils.rm_rf(tmp) }
60
+ path
61
+ end
62
+
63
+ # (see SoloRunner#apply_chef_config!)
64
+ def apply_chef_config!
65
+ super
66
+ Chef::Config[:client_key] = client_key
67
+ Chef::Config[:client_name] = "chefspec"
68
+ Chef::Config[:node_name] = "chefspec"
69
+ Chef::Config[:solo] = false
70
+ Chef::Config[:solo_legacy_mode] = false
71
+
72
+ Chef::Config[:chef_server_url] = server.url
73
+ Chef::Config[:http_retry_count] = 0
74
+ end
75
+ end
76
+ end