inspec 0.9.5 → 0.9.6

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 (110) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +58 -8
  3. data/README.md +8 -39
  4. data/Rakefile +74 -9
  5. data/bin/inspec +66 -10
  6. data/docs/ctl_inspec.rst +7 -1
  7. data/docs/inspec_and_friends.rst +1 -1
  8. data/docs/resources.rst +51 -45
  9. data/examples/README.md +7 -0
  10. data/examples/kitchen-ansible/.kitchen.yml +25 -0
  11. data/examples/kitchen-ansible/Gemfile +20 -0
  12. data/examples/kitchen-ansible/README.md +53 -0
  13. data/examples/kitchen-ansible/files/nginx.repo +6 -0
  14. data/examples/kitchen-ansible/tasks/main.yml +16 -0
  15. data/examples/kitchen-ansible/test/integration/default/default.yml +5 -0
  16. data/examples/{test-kitchen → kitchen-ansible}/test/integration/default/web_spec.rb +0 -0
  17. data/examples/{test-kitchen → kitchen-chef}/.kitchen.yml +1 -1
  18. data/examples/{test-kitchen → kitchen-chef}/Berksfile +0 -0
  19. data/examples/{test-kitchen → kitchen-chef}/Gemfile +1 -2
  20. data/examples/{test-kitchen → kitchen-chef}/README.md +1 -1
  21. data/examples/{test-kitchen → kitchen-chef}/metadata.rb +0 -0
  22. data/examples/{test-kitchen → kitchen-chef}/recipes/default.rb +0 -0
  23. data/examples/{test-kitchen → kitchen-chef}/recipes/nginx.rb +0 -0
  24. data/examples/kitchen-chef/test/integration/default/web_spec.rb +28 -0
  25. data/examples/kitchen-puppet/.kitchen.yml +22 -0
  26. data/examples/kitchen-puppet/Gemfile +21 -0
  27. data/examples/kitchen-puppet/Puppetfile +25 -0
  28. data/examples/kitchen-puppet/README.md +53 -0
  29. data/examples/kitchen-puppet/manifests/site.pp +33 -0
  30. data/examples/kitchen-puppet/metadata.json +11 -0
  31. data/examples/kitchen-puppet/test/integration/default/web_spec.rb +28 -0
  32. data/inspec.gemspec +2 -0
  33. data/lib/inspec/plugins/resource.rb +21 -0
  34. data/lib/inspec/shell.rb +73 -11
  35. data/lib/inspec/version.rb +1 -1
  36. data/lib/matchers/matchers.rb +43 -0
  37. data/lib/resources/apache_conf.rb +12 -9
  38. data/lib/resources/apt.rb +7 -0
  39. data/lib/resources/audit_policy.rb +6 -6
  40. data/lib/resources/auditd_conf.rb +6 -7
  41. data/lib/resources/auditd_rules.rb +9 -8
  42. data/lib/resources/bond.rb +6 -6
  43. data/lib/resources/bridge.rb +7 -0
  44. data/lib/resources/command.rb +10 -8
  45. data/lib/resources/csv.rb +6 -5
  46. data/lib/resources/directory.rb +6 -0
  47. data/lib/resources/etc_group.rb +9 -1
  48. data/lib/resources/file.rb +72 -61
  49. data/lib/resources/gem.rb +6 -4
  50. data/lib/resources/group.rb +7 -0
  51. data/lib/resources/host.rb +6 -0
  52. data/lib/resources/inetd_conf.rb +8 -8
  53. data/lib/resources/ini.rb +6 -6
  54. data/lib/resources/interface.rb +8 -8
  55. data/lib/resources/iptables.rb +6 -0
  56. data/lib/resources/json.rb +6 -5
  57. data/lib/resources/kernel_module.rb +6 -5
  58. data/lib/resources/kernel_parameter.rb +6 -4
  59. data/lib/resources/limits_conf.rb +6 -6
  60. data/lib/resources/login_def.rb +6 -0
  61. data/lib/resources/mysql_conf.rb +6 -0
  62. data/lib/resources/mysql_session.rb +7 -0
  63. data/lib/resources/npm.rb +6 -4
  64. data/lib/resources/ntp_conf.rb +7 -7
  65. data/lib/resources/oneget.rb +6 -0
  66. data/lib/resources/os.rb +8 -0
  67. data/lib/resources/os_env.rb +6 -0
  68. data/lib/resources/package.rb +8 -1
  69. data/lib/resources/parse_config.rb +14 -0
  70. data/lib/resources/passwd.rb +7 -0
  71. data/lib/resources/pip.rb +6 -0
  72. data/lib/resources/port.rb +22 -11
  73. data/lib/resources/postgres_conf.rb +6 -0
  74. data/lib/resources/postgres_session.rb +8 -0
  75. data/lib/resources/processes.rb +17 -1
  76. data/lib/resources/registry_key.rb +7 -0
  77. data/lib/resources/script.rb +11 -0
  78. data/lib/resources/security_policy.rb +6 -1
  79. data/lib/resources/service.rb +10 -0
  80. data/lib/resources/ssh_conf.rb +6 -0
  81. data/lib/resources/user.rb +9 -2
  82. data/lib/resources/windows_feature.rb +6 -0
  83. data/lib/resources/yaml.rb +6 -0
  84. data/lib/resources/yum.rb +7 -0
  85. data/lib/utils/find_files.rb +15 -7
  86. data/test/helper.rb +9 -0
  87. data/test/integration/.kitchen.yml +3 -0
  88. data/test/integration/test/integration/default/compare_matcher_spec.rb +19 -0
  89. data/test/integration/test/integration/default/etc_group.rb +13 -0
  90. data/test/integration/test/integration/default/os_spec.rb +13 -0
  91. data/test/integration/test/integration/default/port_spec.rb +1 -1
  92. data/test/unit/mock/cmd/find-apache2-conf-enabled +1 -0
  93. data/test/unit/mock/cmd/find-apache2-ports-conf +1 -0
  94. data/test/unit/mock/cmd/ps-aux +2 -0
  95. data/test/unit/mock/files/apache2.conf +14 -0
  96. data/test/unit/mock/files/ports.conf +6 -0
  97. data/test/unit/mock/files/serve-cgi-bin.conf +20 -0
  98. data/test/unit/resources/apache_conf_test.rb +31 -0
  99. data/test/unit/resources/file_test.rb +181 -0
  100. data/test/unit/resources/package_test.rb +9 -0
  101. data/test/unit/resources/port_test.rb +33 -13
  102. data/test/unit/resources/processes_test.rb +6 -0
  103. data/test/unit/resources/service_test.rb +10 -0
  104. data/test/unit/resources/user_test.rb +12 -0
  105. data/test/unit/utils/find_files_test.rb +23 -0
  106. metadata +61 -16
  107. data/bin/inspec.orig +0 -115
  108. data/lib/resources/.service.rb.swp +0 -0
  109. data/test/unit/mock/profiles/rules/metadata.rb +0 -2
  110. data/test/unit/mock/profiles/rules/test/test.rb +0 -6
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 3fc1943a4f7b887acce7a49336b5d32aef1e4847
4
- data.tar.gz: 88da833cba32da598a683bd1fff826caf2809af2
3
+ metadata.gz: 2a0409ea39853cce8b89f828d6c639c48c0adfe4
4
+ data.tar.gz: a424f575ac78ec70775f6d84d577330f278be8fc
5
5
  SHA512:
