inspec 1.0.0 → 1.35.1

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.
Files changed (286) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +933 -101
  3. data/Gemfile +8 -17
  4. data/MAINTAINERS.md +2 -1
  5. data/MAINTAINERS.toml +9 -4
  6. data/README.md +49 -28
  7. data/Rakefile +54 -39
  8. data/bin/inspec +1 -1
  9. data/docs/dsl_inspec.md +17 -4
  10. data/docs/dsl_resource.md +1 -1
  11. data/docs/habitat.md +192 -0
  12. data/docs/inspec_and_friends.md +4 -2
  13. data/docs/matchers.md +11 -0
  14. data/docs/migration.md +293 -0
  15. data/docs/profiles.md +124 -76
  16. data/docs/resources/aide_conf.md.erb +81 -0
  17. data/docs/resources/apache_conf.md.erb +10 -10
  18. data/docs/resources/apt.md.erb +13 -13
  19. data/docs/resources/audit_policy.md.erb +10 -10
  20. data/docs/resources/auditd_conf.md.erb +10 -10
  21. data/docs/resources/auditd_rules.md.erb +11 -11
  22. data/docs/resources/bash.md.erb +12 -12
  23. data/docs/resources/bond.md.erb +15 -15
  24. data/docs/resources/bridge.md.erb +11 -11
  25. data/docs/resources/bsd_service.md.erb +11 -11
  26. data/docs/resources/command.md.erb +23 -23
  27. data/docs/resources/crontab.md.erb +84 -0
  28. data/docs/resources/csv.md.erb +10 -10
  29. data/docs/resources/dh_params.md +191 -0
  30. data/docs/resources/directory.md.erb +8 -8
  31. data/docs/resources/docker.md.erb +160 -0
  32. data/docs/resources/docker_container.md.erb +89 -0
  33. data/docs/resources/docker_image.md.erb +86 -0
  34. data/docs/resources/etc_group.md.erb +16 -16
  35. data/docs/resources/etc_hosts.md.erb +62 -0
  36. data/docs/resources/file.md.erb +80 -58
  37. data/docs/resources/gem.md.erb +32 -13
  38. data/docs/resources/group.md.erb +12 -12
  39. data/docs/resources/grub_conf.md.erb +11 -11
  40. data/docs/resources/host.md.erb +27 -18
  41. data/docs/resources/http.md.erb +104 -0
  42. data/docs/resources/iis_app.md.erb +126 -0
  43. data/docs/resources/iis_site.md.erb +17 -17
  44. data/docs/resources/inetd_conf.md.erb +10 -10
  45. data/docs/resources/ini.md.erb +9 -9
  46. data/docs/resources/interface.md.erb +13 -13
  47. data/docs/resources/iptables.md.erb +21 -14
  48. data/docs/resources/json.md.erb +11 -11
  49. data/docs/resources/kernel_module.md.erb +73 -12
  50. data/docs/resources/kernel_parameter.md.erb +12 -12
  51. data/docs/resources/key_rsa.md.erb +70 -0
  52. data/docs/resources/launchd_service.md.erb +11 -11
  53. data/docs/resources/limits_conf.md.erb +10 -10
  54. data/docs/resources/login_def.md.erb +12 -12
  55. data/docs/resources/mount.md.erb +14 -14
  56. data/docs/resources/mssql_session.md.erb +62 -0
  57. data/docs/resources/mysql_conf.md.erb +14 -14
  58. data/docs/resources/mysql_session.md.erb +22 -10
  59. data/docs/resources/npm.md.erb +13 -13
  60. data/docs/resources/ntp_conf.md.erb +9 -9
  61. data/docs/resources/oneget.md.erb +11 -11
  62. data/docs/resources/oracledb_session.md.erb +53 -0
  63. data/docs/resources/os.md.erb +17 -17
  64. data/docs/resources/os_env.md.erb +12 -12
  65. data/docs/resources/package.md.erb +29 -16
  66. data/docs/resources/parse_config.md.erb +18 -18
  67. data/docs/resources/parse_config_file.md.erb +29 -23
  68. data/docs/resources/{etc_passwd.md.erb → passwd.md.erb} +17 -17
  69. data/docs/resources/pip.md.erb +15 -15
  70. data/docs/resources/port.md.erb +23 -23
  71. data/docs/resources/postgres_conf.md.erb +15 -13
  72. data/docs/resources/postgres_hba_conf.md.erb +104 -0
  73. data/docs/resources/postgres_ident_conf.md.erb +87 -0
  74. data/docs/resources/postgres_session.md.erb +28 -21
  75. data/docs/resources/powershell.md.erb +14 -14
  76. data/docs/resources/processes.md.erb +123 -0
  77. data/docs/resources/rabbitmq_config.md.erb +55 -0
  78. data/docs/resources/registry_key.md.erb +44 -21
  79. data/docs/resources/runit_service.md.erb +11 -11
  80. data/docs/resources/security_policy.md.erb +10 -10
  81. data/docs/resources/service.md.erb +18 -18
  82. data/docs/resources/{etc_shadow.md.erb → shadow.md.erb} +19 -19
  83. data/docs/resources/ssh_config.md.erb +13 -13
  84. data/docs/resources/sshd_config.md.erb +15 -15
  85. data/docs/resources/ssl.md.erb +13 -13
  86. data/docs/resources/sys_info.md.erb +10 -10
  87. data/docs/resources/systemd_service.md.erb +11 -11
  88. data/docs/resources/sysv_service.md.erb +11 -11
  89. data/docs/resources/upstart_service.md.erb +11 -11
  90. data/docs/resources/user.md.erb +20 -20
  91. data/docs/resources/users.md.erb +19 -19
  92. data/docs/resources/vbscript.md.erb +13 -13
  93. data/docs/resources/virtualization.md.erb +71 -0
  94. data/docs/resources/windows_feature.md.erb +10 -10
  95. data/docs/resources/windows_task.md.erb +103 -0
  96. data/docs/resources/wmi.md.erb +10 -10
  97. data/docs/resources/x509_certificate.md.erb +146 -0
  98. data/docs/resources/xinetd_conf.md.erb +17 -17
  99. data/docs/resources/xml.md.erb +75 -0
  100. data/docs/resources/yaml.md.erb +25 -11
  101. data/docs/resources/yum.md.erb +24 -16
  102. data/docs/resources/zfs_dataset.md.erb +63 -0
  103. data/docs/resources/zfs_pool.md.erb +57 -0
  104. data/docs/ruby_usage.md +50 -0
  105. data/docs/shared/matcher_cmp.md.erb +4 -6
  106. data/examples/inheritance/README.md +49 -3
  107. data/examples/inheritance/controls/example.rb +4 -1
  108. data/examples/inheritance/inspec.yml +3 -1
  109. data/examples/meta-profile/README.md +29 -3
  110. data/examples/meta-profile/controls/example.rb +10 -5
  111. data/examples/meta-profile/inspec.yml +4 -8
  112. data/examples/profile/README.md +1 -1
  113. data/examples/profile/controls/example.rb +0 -1
  114. data/examples/profile/controls/gordon.rb +0 -1
  115. data/examples/profile/inspec.yml +1 -1
  116. data/examples/profile-attribute/inspec.yml +1 -1
  117. data/examples/profile-sensitive/README.md +29 -0
  118. data/examples/profile-sensitive/controls/sensitive-failures.rb +9 -0
  119. data/examples/profile-sensitive/controls/sensitive.rb +9 -0
  120. data/examples/profile-sensitive/inspec.yml +8 -0
  121. data/inspec.gemspec +10 -2
  122. data/lib/bundles/inspec-artifact/README.md +1 -0
  123. data/lib/bundles/inspec-artifact/cli.rb +284 -0
  124. data/lib/bundles/inspec-artifact.rb +7 -0
  125. data/lib/bundles/inspec-compliance/README.md +44 -15
  126. data/lib/bundles/inspec-compliance/api.rb +135 -29
  127. data/lib/bundles/inspec-compliance/cli.rb +128 -21
  128. data/lib/bundles/inspec-compliance/configuration.rb +8 -0
  129. data/lib/bundles/inspec-compliance/http.rb +26 -19
  130. data/lib/bundles/inspec-compliance/target.rb +50 -25
  131. data/lib/bundles/inspec-habitat/cli.rb +31 -0
  132. data/lib/bundles/inspec-habitat/log.rb +10 -0
  133. data/lib/bundles/inspec-habitat/profile.rb +372 -0
  134. data/lib/bundles/inspec-habitat.rb +12 -0
  135. data/lib/bundles/inspec-init/templates/profile/controls/example.rb +0 -1
  136. data/lib/bundles/inspec-init/templates/profile/inspec.yml +1 -1
  137. data/lib/bundles/inspec-supermarket/api.rb +7 -5
  138. data/lib/bundles/inspec-supermarket/cli.rb +2 -2
  139. data/lib/fetchers/git.rb +4 -2
  140. data/lib/fetchers/local.rb +4 -1
  141. data/lib/fetchers/url.rb +64 -10
  142. data/lib/inspec/archive/tar.rb +1 -1
  143. data/lib/inspec/backend.rb +26 -3
  144. data/lib/inspec/base_cli.rb +44 -7
  145. data/lib/inspec/cached_fetcher.rb +2 -2
  146. data/lib/inspec/cli.rb +34 -12
  147. data/lib/inspec/completions/fish.sh.erb +34 -0
  148. data/lib/inspec/control_eval_context.rb +0 -2
  149. data/lib/inspec/dependencies/cache.rb +0 -1
  150. data/lib/inspec/dependencies/dependency_set.rb +2 -2
  151. data/lib/inspec/dependencies/lockfile.rb +13 -6
  152. data/lib/inspec/dependencies/requirement.rb +6 -6
  153. data/lib/inspec/dependencies/resolver.rb +4 -4
  154. data/lib/inspec/dsl.rb +3 -5
  155. data/lib/inspec/env_printer.rb +9 -1
  156. data/lib/inspec/exceptions.rb +8 -0
  157. data/lib/inspec/fetcher.rb +1 -1
  158. data/lib/inspec/file_provider.rb +47 -11
  159. data/lib/inspec/library_eval_context.rb +1 -1
  160. data/lib/inspec/metadata.rb +62 -18
  161. data/lib/inspec/method_source.rb +24 -0
  162. data/lib/inspec/objects/attribute.rb +21 -0
  163. data/lib/inspec/objects/control.rb +21 -3
  164. data/lib/inspec/objects/each_loop.rb +2 -1
  165. data/lib/inspec/objects/list.rb +1 -1
  166. data/lib/inspec/objects/or_test.rb +17 -2
  167. data/lib/inspec/objects/tag.rb +27 -0
  168. data/lib/inspec/objects/test.rb +9 -8
  169. data/lib/inspec/objects.rb +1 -0
  170. data/lib/inspec/plugins/fetcher.rb +4 -5
  171. data/lib/inspec/plugins/resource.rb +1 -2
  172. data/lib/inspec/plugins/source_reader.rb +3 -3
  173. data/lib/inspec/plugins.rb +1 -1
  174. data/lib/inspec/polyfill.rb +0 -1
  175. data/lib/inspec/profile.rb +92 -23
  176. data/lib/inspec/profile_context.rb +1 -1
  177. data/lib/inspec/profile_vendor.rb +66 -0
  178. data/lib/inspec/resource.rb +29 -3
  179. data/lib/inspec/rspec_json_formatter.rb +672 -285
  180. data/lib/inspec/rule.rb +12 -16
  181. data/lib/inspec/runner.rb +26 -15
  182. data/lib/inspec/runner_rspec.rb +1 -0
  183. data/lib/inspec/runtime_profile.rb +26 -0
  184. data/lib/inspec/schema.rb +185 -0
  185. data/lib/inspec/secrets/yaml.rb +8 -1
  186. data/lib/inspec/secrets.rb +1 -1
  187. data/lib/inspec/shell.rb +92 -22
  188. data/lib/inspec/source_reader.rb +1 -1
  189. data/lib/inspec/version.rb +1 -1
  190. data/lib/inspec.rb +1 -1
  191. data/lib/matchers/matchers.rb +67 -17
  192. data/lib/resources/aide_conf.rb +162 -0
  193. data/lib/resources/apache.rb +0 -1
  194. data/lib/resources/apache_conf.rb +3 -3
  195. data/lib/resources/apt.rb +2 -1
  196. data/lib/resources/audit_policy.rb +0 -1
  197. data/lib/resources/auditd_conf.rb +1 -2
  198. data/lib/resources/auditd_rules.rb +5 -5
  199. data/lib/resources/bond.rb +1 -1
  200. data/lib/resources/bridge.rb +1 -1
  201. data/lib/resources/command.rb +5 -3
  202. data/lib/resources/crontab.rb +102 -0
  203. data/lib/resources/csv.rb +18 -1
  204. data/lib/resources/dh_params.rb +84 -0
  205. data/lib/resources/directory.rb +7 -3
  206. data/lib/resources/docker.rb +198 -0
  207. data/lib/resources/docker_container.rb +114 -0
  208. data/lib/resources/docker_image.rb +96 -0
  209. data/lib/resources/etc_group.rb +2 -3
  210. data/lib/resources/etc_hosts.rb +81 -0
  211. data/lib/resources/file.rb +88 -30
  212. data/lib/resources/gem.rb +26 -6
  213. data/lib/resources/groups.rb +4 -5
  214. data/lib/resources/grub_conf.rb +3 -4
  215. data/lib/resources/host.rb +175 -35
  216. data/lib/resources/http.rb +73 -0
  217. data/lib/resources/iis_app.rb +103 -0
  218. data/lib/resources/iis_site.rb +23 -0
  219. data/lib/resources/inetd_conf.rb +9 -4
  220. data/lib/resources/interface.rb +4 -3
  221. data/lib/resources/json.rb +37 -14
  222. data/lib/resources/kernel_module.rb +77 -10
  223. data/lib/resources/kernel_parameter.rb +0 -1
  224. data/lib/resources/key_rsa.rb +67 -0
  225. data/lib/resources/limits_conf.rb +3 -4
  226. data/lib/resources/login_def.rb +2 -3
  227. data/lib/resources/mount.rb +34 -4
  228. data/lib/resources/mssql_session.rb +81 -12
  229. data/lib/resources/mysql.rb +0 -1
  230. data/lib/resources/mysql_conf.rb +1 -2
  231. data/lib/resources/mysql_session.rb +18 -7
  232. data/lib/resources/nginx_conf.rb +95 -0
  233. data/lib/resources/ntp_conf.rb +2 -3
  234. data/lib/resources/oracledb_session.rb +138 -0
  235. data/lib/resources/os_env.rb +7 -5
  236. data/lib/resources/package.rb +70 -13
  237. data/lib/resources/packages.rb +111 -0
  238. data/lib/resources/parse_config.rb +3 -4
  239. data/lib/resources/passwd.rb +4 -5
  240. data/lib/resources/pip.rb +29 -21
  241. data/lib/resources/port.rb +133 -14
  242. data/lib/resources/postgres.rb +53 -43
  243. data/lib/resources/postgres_conf.rb +40 -13
  244. data/lib/resources/postgres_hba_conf.rb +101 -0
  245. data/lib/resources/postgres_ident_conf.rb +79 -0
  246. data/lib/resources/postgres_session.rb +28 -20
  247. data/lib/resources/powershell.rb +2 -2
  248. data/lib/resources/processes.rb +61 -26
  249. data/lib/resources/rabbitmq_conf.rb +53 -0
  250. data/lib/resources/registry_key.rb +34 -11
  251. data/lib/resources/security_policy.rb +2 -2
  252. data/lib/resources/service.rb +17 -7
  253. data/lib/resources/ssh_conf.rb +17 -6
  254. data/lib/resources/ssl.rb +3 -4
  255. data/lib/resources/sys_info.rb +1 -1
  256. data/lib/resources/toml.rb +26 -0
  257. data/lib/resources/users.rb +41 -41
  258. data/lib/resources/virtualization.rb +252 -0
  259. data/lib/resources/windows_task.rb +106 -0
  260. data/lib/resources/x509_certificate.rb +143 -0
  261. data/lib/resources/xinetd.rb +18 -2
  262. data/lib/resources/xml.rb +27 -0
  263. data/lib/resources/yaml.rb +10 -2
  264. data/lib/resources/yum.rb +25 -7
  265. data/lib/resources/zfs_dataset.rb +60 -0
  266. data/lib/resources/zfs_pool.rb +49 -0
  267. data/lib/source_readers/flat.rb +2 -1
  268. data/lib/source_readers/inspec.rb +30 -11
  269. data/lib/utils/command_wrapper.rb +3 -3
  270. data/lib/utils/database_helpers.rb +77 -0
  271. data/lib/utils/erlang_parser.rb +192 -0
  272. data/lib/utils/filter.rb +2 -1
  273. data/lib/utils/filter_array.rb +0 -1
  274. data/lib/utils/find_files.rb +1 -2
  275. data/lib/utils/latest_version.rb +21 -0
  276. data/lib/utils/nginx_parser.rb +76 -0
  277. data/lib/utils/object_traversal.rb +5 -4
  278. data/lib/utils/parser.rb +23 -4
  279. data/lib/utils/plugin_registry.rb +3 -3
  280. data/lib/utils/simpleconfig.rb +25 -8
  281. data/lib/utils/spdx.rb +13 -0
  282. data/lib/utils/spdx.txt +344 -0
  283. metadata +168 -22
  284. data/docs/cli.md +0 -342
  285. data/docs/resources/process.md.erb +0 -73
  286. /data/docs/{plugin_kitchen_inspec.html.md → plugin_kitchen_inspec.md} +0 -0
@@ -117,7 +117,7 @@ module Inspec::Resources
117
117
  return skip_resource "Can't read security policy" if cmd.exit_status.to_i != 0
118
118
  @content = cmd.stdout
119
119
 
120
- if @content.empty? && file.size > 0
120
+ if @content.empty? && !file.empty?
121
121
  return skip_resource "Can't read security policy"
122
122
  end
123
123
  @content
@@ -132,7 +132,7 @@ module Inspec::Resources
132
132
 
133
133
  conf = SimpleConfig.new(
134
134
  @content,
135
- assignment_re: /^\s*(.*)=\s*(\S*)\s*$/,
135
+ assignment_regex: /^\s*(.*)=\s*(\S*)\s*$/,
136
136
  )
137
137
  @params = convert_hash(conf.params)
138
138
  end
@@ -2,7 +2,7 @@
2
2
  # author: Christoph Hartmann
3
3
  # author: Dominik Richter
4
4
  # author: Stephan Renatus
5
- # license: All rights reserved
5
+
6
6
  require 'hashie'
7
7
 
8
8
  module Inspec::Resources
@@ -120,6 +120,13 @@ module Inspec::Resources
120
120
  else
121
121
  Systemd.new(inspec, service_ctl)
122
122
  end
123
+ elsif %w{linuxmint}.include?(platform)
124
+ version = os[:release].to_f
125
+ if version < 18
126
+ Upstart.new(inspec, service_ctl)
127
+ else
128
+ Systemd.new(inspec, service_ctl)
129
+ end
123
130
  elsif %w{debian}.include?(platform)
124
131
  version = os[:release].to_i
125
132
  if version > 7
@@ -127,9 +134,9 @@ module Inspec::Resources
127
134
  else
128
135
  SysV.new(inspec, service_ctl || '/usr/sbin/service')
129
136
  end
130
- elsif %w{redhat fedora centos}.include?(platform)
137
+ elsif %w{redhat fedora centos oracle}.include?(platform)
131
138
  version = os[:release].to_i
132
- if (%w{ redhat centos }.include?(platform) && version >= 7) || (platform == 'fedora' && version >= 15)
139
+ if (%w{ redhat centos oracle }.include?(platform) && version >= 7) || (platform == 'fedora' && version >= 15)
133
140
  Systemd.new(inspec, service_ctl)
134
141
  else
135
142
  SysV.new(inspec, service_ctl || '/sbin/service')
@@ -144,6 +151,8 @@ module Inspec::Resources
144
151
  BSDInit.new(inspec, service_ctl)
145
152
  elsif %w{arch}.include?(platform)
146
153
  Systemd.new(inspec, service_ctl)
154
+ elsif %w{coreos}.include?(platform)
155
+ Systemd.new(inspec, service_ctl)
147
156
  elsif %w{suse opensuse}.include?(platform)
148
157
  if os[:release].to_i >= 12
149
158
  Systemd.new(inspec, service_ctl)
@@ -255,7 +264,7 @@ module Inspec::Resources
255
264
  # parse data
256
265
  params = SimpleConfig.new(
257
266
  cmd.stdout.chomp,
258
- assignment_re: /^\s*([^=]*?)\s*=\s*(.*?)\s*$/,
267
+ assignment_regex: /^\s*([^=]*?)\s*=\s*(.*?)\s*$/,
259
268
  multiple_values: false,
260
269
  ).params
261
270
 
@@ -329,7 +338,7 @@ module Inspec::Resources
329
338
  status = inspec.command("#{service_ctl} status #{service_name}")
330
339
 
331
340
  # fallback for systemv services, those are not handled via `initctl`
332
- return SysV.new(inspec).info(service_name) if status.exit_status.to_i != 0
341
+ return SysV.new(inspec).info(service_name) if status.exit_status.to_i != 0 || status.stdout == ''
333
342
 
334
343
  # @see: http://upstart.ubuntu.com/cookbook/#job-states
335
344
  # grep for running to indicate the service is there
@@ -606,7 +615,8 @@ module Inspec::Resources
606
615
  def service_enabled?(service)
607
616
  !service['WMI'].nil? &&
608
617
  !service['WMI']['StartMode'].nil? &&
609
- service['WMI']['StartMode'] == 'Auto'
618
+ (service['WMI']['StartMode'] == 'Auto' ||
619
+ service['WMI']['StartMode'] == 'Manual')
610
620
  end
611
621
 
612
622
  # detect if service is running
@@ -629,7 +639,7 @@ module Inspec::Resources
629
639
 
630
640
  params = SimpleConfig.new(
631
641
  cmd.stdout.chomp,
632
- assignment_re: /^(\w+)\s*(.*)$/,
642
+ assignment_regex: /^(\w+)\s*(.*)$/,
633
643
  multiple_values: false,
634
644
  ).params
635
645
 
@@ -2,17 +2,18 @@
2
2
  # copyright: 2015, Vulcano Security GmbH
3
3
  # author: Dominik Richter
4
4
  # author: Christoph Hartmann
5
- # license: All rights reserved
6
5
 
7
6
  require 'utils/simpleconfig'
8
7
 
9
8
  module Inspec::Resources
10
9
  class SshConf < Inspec.resource(1)
11
10
  name 'ssh_config'
12
- desc 'Use the sshd_config InSpec audit resource to test configuration data for the Open SSH daemon located at /etc/ssh/sshd_config on Linux and UNIX platforms. sshd---the Open SSH daemon---listens on dedicated ports, starts a daemon for each incoming connection, and then handles encryption, authentication, key exchanges, command executation, and data exchanges.'
11
+ desc 'Use the `ssh_config` InSpec audit resource to test OpenSSH client configuration data located at `/etc/ssh/ssh_config` on Linux and Unix platforms.'
13
12
  example "
14
- describe sshd_config do
15
- its('Protocol') { should eq '2' }
13
+ describe ssh_config do
14
+ its('cipher') { should contain '3des' }
15
+ its('port') { should eq '22' }
16
+ its('hostname') { should include('example.com') }
16
17
  end
17
18
  "
18
19
 
@@ -62,7 +63,7 @@ module Inspec::Resources
62
63
  end
63
64
 
64
65
  @content = file.content
65
- if @content.empty? && file.size > 0
66
+ if @content.empty? && !file.empty?
66
67
  return skip_resource "Can't read file \"#{@conf_path}\""
67
68
  end
68
69
 
@@ -74,7 +75,7 @@ module Inspec::Resources
74
75
  return @params = {} if read_content.nil?
75
76
  conf = SimpleConfig.new(
76
77
  read_content,
77
- assignment_re: /^\s*(\S+?)\s+(.*?)\s*$/,
78
+ assignment_regex: /^\s*(\S+?)\s+(.*?)\s*$/,
78
79
  multiple_values: true,
79
80
  )
80
81
  @params = convert_hash(conf.params)
@@ -83,9 +84,19 @@ module Inspec::Resources
83
84
 
84
85
  class SshdConf < SshConf
85
86
  name 'sshd_config'
87
+ desc 'Use the sshd_config InSpec audit resource to test configuration data for the Open SSH daemon located at /etc/ssh/sshd_config on Linux and UNIX platforms. sshd---the Open SSH daemon---listens on dedicated ports, starts a daemon for each incoming connection, and then handles encryption, authentication, key exchanges, command execution, and data exchanges.'
88
+ example "
89
+ describe sshd_config do
90
+ its('Protocol') { should eq '2' }
91
+ end
92
+ "
86
93
 
87
94
  def initialize(path = nil)
88
95
  super(path || '/etc/ssh/sshd_config')
89
96
  end
97
+
98
+ def to_s
99
+ 'SSHD Configuration'
100
+ end
90
101
  end
91
102
  end
data/lib/resources/ssl.rb CHANGED
@@ -1,6 +1,5 @@
1
1
  # encoding: utf-8
2
2
  # copyright: 2015, Chef Software Inc.
3
- # license: All rights reserved
4
3
  # author: Dominik Richter
5
4
  # author: Christoph Hartmann
6
5
 
@@ -41,7 +40,7 @@ class SSL < Inspec.resource(1)
41
40
  'tls1.2',
42
41
  ].freeze
43
42
 
44
- attr_reader :host, :port
43
+ attr_reader :host, :port, :timeout, :retries
45
44
 
46
45
  def initialize(opts = {})
47
46
  @host = opts[:host]
@@ -52,7 +51,7 @@ class SSL < Inspec.resource(1)
52
51
  elsif inspec.backend.class.to_s == 'Train::Transports::Local::Connection'
53
52
  @host = 'localhost'
54
53
  else
55
- fail 'Cannot determine host for SSL test. Please specify it or use a different target.'
54
+ raise 'Cannot determine host for SSL test. Please specify it or use a different target.'
56
55
  end
57
56
  end
58
57
  @port = opts[:port] || 443
@@ -71,7 +70,7 @@ class SSL < Inspec.resource(1)
71
70
  res = Parallel.map(groups, in_threads: 8) do |proto, e|
72
71
  [proto, SSLShake.hello(x.resource.host, port: x.resource.port,
73
72
  protocol: proto, ciphers: e.map(&:cipher),
74
- timeout: @timeout, retries: @retries)]
73
+ timeout: x.resource.timeout, retries: x.resource.retries, servername: x.resource.host)]
75
74
  end
76
75
  Hash[res]
77
76
  }
@@ -14,7 +14,7 @@ module Inspec::Resources
14
14
  # returns the hostname of the local system
15
15
  def hostname
16
16
  os = inspec.os
17
- if os.linux?
17
+ if os.linux? || os.darwin?
18
18
  inspec.command('hostname').stdout.chomp
19
19
  elsif os.windows?
20
20
  inspec.powershell('$env:computername').stdout.chomp
@@ -0,0 +1,26 @@
1
+ # encoding: utf-8
2
+ # author: Nolan Davidson
3
+
4
+ require 'toml'
5
+
6
+ module Inspec::Resources
7
+ class TomlConfig < JsonConfig
8
+ name 'toml'
9
+ desc 'Use the toml InSpec resource to test configuration data in a TOML file'
10
+ example "
11
+ describe toml('default.toml') do
12
+ its('key') { should eq('value') }
13
+ its (['arr', 1]) { should eq 2 }
14
+ its (['mytable', 'key1']) { should eq 'value1' }
15
+ end
16
+ "
17
+
18
+ def parse(content)
19
+ TOML::Parser.new(content).parsed
20
+ end
21
+
22
+ def to_s
23
+ "TOML #{@path}"
24
+ end
25
+ end
26
+ end
@@ -57,7 +57,7 @@ module Inspec::Resources
57
57
  name 'users'
58
58
  desc 'Use the users InSpec audit resource to test local user profiles. Users can be filtered by groups to which they belong, the frequency of required password changes, the directory paths to home and shell.'
59
59
  example "
60
- describe users.where(uid: 0).entries do
60
+ describe users.where { uid == 0 }.entries do
61
61
  it { should eq ['root'] }
62
62
  its('uids') { should eq [1234] }
63
63
  its('gids') { should eq [1234] }
@@ -242,7 +242,7 @@ module Inspec::Resources
242
242
 
243
243
  def has_authorized_key?(_compare_key)
244
244
  deprecated('has_authorized_key?')
245
- fail NotImplementedError
245
+ raise NotImplementedError
246
246
  end
247
247
 
248
248
  def deprecated(name, alternative = nil)
@@ -292,7 +292,7 @@ module Inspec::Resources
292
292
  # groups: '',
293
293
  # }
294
294
  def identity(_username)
295
- fail 'user provider must implement the `identity` method'
295
+ raise 'user provider must implement the `identity` method'
296
296
  end
297
297
 
298
298
  # returns optional information about a user, eg shell
@@ -313,7 +313,7 @@ module Inspec::Resources
313
313
 
314
314
  # returns an array with users
315
315
  def list_users
316
- fail 'user provider must implement the `list_users` method'
316
+ raise 'user provider must implement the `list_users` method'
317
317
  end
318
318
 
319
319
  # retuns all aspects of the user as one hash
@@ -358,7 +358,7 @@ module Inspec::Resources
358
358
  SimpleConfig.new(
359
359
  line,
360
360
  line_separator: ',',
361
- assignment_re: /^\s*([^\(]*?)\s*\(\s*(.*?)\)*$/,
361
+ assignment_regex: /^\s*([^\(]*?)\s*\(\s*(.*?)\)*$/,
362
362
  group_re: nil,
363
363
  multiple_values: false,
364
364
  ).params
@@ -372,7 +372,7 @@ module Inspec::Resources
372
372
  # parse words
373
373
  params = SimpleConfig.new(
374
374
  parse_id_entries(cmd.stdout.chomp),
375
- assignment_re: /^\s*([^=]*?)\s*=\s*(.*?)\s*$/,
375
+ assignment_regex: /^\s*([^=]*?)\s*=\s*(.*?)\s*$/,
376
376
  group_re: nil,
377
377
  multiple_values: false,
378
378
  ).params
@@ -419,7 +419,7 @@ module Inspec::Resources
419
419
 
420
420
  params = SimpleConfig.new(
421
421
  cmd.stdout.chomp,
422
- assignment_re: /^\s*([^:]*?)\s*:\s*(.*?)\s*$/,
422
+ assignment_regex: /^\s*([^:]*?)\s*:\s*(.*?)\s*$/,
423
423
  group_re: nil,
424
424
  multiple_values: false,
425
425
  ).params
@@ -512,7 +512,7 @@ module Inspec::Resources
512
512
 
513
513
  params = SimpleConfig.new(
514
514
  cmd.stdout.chomp,
515
- assignment_re: /^\s*([^:]*?)\s*:\s*(.*?)\s*$/,
515
+ assignment_regex: /^\s*([^:]*?)\s*:\s*(.*?)\s*$/,
516
516
  group_re: nil,
517
517
  multiple_values: false,
518
518
  ).params
@@ -556,7 +556,7 @@ module Inspec::Resources
556
556
  def parse_windows_account(username)
557
557
  account = username.split('\\')
558
558
  name = account.pop
559
- domain = account.pop if account.size > 0
559
+ domain = account.pop if !account.empty?
560
560
  [name, domain]
561
561
  end
562
562
 
@@ -565,7 +565,7 @@ module Inspec::Resources
565
565
  name, _domain = parse_windows_account(username)
566
566
  return if collect_user_details.nil?
567
567
  res = collect_user_details.select { |user| user[:username] == name }
568
- res[0] if res.length > 0
568
+ res[0] if !res.empty?
569
569
  end
570
570
 
571
571
  def list_users
@@ -576,42 +576,42 @@ module Inspec::Resources
576
576
  def collect_user_details # rubocop:disable Metrics/MethodLength
577
577
  return @users_cache if defined?(@users_cache)
578
578
  script = <<-EOH
579
- Function ConvertTo-SID { Param([byte[]]$BinarySID)
580
- (New-Object System.Security.Principal.SecurityIdentifier($BinarySID,0)).Value
579
+ Function ConvertTo-SID { Param([byte[]]$BinarySID)
580
+ (New-Object System.Security.Principal.SecurityIdentifier($BinarySID,0)).Value
581
581
  }
582
582
 
583
- Function Convert-UserFlag { Param ($UserFlag)
584
- $List = @()
585
- Switch ($UserFlag) {
586
- ($UserFlag -BOR 0x0001) { $List += 'SCRIPT' }
587
- ($UserFlag -BOR 0x0002) { $List += 'ACCOUNTDISABLE' }
588
- ($UserFlag -BOR 0x0008) { $List += 'HOMEDIR_REQUIRED' }
589
- ($UserFlag -BOR 0x0010) { $List += 'LOCKOUT' }
590
- ($UserFlag -BOR 0x0020) { $List += 'PASSWD_NOTREQD' }
591
- ($UserFlag -BOR 0x0040) { $List += 'PASSWD_CANT_CHANGE' }
592
- ($UserFlag -BOR 0x0080) { $List += 'ENCRYPTED_TEXT_PWD_ALLOWED' }
593
- ($UserFlag -BOR 0x0100) { $List += 'TEMP_DUPLICATE_ACCOUNT' }
594
- ($UserFlag -BOR 0x0200) { $List += 'NORMAL_ACCOUNT' }
595
- ($UserFlag -BOR 0x0800) { $List += 'INTERDOMAIN_TRUST_ACCOUNT' }
596
- ($UserFlag -BOR 0x1000) { $List += 'WORKSTATION_TRUST_ACCOUNT' }
597
- ($UserFlag -BOR 0x2000) { $List += 'SERVER_TRUST_ACCOUNT' }
598
- ($UserFlag -BOR 0x10000) { $List += 'DONT_EXPIRE_PASSWORD' }
599
- ($UserFlag -BOR 0x20000) { $List += 'MNS_LOGON_ACCOUNT' }
600
- ($UserFlag -BOR 0x40000) { $List += 'SMARTCARD_REQUIRED' }
601
- ($UserFlag -BOR 0x80000) { $List += 'TRUSTED_FOR_DELEGATION' }
602
- ($UserFlag -BOR 0x100000) { $List += 'NOT_DELEGATED' }
603
- ($UserFlag -BOR 0x200000) { $List += 'USE_DES_KEY_ONLY' }
604
- ($UserFlag -BOR 0x400000) { $List += 'DONT_REQ_PREAUTH' }
605
- ($UserFlag -BOR 0x800000) { $List += 'PASSWORD_EXPIRED' }
606
- ($UserFlag -BOR 0x1000000) { $List += 'TRUSTED_TO_AUTH_FOR_DELEGATION' }
607
- ($UserFlag -BOR 0x04000000) { $List += 'PARTIAL_SECRETS_ACCOUNT' }
583
+ Function Convert-UserFlag { Param ($UserFlag)
584
+ $List = @()
585
+ Switch ($UserFlag) {
586
+ ($UserFlag -BOR 0x0001) { $List += 'SCRIPT' }
587
+ ($UserFlag -BOR 0x0002) { $List += 'ACCOUNTDISABLE' }
588
+ ($UserFlag -BOR 0x0008) { $List += 'HOMEDIR_REQUIRED' }
589
+ ($UserFlag -BOR 0x0010) { $List += 'LOCKOUT' }
590
+ ($UserFlag -BOR 0x0020) { $List += 'PASSWD_NOTREQD' }
591
+ ($UserFlag -BOR 0x0040) { $List += 'PASSWD_CANT_CHANGE' }
592
+ ($UserFlag -BOR 0x0080) { $List += 'ENCRYPTED_TEXT_PWD_ALLOWED' }
593
+ ($UserFlag -BOR 0x0100) { $List += 'TEMP_DUPLICATE_ACCOUNT' }
594
+ ($UserFlag -BOR 0x0200) { $List += 'NORMAL_ACCOUNT' }
595
+ ($UserFlag -BOR 0x0800) { $List += 'INTERDOMAIN_TRUST_ACCOUNT' }
596
+ ($UserFlag -BOR 0x1000) { $List += 'WORKSTATION_TRUST_ACCOUNT' }
597
+ ($UserFlag -BOR 0x2000) { $List += 'SERVER_TRUST_ACCOUNT' }
598
+ ($UserFlag -BOR 0x10000) { $List += 'DONT_EXPIRE_PASSWORD' }
599
+ ($UserFlag -BOR 0x20000) { $List += 'MNS_LOGON_ACCOUNT' }
600
+ ($UserFlag -BOR 0x40000) { $List += 'SMARTCARD_REQUIRED' }
601
+ ($UserFlag -BOR 0x80000) { $List += 'TRUSTED_FOR_DELEGATION' }
602
+ ($UserFlag -BOR 0x100000) { $List += 'NOT_DELEGATED' }
603
+ ($UserFlag -BOR 0x200000) { $List += 'USE_DES_KEY_ONLY' }
604
+ ($UserFlag -BOR 0x400000) { $List += 'DONT_REQ_PREAUTH' }
605
+ ($UserFlag -BOR 0x800000) { $List += 'PASSWORD_EXPIRED' }
606
+ ($UserFlag -BOR 0x1000000) { $List += 'TRUSTED_TO_AUTH_FOR_DELEGATION' }
607
+ ($UserFlag -BOR 0x04000000) { $List += 'PARTIAL_SECRETS_ACCOUNT' }
608
608
  }
609
609
  $List
610
610
  }
611
611
 
612
- $Computername = $Env:Computername
613
- $adsi = [ADSI]"WinNT://$Computername"
614
- $adsi.Children | where {$_.SchemaClassName -eq 'user'} | ForEach {
612
+ $Computername = $Env:Computername
613
+ $adsi = [ADSI]"WinNT://$Computername"
614
+ $adsi.Children | where {$_.SchemaClassName -eq 'user'} | ForEach {
615
615
  New-Object PSObject -property @{
616
616
  uid = ConvertTo-SID -BinarySID $_.ObjectSID[0]
617
617
  username = $_.Name[0]
@@ -627,7 +627,7 @@ $adsi.Children | where {$_.SchemaClassName -eq 'user'} | ForEach {
627
627
  maxbadpasswords = $_.MaxBadPasswordsAllowed[0]
628
628
  gid = $null
629
629
  group = $null
630
- groups = $null
630
+ groups = @($_.Groups() | Foreach-Object { $_.GetType().InvokeMember('Name', 'GetProperty', $null, $_, $null) })
631
631
  home = $_.HomeDirectory[0]
632
632
  shell = $null
633
633
  domain = $Computername
@@ -0,0 +1,252 @@
1
+ # encoding: utf-8
2
+ # author: Takaaki Furukawa
3
+
4
+ require 'hashie/mash'
5
+
6
+ module Inspec::Resources
7
+ class Virtualization < Inspec.resource(1) # rubocop:disable Metrics/ClassLength
8
+ name 'virtualization'
9
+ desc 'Use the virtualization InSpec audit resource to test the virtualization platform on which the system is running'
10
+ example "
11
+ describe virtualization do
12
+ its('system') { should eq 'docker' }
13
+ end
14
+
15
+ describe virtualization do
16
+ its('role') { should eq 'guest' }
17
+ end
18
+
19
+ control 'test' do
20
+ describe file('/var/tmp/foo') do
21
+ it { should be_file }
22
+ end
23
+ only_if { virtualization.system == 'docker' }
24
+ end
25
+ "
26
+
27
+ def initialize
28
+ unless inspec.os.linux?
29
+ skip_resource 'The `virtualization` resource is not supported on your OS yet.'
30
+ else
31
+ collect_data_linux
32
+ end
33
+ end
34
+
35
+ # add helper methods for easy access of properties
36
+ # allows users to use virtualization.role, virtualization.system
37
+ %w{role system}.each do |property|
38
+ define_method(property.to_sym) do
39
+ @virtualization_data[property.to_sym]
40
+ end
41
+ end
42
+
43
+ def params
44
+ collect_data_linux
45
+ end
46
+
47
+ def to_s
48
+ 'Virtualization Detection'
49
+ end
50
+
51
+ private
52
+
53
+ def lxc_version_exists?
54
+ inspec.command('lxc-version').exist?
55
+ end
56
+
57
+ def docker_exists?
58
+ inspec.command('docker').exist?
59
+ end
60
+
61
+ def nova_exists?
62
+ inspec.command('nova').exist?
63
+ end
64
+
65
+ # Detect Xen
66
+ # /proc/xen is an empty dir for EL6 + Linode Guests + Paravirt EC2 instances
67
+ # Notes:
68
+ # - cpuid of guests, if we could get it, would also be a clue
69
+ # - may be able to determine if under paravirt from /dev/xen/evtchn (See OHAI-253)
70
+ # - Additional edge cases likely should not change the above assumptions
71
+ # but rather be additive - btm
72
+ def detect_xen
73
+ return false unless inspec.file('/proc/xen').exist?
74
+ @virtualization_data[:system] = 'xen'
75
+ @virtualization_data[:role] = 'guest'
76
+
77
+ # This file should exist on most Xen systems, normally empty for guests
78
+ if inspec.file('/proc/xen/capabilities').exist? &&
79
+ inspec.file('/proc/xen/capabilities').content =~ /control_d/i # rubocop:disable Style/MultilineOperationIndentation
80
+ @virtualization_data[:role] = 'host'
81
+ end
82
+ true
83
+ end
84
+
85
+ # Detect Virtualbox from kernel module
86
+ def detect_virtualbox
87
+ return false unless inspec.file('/proc/modules').exist?
88
+ modules = inspec.file('/proc/modules').content
89
+ if modules =~ /^vboxdrv/
90
+ Inspec::Log.debug('Plugin Virtualization: /proc/modules contains vboxdrv. Detecting as vbox host')
91
+ @virtualization_data[:system] = 'vbox'
92
+ @virtualization_data[:role] = 'host'
93
+ elsif modules =~ /^vboxguest/
94
+ Inspec::Log.debug('Plugin Virtualization: /proc/modules contains vboxguest. Detecting as vbox guest')
95
+ @virtualization_data[:system] = 'vbox'
96
+ @virtualization_data[:role] = 'guest'
97
+ else
98
+ return false
99
+ end
100
+ true
101
+ end
102
+
103
+ # if nova binary is present we're on an openstack host
104
+ def detect_openstack
105
+ return false unless nova_exists?
106
+ @virtualization_data[:system] = 'openstack'
107
+ @virtualization_data[:role] = 'host'
108
+ true
109
+ end
110
+
111
+ # Detect paravirt KVM/QEMU from cpuinfo, report as KVM
112
+ def detect_kvm_from_cpuinfo
113
+ return false unless inspec.file('/proc/cpuinfo').content =~ /QEMU Virtual CPU|Common KVM processor|Common 32-bit KVM processor/
114
+ @virtualization_data[:system] = 'kvm'
115
+ @virtualization_data[:role] = 'guest'
116
+ true
117
+ end
118
+
119
+ # Detect KVM systems via /sys
120
+ # guests will have the hypervisor cpu feature that hosts don't have
121
+ def detect_kvm_from_sys
122
+ return false unless inspec.file('/sys/devices/virtual/misc/kvm').exist?
123
+ if inspec.file('/proc/cpuinfo').content =~ /hypervisor/
124
+ @virtualization_data[:system] = 'kvm'
125
+ @virtualization_data[:role] = 'guest'
126
+ else
127
+ @virtualization_data[:system] = 'kvm'
128
+ @virtualization_data[:role] = 'host'
129
+ end
130
+ true
131
+ end
132
+
133
+ # Detect OpenVZ / Virtuozzo.
134
+ # http://wiki.openvz.org/BC_proc_entries
135
+ def detect_openvz
136
+ if inspec.file('/proc/bc/0').exist?
137
+ @virtualization_data[:system] = 'openvz'
138
+ @virtualization_data[:role] = 'host'
139
+ elsif inspec.file('/proc/vz').exist?
140
+ @virtualization_data[:system] = 'openvz'
141
+ @virtualization_data[:role] = 'guest'
142
+ else
143
+ return false
144
+ end
145
+ true
146
+ end
147
+
148
+ # Detect Parallels virtual machine from pci devices
149
+ def detect_parallels
150
+ return false unless inspec.file('/proc/bus/pci/devices').content =~ /1ab84000/
151
+ @virtualization_data[:system] = 'parallels'
152
+ @virtualization_data[:role] = 'guest'
153
+ true
154
+ end
155
+
156
+ # Detect Linux-VServer
157
+ def detect_linux_vserver
158
+ return false unless inspec.file('/proc/self/status').exist?
159
+ proc_self_status = inspec.file('/proc/self/status').content
160
+ vxid = proc_self_status.match(/^(s_context|VxID):\s*(\d+)$/)
161
+ return false unless vxid && vxid[2]
162
+ @virtualization_data[:system] = 'linux-vserver'
163
+ if vxid[2] == '0'
164
+ @virtualization_data[:role] = 'host'
165
+ else
166
+ @virtualization_data[:role] = 'guest'
167
+ end
168
+ true
169
+ end
170
+
171
+ # Detect LXC/Docker
172
+ #
173
+ # /proc/self/cgroup will look like this inside a docker container:
174
+ # <index #>:<subsystem>:/lxc/<hexadecimal container id>
175
+ #
176
+ # /proc/self/cgroup could have a name including alpha/digit/dashes
177
+ # <index #>:<subsystem>:/lxc/<named container id>
178
+ #
179
+ # /proc/self/cgroup could have a non-lxc cgroup name indicating other uses
180
+ # of cgroups. This is probably not LXC/Docker.
181
+ # <index #>:<subsystem>:/Charlie
182
+ #
183
+ # A host which supports cgroups, and has capacity to host lxc containers,
184
+ # will show the subsystems and root (/) namespace.
185
+ # <index #>:<subsystem>:/
186
+ #
187
+ # Full notes, https://tickets.opscode.com/browse/OHAI-551
188
+ # Kernel docs, https://www.kernel.org/doc/Documentation/cgroups
189
+ def detect_lxc_docker
190
+ return false unless inspec.file('/proc/self/cgroup').exist?
191
+ cgroup_content = inspec.file('/proc/self/cgroup').content
192
+ if cgroup_content =~ %r{^\d+:[^:]+:/(lxc|docker)/.+$} ||
193
+ cgroup_content =~ %r{^\d+:[^:]+:/[^/]+/(lxc|docker)-.+$} # rubocop:disable Style/MultilineOperationIndentation
194
+ @virtualization_data[:system] = $1 # rubocop:disable Style/PerlBackrefs
195
+ @virtualization_data[:role] = 'guest'
196
+ elsif lxc_version_exists? && cgroup_content =~ %r{\d:[^:]+:/$}
197
+ # lxc-version shouldn't be installed by default
198
+ # Even so, it is likely we are on an LXC capable host that is not being used as such
199
+ # So we're cautious here to not overwrite other existing values (OHAI-573)
200
+ unless @virtualization_data[:system] && @virtualization_data[:role]
201
+ @virtualization_data[:system] = 'lxc'
202
+ @virtualization_data[:role] = 'host'
203
+ end
204
+ else
205
+ return false
206
+ end
207
+ true
208
+ end
209
+
210
+ def detect_docker
211
+ return false unless inspec.file('/.dockerenv').exist? || inspec.file('/.dockerinit').exist?
212
+ @virtualization_data[:system] = 'docker'
213
+ @virtualization_data[:role] = 'guest'
214
+ true
215
+ end
216
+
217
+ # Detect LXD
218
+ # See https://github.com/lxc/lxd/blob/master/doc/dev-lxd.md
219
+ def detect_lxd
220
+ if inspec.file('/dev/lxd/sock').exist?
221
+ @virtualization_data[:system] = 'lxd'
222
+ @virtualization_data[:role] = 'guest'
223
+ elsif inspec.file('/var/lib/lxd/devlxd').exist?
224
+ @virtualization_data[:system] = 'lxd'
225
+ @virtualization_data[:role] = 'host'
226
+ else
227
+ return false
228
+ end
229
+ true
230
+ end
231
+
232
+ def collect_data_linux # rubocop:disable Metrics/PerceivedComplexity, Metrics/CyclomaticComplexity
233
+ # cache data in an instance var to avoid doing multiple detections for a single test
234
+ @virtualization_data ||= Hashie::Mash.new
235
+ return unless @virtualization_data.empty?
236
+
237
+ # each detect method will return true if it matched and was successfully
238
+ # able to populate @virtualization_data with stuff.
239
+ return if detect_xen
240
+ return if detect_virtualbox
241
+ return if detect_openstack
242
+ return if detect_kvm_from_cpuinfo
243
+ return if detect_kvm_from_sys
244
+ return if detect_openvz
245
+ return if detect_parallels
246
+ return if detect_linux_vserver
247
+ return if detect_lxc_docker
248
+ return if detect_docker
249
+ return if detect_lxd
250
+ end
251
+ end
252
+ end