6
- metadata.gz: c2d297e8107586f5657e7fb77e4973153e1beb9f1ad2d5f31db4135cb56006a5b8e311edc4d6a2e7f4cfbdb37db3bb26cb4337e550d5d9e3b5be8ffbc845a386
7
- data.tar.gz: 3943ace22dbed7065268d871c5dfd5b4e46048d3c33474a2938e6e65619db190ded570559f3b1256a9c5fdc998dfea8fc841b8796e5f3665178f144fd0cca988
6
+ metadata.gz: 4be07873774b1a7b9bb11160c9078d004808aaad09be4c91841cc5af5e4a896d0d3c5f6c83d184fadd88048e26c4611ff26e688bc499149e32b91c66fca27071
7
+ data.tar.gz: a11ee4ab19c53b5c7f8e3a8d30a1047655ffe62d562a8874818bb29050005e7cb917c7e7d93fd8e396535147530aae450ce24f4f31c36f5c7415c029362c9d83
@@ -1,15 +1,65 @@
1
1
  # Change Log
2
2
 
3
- ## [0.9.5](https://github.com/chef/inspec/tree/0.9.5) (2015-11-25)
4
- [Full Changelog](https://github.com/chef/inspec/compare/v0.9.4...0.9.5)
3
+ ## [0.9.6](https://github.com/chef/inspec/tree/0.9.6) (2015-12-11)
4
+ [Full Changelog](https://github.com/chef/inspec/compare/v0.9.5...0.9.6)
5
5
 
6
6
  **Implemented enhancements:**
7
7
 
8
- - Support the -i switch for key files as per ssh? [\#261](https://github.com/chef/inspec/issues/261)
8
+ - JSON configuration [\#292](https://github.com/chef/inspec/issues/292)
9
+ - Replace the `pry... ` bits in inspec shell [\#267](https://github.com/chef/inspec/issues/267)
10
+ - Better wording for check [\#260](https://github.com/chef/inspec/issues/260)
11
+ - OS resource with string and symbol support [\#227](https://github.com/chef/inspec/issues/227)
12
+ - matcher for less-restrictive comparison [\#318](https://github.com/chef/inspec/pull/318) ([chris-rock](https://github.com/chris-rock))
13
+ - add readme to examples [\#313](https://github.com/chef/inspec/pull/313) ([chris-rock](https://github.com/chris-rock))
14
+ - Minor `inspec shell` improvements [\#283](https://github.com/chef/inspec/pull/283) ([srenatus](https://github.com/srenatus))
15
+ - add kitchen-ansible inspec example [\#275](https://github.com/chef/inspec/pull/275) ([alexpop](https://github.com/alexpop))
16
+ - add kitchen-puppet example with inspec testing [\#273](https://github.com/chef/inspec/pull/273) ([alexpop](https://github.com/alexpop))
17
+ - Feature: Add shell `help resource` command [\#269](https://github.com/chef/inspec/pull/269) ([chris-rock](https://github.com/chris-rock))
18
+
19
+ **Fixed bugs:**
20
+
21
+ - auditd\_conf parameters should be case insensitive [\#307](https://github.com/chef/inspec/issues/307)
22
+ - Processes resource doesn't handle user or state [\#295](https://github.com/chef/inspec/issues/295)
23
+ - JSON configuration [\#292](https://github.com/chef/inspec/issues/292)
24
+ - Windows file matcher does not match existing files [\#288](https://github.com/chef/inspec/issues/288)
25
+ - Inspec hangs when executing some windows profiles against linux machine [\#279](https://github.com/chef/inspec/issues/279)
26
+ - Utils::FindFiles doesn't work [\#276](https://github.com/chef/inspec/issues/276)
27
+ - etc\_group not implemented for centos [\#266](https://github.com/chef/inspec/issues/266)
28
+ - Port resource returns arrays [\#256](https://github.com/chef/inspec/issues/256)
29
+ - Custom resource not available, undefined local variable or method `gordon\_config` [\#232](https://github.com/chef/inspec/issues/232)
30
+ - File permission checks should return false unless file exists [\#301](https://github.com/chef/inspec/pull/301) ([adamleff](https://github.com/adamleff))
31
+ - remove json doc for windows\_feature [\#272](https://github.com/chef/inspec/pull/272) ([chris-rock](https://github.com/chris-rock))
32
+ - improvement: add etc\_group support for centos and add integration test [\#270](https://github.com/chef/inspec/pull/270) ([chris-rock](https://github.com/chris-rock))
33
+
34
+ **Merged pull requests:**
35
+
36
+ - Bugfix: Properly initialize script resource [\#316](https://github.com/chef/inspec/pull/316) ([chris-rock](https://github.com/chris-rock))
37
+ - improve shell prompt and help [\#315](https://github.com/chef/inspec/pull/315) ([chris-rock](https://github.com/chris-rock))
38
+ - port resource: array attributes, resource alternative [\#303](https://github.com/chef/inspec/pull/303) ([srenatus](https://github.com/srenatus))
39
+ - support string and symbol for os resource [\#299](https://github.com/chef/inspec/pull/299) ([chris-rock](https://github.com/chris-rock))
40
+ - \[resources/apache\_conf\]: add tests, fix bug [\#298](https://github.com/chef/inspec/pull/298) ([srenatus](https://github.com/srenatus))
41
+ - \[resources/processes\] add user\(s\), state\(s\) attribute [\#297](https://github.com/chef/inspec/pull/297) ([srenatus](https://github.com/srenatus))
42
+ - fix small grammar error [\#294](https://github.com/chef/inspec/pull/294) ([juliandunn](https://github.com/juliandunn))
43
+ - read config from file/stdin [\#293](https://github.com/chef/inspec/pull/293) ([srenatus](https://github.com/srenatus))
44
+ - revert to old find\_files interface [\#291](https://github.com/chef/inspec/pull/291) ([srenatus](https://github.com/srenatus))
45
+ - Adding support for Wind River Linux [\#289](https://github.com/chef/inspec/pull/289) ([adamleff](https://github.com/adamleff))
46
+ - travis workarounds [\#286](https://github.com/chef/inspec/pull/286) ([srenatus](https://github.com/srenatus))
47
+ - Support mint in the integration tests [\#281](https://github.com/chef/inspec/pull/281) ([artem-sidorenko](https://github.com/artem-sidorenko))
48
+ - align cli documentation with cli [\#278](https://github.com/chef/inspec/pull/278) ([chris-rock](https://github.com/chris-rock))
49
+ - Remove description of custom resource [\#277](https://github.com/chef/inspec/pull/277) ([chris-rock](https://github.com/chris-rock))
50
+ - add rake tasks for showing and bumping the version of inspec [\#265](https://github.com/chef/inspec/pull/265) ([arlimus](https://github.com/arlimus))
51
+
52
+ ## [v0.9.5](https://github.com/chef/inspec/tree/v0.9.5) (2015-11-25)
53
+ [Full Changelog](https://github.com/chef/inspec/compare/v0.9.4...v0.9.5)
54
+
55
+ **Implemented enhancements:**
56
+
57
+ - Support the -i switch for key files as per ssh [\#261](https://github.com/chef/inspec/issues/261)
9
58
  - Add -p alias for --port like ssh [\#263](https://github.com/chef/inspec/pull/263) ([alexmanly](https://github.com/alexmanly))
10
59
 
11
60
  **Merged pull requests:**
12
61
 
62
+ - 0.9.5 [\#264](https://github.com/chef/inspec/pull/264) ([arlimus](https://github.com/arlimus))
13
63
  - Add -i alias for --key\_files like ssh [\#262](https://github.com/chef/inspec/pull/262) ([jcreedcmu](https://github.com/jcreedcmu))
14
64
 
15
65
  ## [v0.9.4](https://github.com/chef/inspec/tree/v0.9.4) (2015-11-24)
@@ -19,13 +69,10 @@
19
69
 
20
70
  - registry\_key needs to be case insensitive [\#254](https://github.com/chef/inspec/issues/254)
21
71
  - User resource doesn't handle group names with spaces [\#238](https://github.com/chef/inspec/issues/238)
72
+ - inspec does not extract section name from test file header [\#182](https://github.com/chef/inspec/issues/182)
22
73
  - bugfix: user resources support for group with whitespace [\#258](https://github.com/chef/inspec/pull/258) ([chris-rock](https://github.com/chris-rock))
23
74
  - Bugfix: make registry\_key resource case-insensitive [\#255](https://github.com/chef/inspec/pull/255) ([alexpop](https://github.com/alexpop))
24
75
 
25
- **Closed issues:**
26
-
27
- - inspec does not extract section name from test file header [\#182](https://github.com/chef/inspec/issues/182)
28
-
29
76
  **Merged pull requests:**
30
77
 
31
78
  - 0.9.4 [\#259](https://github.com/chef/inspec/pull/259) ([arlimus](https://github.com/arlimus))
@@ -39,9 +86,12 @@
39
86
 
40
87
  - Support the control keyword, synonymous to rule [\#188](https://github.com/chef/inspec/issues/188)
41
88
 
42
- **Closed issues:**
89
+ **Fixed bugs:**
43
90
 
44
91
  - Multiple computed calls to describe aren't registered [\#246](https://github.com/chef/inspec/issues/246)
92
+
93
+ **Closed issues:**
94
+
45
95
  - port resource does not work on CentOS [\#239](https://github.com/chef/inspec/issues/239)
46
96
  - os\_env not working [\#236](https://github.com/chef/inspec/issues/236)
47
97
  - service resource misbehaves on upstart hosts [\#226](https://github.com/chef/inspec/issues/226)
data/README.md CHANGED
@@ -1,6 +1,6 @@
1
1
  # InSpec: Inspect Your Infrastructure
2
2
 
3
- InSpec is open-source testing framework for infrastructure with a human- and machine-readable language for specifying compliance, security and policy requirements.
3
+ InSpec is an open-source testing framework for infrastructure with a human- and machine-readable language for specifying compliance, security and policy requirements.
4
4
 
5
5
  ```ruby
6
6
  # Disallow insecure protocols by testing
@@ -92,7 +92,7 @@ end
92
92
 
93
93
  describe port(443) do
94
94
    it { should be_listening }
95
-   its('protocol') {should eq 'tcp'}
95
+   its('protocols') {should include 'tcp'}
96
96
  end
97
97
  ```
98
98
 
@@ -152,43 +152,6 @@ Which will provide you with:
152
152
  {"family":"ubuntu","release":"14.04","arch":null}
153
153
  ```
154
154
 
155
- ## Custom InSpec resources
156
-
157
- You can easily create your own resources. Here is a custom resource for an
158
- application called Gordon. It is saved as `gordon_config.rb`.
159
-
160
- ```ruby
161
- require 'yaml'
162
-
163
- class GordonConfig < Inspec.resource(1)
164
- name 'gordon_config'
165
-
166
- def initialize
167
- @path = '/etc/gordon/config.yaml'
168
- @config = inspec.file(@path).content
169
- @params = YAML.load(@config)
170
- end
171
-
172
- def method_missing(name)
173
- @params[name.to_s]
174
- end
175
- end
176
- ```
177
-
178
- Include this file in your `test.rb`:
179
-
180
- ```ruby
181
- require_relative 'gordon_config'
182
- ```
183
-
184
- Now you can start using your new resource:
185
-
186
- ```ruby
187
- describe gordon_config do
188
- its('Version') { should eq('1.0') }
189
- end
190
- ```
191
-
192
155
  ## Documentation
193
156
 
194
157
  Documentation is available: https://github.com/chef/inspec/tree/master/docs
@@ -221,6 +184,12 @@ We perform `unit`, `resource` and `integration` tests.
221
184
  bundle exec rake test
222
185
  ```
223
186
 
187
+ If you like to run only one test, use
188
+
189
+ ```bash
190
+ bundle exec ruby -W -Ilib:test test/unit/resources/user_test.rb
191
+ ```
192
+
224
193
  ### Resource tests
225
194
 
226
195
  Resource tests make sure the backend execution layer behaves as expected. These tests will take a while, as a lot of different operating systems and configurations are being tested.
data/Rakefile CHANGED
@@ -48,14 +48,79 @@ namespace :test do
48
48
  end
49
49
  end
50
50
 
51
- # Automatically generate a changelog for this project. Only loaded if
52
- # the necessary gem is installed.
53
- begin
54
- require 'github_changelog_generator/task'
55
- require_relative 'lib/inspec/version'
56
- GitHubChangelogGenerator::RakeTask.new :changelog do |config|
57
- config.since_tag = '0.7.0'
58
- config.future_release = Inspec::VERSION
51
+ # Print the current version of this gem or update it.
52
+ #
53
+ # @param [Type] target the new version you want to set, or nil if you only want to show
54
+ def inspec_version(target = nil)
55
+ path = 'lib/inspec/version.rb'
56
+ require_relative path.sub(/.rb$/, '')
57
+
58
+ nu_version = target.nil? ? '' : " -> #{target}"
59
+ puts "Inspec: #{Inspec::VERSION}#{nu_version}"
60
+
61
+ unless target.nil?
62
+ raw = File.read(path)
63
+ nu = raw.sub(/VERSION.*/, "VERSION = '#{target}'")
64
+ File.write(path, nu)
65
+ load(path)
59
66
  end
60
- rescue LoadError
67
+ end
68
+
69
+ # Check if a command is available
70
+ #
71
+ # @param [Type] x the command you are interested in
72
+ # @param [Type] msg the message to display if the command is missing
73
+ def require_command(x, msg = nil)
74
+ return if system("command -v #{x} || exit 1")
75
+ msg ||= 'Please install it first!'
76
+ puts "\033[31;1mCan't find command #{x.inspect}. #{msg}\033[0m"
77
+ exit 1
78
+ end
79
+
80
+ # Check if a required environment variable has been set
81
+ #
82
+ # @param [String] x the variable you are interested in
83
+ # @param [String] msg the message you want to display if the variable is missing
84
+ def require_env(x, msg = nil)
85
+ exists = `env | grep "^#{x}="`
86
+ return unless exists.empty?
87
+ puts "\033[31;1mCan't find environment variable #{x.inspect}. #{msg}\033[0m"
88
+ exit 1
89
+ end
90
+
91
+ # Check the requirements for running an update of this repository.
92
+ def check_update_requirements
93
+ require_command 'git'
94
+ require_command 'github_changelog_generator', "\n"\
95
+ "For more information on how to install it see:\n"\
96
+ " https://github.com/skywinder/github-changelog-generator\n"
97
+ require_env 'CHANGELOG_GITHUB_TOKEN', "\n"\
98
+ "Please configure this token to make sure you can run all commands\n"\
99
+ "against GitHub.\n\n"\
100
+ "See github_changelog_generator homepage for more information:\n"\
101
+ " https://github.com/skywinder/github-changelog-generator\n"
102
+ end
103
+
104
+ # Show the current version of this gem.
105
+ desc 'Show the version of this gem'
106
+ task :version do
107
+ inspec_version
108
+ end
109
+
110
+ desc 'Generate the changelog'
111
+ task :changelog do
112
+ require_relative 'lib/inspec/version'
113
+ system "github_changelog_generator -u chef -p inspec --future-release #{Inspec::VERSION} --since-tag 0.7.0"
114
+ end
115
+
116
+ # Update the version of this gem and create an updated
117
+ # changelog. It covers everything short of actually releasing
118
+ # the gem.
119
+ desc 'Bump the version of this gem'
120
+ task :bump_version, [:version] do |_, args|
121
+ v = args[:version] || ENV['to']
122
+ fail "You must specify a target version! rake release[1.2.3]" if v.empty?
123
+ check_update_requirements
124
+ inspec_version(v)
125
+ Rake::Task['changelog'].invoke
61
126
  end
data/bin/inspec CHANGED
@@ -6,9 +6,13 @@
6
6
 
7
7
  require 'thor'
8
8
  require 'json'
9
+ require 'pp'
9
10
  require_relative '../lib/inspec'
10
11
 
11
- class InspecCLI < Thor
12
+ class InspecCLI < Thor # rubocop:disable Metrics/ClassLength
13
+ class_option :diagnose, type: :boolean,
14
+ desc: 'Show diagnostics (versions, configurations)'
15
+
12
16
  def self.target_options
13
17
  option :target, aliases: :t, type: :string, default: nil,
14
18
  desc: 'Simple targeting option using URIs, e.g. ssh://user:pass@host:port'
@@ -36,16 +40,20 @@ class InspecCLI < Thor
36
40
  desc: 'Use SSL for transport layer encryption (WinRM).'
37
41
  option :self_signed, type: :boolean, default: false,
38
42
  desc: 'Allow remote scans with self-signed certificates (WinRM).'
43
+ option :json_config, type: :string,
44
+ desc: 'Read configuration from JSON file (`-` reads from stdin).'
39
45
  end
40
46
 
41
- desc 'json PATH', 'read all tests in PATH and generate a JSON profile'
47
+ desc 'json PATH', 'read all tests in PATH and generate a JSON summary'
42
48
  option :id, type: :string,
43
49
  desc: 'Attach a profile ID to all test results'
44
50
  option :output, aliases: :o, type: :string,
45
51
  desc: 'Save the created profile to a path'
46
52
  def json(path)
47
- profile = Inspec::Profile.from_path(path, options)
48
- dst = options[:output].to_s
53
+ diagnose
54
+
55
+ profile = Inspec::Profile.from_path(path, opts)
56
+ dst = opts[:output].to_s
49
57
  if dst.empty?
50
58
  puts JSON.pretty_generate(profile.info)
51
59
  else
@@ -59,21 +67,25 @@ class InspecCLI < Thor
59
67
  end
60
68
  end
61
69
 
62
- desc 'check PATH', 'verify test structure in PATH'
70
+ desc 'check PATH', 'verify all tests at the specified PATH'
63
71
  def check(path)
64
- o = options.dup
72
+ diagnose
73
+
74
+ o = opts.dup
65
75
  o[:logger] = Logger.new(STDOUT)
66
76
  profile = Inspec::Profile.from_path(path, o)
67
77
  exit 1 unless profile.check
68
78
  end
69
79
 
70
- desc 'exec PATHS', 'run all test files'
80
+ desc 'exec PATHS', 'run all test files at the specified PATH.'
71
81
  option :id, type: :string,
72
82
  desc: 'Attach a profile ID to all test results'
73
83
  target_options
74
84
  option :format, type: :string, default: 'progress'
75
85
  def exec(*tests)
76
- runner = Inspec::Runner.new(options)
86
+ diagnose
87
+
88
+ runner = Inspec::Runner.new(opts)
77
89
  runner.add_tests(tests)
78
90
  runner.run
79
91
  rescue RuntimeError => e
@@ -83,7 +95,9 @@ class InspecCLI < Thor
83
95
  desc 'detect', 'detect the target OS'
84
96
  target_options
85
97
  def detect
86
- runner = Inspec::Runner.new(options)
98
+ diagnose
99
+
100
+ runner = Inspec::Runner.new(opts)
87
101
  rel = File.join(File.dirname(__FILE__), *%w{.. lib utils detect.rb})
88
102
  detect_util = File.expand_path(rel)
89
103
  runner.add_tests([detect_util])
@@ -94,8 +108,11 @@ class InspecCLI < Thor
94
108
 
95
109
  desc 'shell', 'open an interactive debugging shell'
96
110
  target_options
111
+ option :format, type: :string, default: Inspec::NoSummaryFormatter, hide: true
97
112
  def shell_func
98
- runner = Inspec::Runner.new(options)
113
+ diagnose
114
+
115
+ runner = Inspec::Runner.new(opts)
99
116
  Inspec::Shell.new(runner).start
100
117
  rescue RuntimeError => e
101
118
  puts e.message
@@ -105,5 +122,44 @@ class InspecCLI < Thor
105
122
  def version
106
123
  puts Inspec::VERSION
107
124
  end
125
+
126
+ private
127
+
128
+ def diagnose
129
+ return unless opts['diagnose']
130
+ puts "InSpec version: #{Inspec::VERSION}"
131
+ puts "Train version: #{Train::VERSION}"
132
+ puts 'Command line configuration:'
133
+ pp options
134
+ puts 'JSON configuration file:'
135
+ pp options_json
136
+ puts 'Merged configuration:'
137
+ pp opts
138
+ puts
139
+ end
140
+
141
+ def opts
142
+ # argv overrides json
143
+ Thor::CoreExt::HashWithIndifferentAccess.new(options_json.merge(options))
144
+ end
145
+
146
+ def options_json
147
+ conffile = options['json_config']
148
+ @json ||= conffile ? read_config(conffile) : {}
149
+ end
150
+
151
+ def read_config(file)
152
+ if file == '-'
153
+ puts 'WARN: reading JSON config from standard input' if STDIN.tty?
154
+ config = STDIN.read
155
+ else
156
+ config = File.read(file)
157
+ end
158
+
159
+ JSON.load(config)
160
+ rescue JSON::ParserError => e
161
+ puts "Failed to load JSON configuration: #{e}\nConfig was: #{config.inspect}"
162
+ exit 1
163
+ end
108
164
  end
109
165
  InspecCLI.start(ARGV)
@@ -47,11 +47,17 @@ The following options may be used with any of the InSpec CLI subcommands:
47
47
  ``--user``
48
48
  The login user for remote scanning.
49
49
 
50
+ ``--json_config``
51
+ A JSON file containing configuration options. Use `--json_config=-` to read from standard input. The file's format corresponds to the command line argument options. For example, `{"host": "example.com", "sudo": true}` is equivalent to `--host=example.com --sudo`. Command line switches override the configuration file.
52
+
53
+ ``--diagnose``
54
+ Dump configuration values from a command line options, the configuration file, and the merged effective options.
55
+
50
56
 
51
57
 
52
58
  check
53
59
  =====================================================
54
- Use ``inspec check`` to run all tests at the specified path.
60
+ Use ``inspec check`` to verify all tests the specified path.
55
61
 
56
62
  Syntax
57
63
  -----------------------------------------------------
@@ -64,7 +64,7 @@ One of the key differences is that InSpec targets more user groups. It is optimi
64
64
  insecure SSHv1 connections anymore.
65
65
  "
66
66
  describe sshd_config do
67
- its('Protocol') { should eq('2') }
67
+ its('Protocol') { should cmp 2 }
68
68
  end
69
69
  end
70
70
 
@@ -258,7 +258,7 @@ A ``auditd_conf`` |inspec resource| block declares configuration settings that s
258
258
  .. code-block:: ruby
259
259
 
260
260
  describe auditd_conf('path') do
261
- its('keyword') { should eq 'value' }
261
+ its('keyword') { should cmp 'value' }
262
262
  end
263
263
 
264
264
  where
@@ -269,11 +269,12 @@ where
269
269
 
270
270
  Matchers
271
271
  -----------------------------------------------------
272
- This |inspec resource| matches any keyword that is listed in the ``auditd.conf`` configuration file:
272
+ This |inspec resource| matches any keyword that is listed in the ``auditd.conf`` configuration file. Since all option names and values are case insensitive for ``auditd_conf``, we recommend to compare values with `cmp` instead of the `eq`:
273
273
 
274
274
  .. code-block:: ruby
275
275
 
276
- its('log_format') { should eq 'raw' }
276
+ its('log_format') { should cmp 'raw' }
277
+ its('max_log_file') { should cmp 6 }
277
278
 
278
279
  Examples
279
280
  -----------------------------------------------------
@@ -284,20 +285,20 @@ The following examples show how to use this InSpec audit resource.
284
285
  .. code-block:: ruby
285
286
 
286
287
  describe auditd_conf do
287
- its('log_file') { should eq '/full/path/to/file' }
288
- its('log_format') { should eq 'raw' }
289
- its('flush') { should eq 'none' }
290
- its('freq') { should eq '1' }
291
- its('num_logs') { should eq '0' }
292
- its('max_log_file') { should eq '6' }
293
- its('max_log_file_action') { should eq 'email' }
294
- its('space_left') { should eq '2' }
295
- its('action_mail_acct') { should eq 'root' }
296
- its('space_left_action') { should eq 'email' }
297
- its('admin_space_left') { should eq '1' }
298
- its('admin_space_left_action') { should eq 'halt' }
299
- its('disk_full_action') { should eq 'halt' }
300
- its('disk_error_action') { should eq 'halt' }
288
+ its('log_file') { should cmp '/full/path/to/file' }
289
+ its('log_format') { should cmp 'raw' }
290
+ its('flush') { should cmp 'none' }
291
+ its('freq') { should cmp 1 }
292
+ its('num_logs') { should cmp 0 }
293
+ its('max_log_file') { should cmp 6 }
294
+ its('max_log_file_action') { should cmp 'email' }
295
+ its('space_left') { should cmp 2 }
296
+ its('action_mail_acct') { should cmp 'root' }
297
+ its('space_left_action') { should cmp 'email' }
298
+ its('admin_space_left') { should cmp 1 }
299
+ its('admin_space_left_action') { should cmp 'halt' }
300
+ its('disk_full_action') { should cmp 'halt' }
301
+ its('disk_error_action') { should cmp 'halt' }
301
302
  end
302
303
 
303
304
 
@@ -3176,10 +3177,10 @@ A ``port`` |inspec resource| block declares a port, and then depending on what n
3176
3177
 
3177
3178
  describe port(514) do
3178
3179
  it { should be_listening }
3179
- its('process') {should eq 'syslog'}
3180
+ its('processes') {should include 'syslog'}
3180
3181
  end
3181
3182
 
3182
- where the ``process`` returns the process listening on port 514.
3183
+ where the ``processes`` returns the processes listening on port 514.
3183
3184
 
3184
3185
  Matchers
3185
3186
  -----------------------------------------------------
@@ -3195,33 +3196,33 @@ The ``be_listening`` matcher tests if the port is listening for traffic:
3195
3196
 
3196
3197
  pid
3197
3198
  +++++++++++++++++++++++++++++++++++++++++++++++++++++
3198
- The ``pid`` matcher tests the process identifier (PID):
3199
+ The ``pids`` matcher tests the process identifier (PID):
3199
3200
 
3200
3201
  .. code-block:: ruby
3201
3202
 
3202
- its('pid') { should eq '27808' }
3203
+ its('pids') { should eq ['27808'] }
3203
3204
 
3204
3205
  process
3205
3206
  +++++++++++++++++++++++++++++++++++++++++++++++++++++
3206
- The ``process`` matcher tests if the named process is running on the system:
3207
+ The ``processes`` matcher tests if the named process is running on the system:
3207
3208
 
3208
3209
  .. code-block:: ruby
3209
3210
 
3210
- its('process') { should eq 'syslog' }
3211
+ its('processes') { should eq ['syslog'] }
3211
3212
 
3212
3213
  protocol
3213
3214
  +++++++++++++++++++++++++++++++++++++++++++++++++++++
3214
- The ``protocol`` matcher tests the Internet protocol: |icmp| (``'icmp'``), |tcp| (``'tcp'`` or ``'tcp6'``), or |udp| (``'udp'`` or ``'udp6'``):
3215
+ The ``protocols`` matcher tests the Internet protocol: |icmp| (``'icmp'``), |tcp| (``'tcp'`` or ``'tcp6'``), or |udp| (``'udp'`` or ``'udp6'``):
3215
3216
 
3216
3217
  .. code-block:: ruby
3217
3218
 
3218
- its('protocol') { should eq 'tcp' }
3219
+ its('protocols') { should eq ['tcp'] }
3219
3220
 
3220
3221
  or for the |ipv6| protocol:
3221
3222
 
3222
3223
  .. code-block:: ruby
3223
3224
 
3224
- its('protocol') { should eq 'tcp6' }
3225
+ its('protocols') { should eq ['tcp6'] }
3225
3226
 
3226
3227
  Examples
3227
3228
  -----------------------------------------------------
@@ -3233,7 +3234,7 @@ The following examples show how to use this InSpec audit resource.
3233
3234
 
3234
3235
  describe port(80) do
3235
3236
  it { should be_listening }
3236
- its('protocol') {should eq 'tcp'}
3237
+ its('protocols') {should eq ['tcp']}
3237
3238
  end
3238
3239
 
3239
3240
  **Test port 80, listening with TCP version IPv6 protocol**
@@ -3242,7 +3243,7 @@ The following examples show how to use this InSpec audit resource.
3242
3243
 
3243
3244
  describe port(80) do
3244
3245
  it { should be_listening }
3245
- its('protocol') {should eq 'tcp6'}
3246
+ its('protocols') {should eq ['tcp6']}
3246
3247
  end
3247
3248
 
3248
3249
  **Test ports for HTTPs**
@@ -3255,7 +3256,22 @@ The following examples show how to use this InSpec audit resource.
3255
3256
 
3256
3257
  describe port(443) do
3257
3258
  it { should be_listening }
3258
- its('protocol') {should eq 'tcp'}
3259
+ its('protocols') {should eq ['tcp']}
3260
+ end
3261
+
3262
+ **Test port 80 on a specific address**
3263
+
3264
+ This check can be implemented in two equivalent ways:
3265
+
3266
+ .. code-block:: ruby
3267
+
3268
+ describe port(80) do
3269
+ it { should be_listening }
3270
+ its('addresses') {should include '0.0.0.0'}
3271
+ end
3272
+
3273
+ describe port('0.0.0.0', 80) do
3274
+ it { should be_listening }
3259
3275
  end
3260
3276
 
3261
3277
  postgres_conf
@@ -3424,7 +3440,7 @@ A ``processes`` |inspec resource| block declares the name of the process to be t
3424
3440
  where
3425
3441
 
3426
3442
  * ``processes('process_name')`` must specify the name of a process that is running on the system
3427
- * Multiple properties may be tested; for each property to be tested, use an ``its('property_name')`` statement
3443
+ * The ``user`` and ``state`` properties may be tested; they are exposed via ``users`` and ``states``, respectively.
3428
3444
 
3429
3445
  Matchers
3430
3446
  -----------------------------------------------------
@@ -3466,7 +3482,7 @@ The following examples show how to use this InSpec audit resource.
3466
3482
  .. code-block:: ruby
3467
3483
 
3468
3484
  describe processes('init') do
3469
- its('user') { should eq 'root' }
3485
+ its('users') { should eq ['root'] }
3470
3486
  end
3471
3487
 
3472
3488
  **Test if a high-priority process is running**
@@ -3474,7 +3490,7 @@ The following examples show how to use this InSpec audit resource.
3474
3490
  .. code-block:: ruby
3475
3491
 
3476
3492
  describe processes('some_process') do
3477
- its('state') { should eq 'R<' }
3493
+ its('states') { should eq ['R<'] }
3478
3494
  end
3479
3495
 
3480
3496
 
@@ -3895,7 +3911,7 @@ The following examples show how to use this InSpec audit resource.
3895
3911
  .. code-block:: ruby
3896
3912
 
3897
3913
  describe sshd_config do
3898
- its('Protocol') { should eq '2' }
3914
+ its('Protocol') { should cmp 2 }
3899
3915
  end
3900
3916
 
3901
3917
  **Test ciphers**
@@ -3911,7 +3927,7 @@ The following examples show how to use this InSpec audit resource.
3911
3927
  .. code-block:: ruby
3912
3928
 
3913
3929
  describe sshd_config do
3914
- its('Port') { should eq '22' }
3930
+ its('Port') { should cmp 22 }
3915
3931
  its('UsePAM') { should eq 'yes' }
3916
3932
  its('ListenAddress') { should eq nil }
3917
3933
  its('HostKey') { should eq [
@@ -4084,20 +4100,10 @@ The |nginx| user is typically ``www-data``, but on |centos| it's ``nginx``. The
4084
4100
 
4085
4101
  windows_feature
4086
4102
  =====================================================
4087
- Use the ``windows_feature`` |inspec resource| to test features on |windows|. The ``Get-WindowsFeature`` cmdlet returns the following values: ``Property Name``, ``DisplayName``, ``Description``, ``Installed``, and ``InstallState``, returned as a |json| object similar to:
4103
+ Use the ``windows_feature`` |inspec resource| to test features on |windows|. It uses the ``Get-WindowsFeature`` cmdlet under the hood.
4088
4104
 
4089
4105
  **Stability: Experimental**
4090
4106
 
4091
- .. code-block:: javascript
4092
-
4093
- {
4094
- "Name": "XPS-Viewer",
4095
- "DisplayName": "XPS Viewer",
4096
- "Description": "The XPS Viewer reads, sets permissions, and digitally signs XPS documents.",
4097
- "Installed": false,
4098
- "InstallState": 0
4099
- }
4100
-
4101
4107
  Syntax
4102
4108
  -----------------------------------------------------
4103
4109
  A ``windows_feature`` |inspec resource| block declares the name of the |windows| feature, tests if that feature is installed, and then returns information about that feature: