├── .github └── workflows │ └── codespell.yml ├── .gitignore ├── .kitchen.yml ├── .puppet-lint.rc ├── .rubocop.yml ├── .travis.yml ├── Gemfile ├── Guardfile ├── Modulefile ├── Puppetfile ├── README.md ├── Rakefile ├── Thorfile ├── manifests ├── init.pp ├── puppetlabs.pp └── puppetlabs_override.pp ├── metadata.json ├── renovate.json └── templates ├── hardening.conf.erb ├── httpd.conf.erb └── mod └── alias.conf.erb /.github/workflows/codespell.yml: -------------------------------------------------------------------------------- 1 | --- 2 | name: Codespell - Spellcheck 3 | 4 | on: # yamllint disable-line rule:truthy 5 | push: 6 | branches: [master] 7 | pull_request: 8 | branches: [master] 9 | 10 | jobs: 11 | codespell: 12 | uses: "dev-sec/.github/.github/workflows/codespell.yml@main" 13 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | exp.* 2 | .kitchen 3 | Berksfile.lock 4 | Puppetfile.lock 5 | .kitchen.local.yml 6 | shared_test_repo/ 7 | .librarian/ 8 | .tmp/ 9 | test/integration 10 | Gemfile.lock 11 | -------------------------------------------------------------------------------- /.kitchen.yml: -------------------------------------------------------------------------------- 1 | --- 2 | driver: 3 | name: vagrant 4 | provisioner: 5 | name: puppet_apply 6 | test_repo_uri: https://github.com/TelekomLabs/tests-apache-hardening.git 7 | platforms: 8 | - name: ubuntu-12.04 9 | driver_config: 10 | box: opscode-ubuntu-12.04 11 | box_url: http://opscode-vm-bento.s3.amazonaws.com/vagrant/virtualbox/opscode_ubuntu-12.04_chef-provisionerless.box 12 | - name: ubuntu-14.04 13 | driver_config: 14 | box: opscode-ubuntu-14.04 15 | box_url: http://opscode-vm-bento.s3.amazonaws.com/vagrant/virtualbox/opscode_ubuntu-14.04_chef-provisionerless.box 16 | - name: centos-6.4 17 | driver_config: 18 | box: opscode-centos-6.4 19 | box_url: https://opscode-vm.s3.amazonaws.com/vagrant/opscode_centos-6.4_provisionerless.box 20 | - name: centos-6.5 21 | driver_config: 22 | box: opscode-centos-6.5 23 | box_url: http://opscode-vm-bento.s3.amazonaws.com/vagrant/virtualbox/opscode_centos-6.5_chef-provisionerless.box 24 | - name: centos-7.1 25 | driver_config: 26 | box: opscode-centos-7.1 27 | box_url: http://opscode-vm-bento.s3.amazonaws.com/vagrant/virtualbox/opscode_centos-7.1_chef-provisionerless.box 28 | - name: oracle-6.4 29 | driver_config: 30 | box: oracle-6.4 31 | box_url: https://storage.us2.oraclecloud.com/v1/istoilis-istoilis/vagrant/oel64-64.box 32 | - name: oracle-6.5 33 | driver_config: 34 | box: oracle-6.5 35 | box_url: https://storage.us2.oraclecloud.com/v1/istoilis-istoilis/vagrant/oel65-64.box 36 | - name: debian-6 37 | driver_config: 38 | box: debian-6 39 | box_url: https://s3.eu-central-1.amazonaws.com/ffuenf-vagrantboxes/debian/debian-6.0.10-amd64_virtualbox.box 40 | - name: debian-7 41 | driver_config: 42 | box: debian-7 43 | box_url: https://s3.eu-central-1.amazonaws.com/ffuenf-vagrantboxes/debian/debian-7.7.0-amd64_virtualbox.box 44 | - name: debian-8 45 | driver_config: 46 | box: debian-8 47 | box_url: https://s3.eu-central-1.amazonaws.com/ffuenf-vagrantboxes/debian/debian-8.0.0-amd64_virtualbox.box 48 | suites: 49 | - name: default 50 | manifest: site.pp 51 | -------------------------------------------------------------------------------- /.puppet-lint.rc: -------------------------------------------------------------------------------- 1 | --no-autoloader_layout-check 2 | --no-80chars-check 3 | --no-inherits_across_namespaces-check -------------------------------------------------------------------------------- /.rubocop.yml: -------------------------------------------------------------------------------- 1 | AllCops: 2 | Exclude: 3 | # Ignore HTML related things 4 | - '**/*.erb' 5 | # Ignore vendored gems 6 | - 'vendor/**/*' 7 | # Ignore code from test fixtures 8 | - 'spec/fixtures/**/*' 9 | 10 | Lint/ConditionPosition: 11 | Enabled: true 12 | 13 | Lint/ElseLayout: 14 | Enabled: true 15 | 16 | Lint/UnreachableCode: 17 | Enabled: true 18 | 19 | Lint/UselessComparison: 20 | Enabled: true 21 | 22 | Lint/EnsureReturn: 23 | Enabled: true 24 | 25 | Lint/HandleExceptions: 26 | Enabled: true 27 | 28 | Lint/LiteralInCondition: 29 | Enabled: true 30 | 31 | Lint/ShadowingOuterLocalVariable: 32 | Enabled: true 33 | 34 | Lint/LiteralInInterpolation: 35 | Enabled: true 36 | 37 | Style/RedundantReturn: 38 | Enabled: true 39 | 40 | Lint/AmbiguousOperator: 41 | Enabled: true 42 | 43 | Lint/AssignmentInCondition: 44 | Enabled: true 45 | 46 | Style/SpaceBeforeComment: 47 | Enabled: true 48 | 49 | # DISABLED - not useful 50 | Style/HashSyntax: 51 | Enabled: false 52 | 53 | # USES: as shortcut for non nil&valid checking a = x() and a.empty? 54 | # DISABLED - not useful 55 | Style/AndOr: 56 | Enabled: false 57 | 58 | # DISABLED - not useful 59 | Style/RedundantSelf: 60 | Enabled: false 61 | 62 | # DISABLED - not useful 63 | Metrics/MethodLength: 64 | Enabled: false 65 | 66 | # DISABLED - not useful 67 | Style/WhileUntilModifier: 68 | Enabled: false 69 | 70 | # DISABLED - the offender is just haskell envy 71 | Lint/AmbiguousRegexpLiteral: 72 | Enabled: false 73 | 74 | # DISABLED 75 | Lint/Eval: 76 | Enabled: false 77 | 78 | # DISABLED 79 | Lint/BlockAlignment: 80 | Enabled: false 81 | 82 | # DISABLED 83 | Lint/DefEndAlignment: 84 | Enabled: false 85 | 86 | # DISABLED 87 | Lint/EndAlignment: 88 | Enabled: false 89 | 90 | # DISABLED 91 | Lint/DeprecatedClassMethods: 92 | Enabled: false 93 | 94 | # DISABLED 95 | Lint/Loop: 96 | Enabled: false 97 | 98 | # DISABLED 99 | Lint/ParenthesesAsGroupedExpression: 100 | Enabled: false 101 | 102 | Lint/RescueException: 103 | Enabled: false 104 | 105 | Lint/StringConversionInInterpolation: 106 | Enabled: false 107 | 108 | Lint/UnusedBlockArgument: 109 | Enabled: false 110 | 111 | Lint/UnusedMethodArgument: 112 | Enabled: false 113 | 114 | Lint/UselessAccessModifier: 115 | Enabled: true 116 | 117 | Lint/UselessAssignment: 118 | Enabled: true 119 | 120 | Lint/Void: 121 | Enabled: true 122 | 123 | Style/AccessModifierIndentation: 124 | Enabled: false 125 | 126 | Style/AccessorMethodName: 127 | Enabled: false 128 | 129 | Style/Alias: 130 | Enabled: false 131 | 132 | Style/AlignArray: 133 | Enabled: false 134 | 135 | Style/AlignHash: 136 | Enabled: false 137 | 138 | Style/AlignParameters: 139 | Enabled: false 140 | 141 | Metrics/BlockNesting: 142 | Enabled: false 143 | 144 | Style/AsciiComments: 145 | Enabled: false 146 | 147 | Style/Attr: 148 | Enabled: false 149 | 150 | Style/BracesAroundHashParameters: 151 | Enabled: false 152 | 153 | Style/CaseEquality: 154 | Enabled: false 155 | 156 | Style/CaseIndentation: 157 | Enabled: false 158 | 159 | Style/CharacterLiteral: 160 | Enabled: false 161 | 162 | Style/ClassAndModuleCamelCase: 163 | Enabled: false 164 | 165 | Style/ClassAndModuleChildren: 166 | Enabled: false 167 | 168 | Style/ClassCheck: 169 | Enabled: false 170 | 171 | Metrics/ClassLength: 172 | Enabled: false 173 | 174 | Style/ClassMethods: 175 | Enabled: false 176 | 177 | Style/ClassVars: 178 | Enabled: false 179 | 180 | Style/WhenThen: 181 | Enabled: false 182 | 183 | # DISABLED - not useful 184 | Style/WordArray: 185 | Enabled: false 186 | 187 | Style/UnneededPercentQ: 188 | Enabled: false 189 | 190 | Style/Tab: 191 | Enabled: false 192 | 193 | Style/SpaceBeforeSemicolon: 194 | Enabled: false 195 | 196 | Style/TrailingBlankLines: 197 | Enabled: false 198 | 199 | Style/SpaceInsideBlockBraces: 200 | Enabled: false 201 | 202 | Style/SpaceInsideBrackets: 203 | Enabled: false 204 | 205 | Style/SpaceInsideHashLiteralBraces: 206 | Enabled: false 207 | 208 | Style/SpaceInsideParens: 209 | Enabled: false 210 | 211 | Style/LeadingCommentSpace: 212 | Enabled: false 213 | 214 | Style/SingleSpaceBeforeFirstArg: 215 | Enabled: false 216 | 217 | Style/SpaceAfterColon: 218 | Enabled: false 219 | 220 | Style/SpaceAfterComma: 221 | Enabled: false 222 | 223 | Style/SpaceAfterControlKeyword: 224 | Enabled: false 225 | 226 | Style/SpaceAfterMethodName: 227 | Enabled: false 228 | 229 | Style/SpaceAfterNot: 230 | Enabled: false 231 | 232 | Style/SpaceAfterSemicolon: 233 | Enabled: false 234 | 235 | Style/SpaceAroundEqualsInParameterDefault: 236 | Enabled: false 237 | 238 | Style/SpaceAroundOperators: 239 | Enabled: false 240 | 241 | Style/SpaceBeforeBlockBraces: 242 | Enabled: false 243 | 244 | Style/SpaceBeforeComma: 245 | Enabled: false 246 | 247 | Style/CollectionMethods: 248 | Enabled: false 249 | 250 | Style/CommentIndentation: 251 | Enabled: false 252 | 253 | Style/ColonMethodCall: 254 | Enabled: false 255 | 256 | Style/CommentAnnotation: 257 | Enabled: false 258 | 259 | Metrics/CyclomaticComplexity: 260 | Enabled: false 261 | 262 | Style/ConstantName: 263 | Enabled: false 264 | 265 | Style/Documentation: 266 | Enabled: false 267 | 268 | Style/DefWithParentheses: 269 | Enabled: false 270 | 271 | Style/DeprecatedHashMethods: 272 | Enabled: false 273 | 274 | Style/DotPosition: 275 | Enabled: false 276 | 277 | # DISABLED - used for converting to bool 278 | Style/DoubleNegation: 279 | Enabled: false 280 | 281 | Style/EachWithObject: 282 | Enabled: false 283 | 284 | Style/EmptyLineBetweenDefs: 285 | Enabled: false 286 | 287 | Style/IndentArray: 288 | Enabled: false 289 | 290 | Style/IndentHash: 291 | Enabled: false 292 | 293 | Style/IndentationConsistency: 294 | Enabled: false 295 | 296 | Style/IndentationWidth: 297 | Enabled: false 298 | 299 | Style/EmptyLines: 300 | Enabled: false 301 | 302 | Style/EmptyLinesAroundAccessModifier: 303 | Enabled: false 304 | 305 | Style/EmptyLiteral: 306 | Enabled: false 307 | 308 | Metrics/LineLength: 309 | Enabled: false 310 | 311 | Style/MethodCallParentheses: 312 | Enabled: false 313 | 314 | Style/MethodDefParentheses: 315 | Enabled: false 316 | 317 | Style/LineEndConcatenation: 318 | Enabled: false 319 | 320 | Style/TrailingWhitespace: 321 | Enabled: false 322 | 323 | Style/StringLiterals: 324 | Enabled: false 325 | 326 | Style/TrailingComma: 327 | Enabled: false 328 | 329 | Style/GlobalVars: 330 | Enabled: false 331 | 332 | Style/GuardClause: 333 | Enabled: false 334 | 335 | Style/IfUnlessModifier: 336 | Enabled: false 337 | 338 | Style/MultilineIfThen: 339 | Enabled: false 340 | 341 | Style/NegatedIf: 342 | Enabled: false 343 | 344 | Style/NegatedWhile: 345 | Enabled: false 346 | 347 | Style/Next: 348 | Enabled: false 349 | 350 | Style/SingleLineBlockParams: 351 | Enabled: false 352 | 353 | Style/SingleLineMethods: 354 | Enabled: false 355 | 356 | Style/SpecialGlobalVars: 357 | Enabled: false 358 | 359 | Style/TrivialAccessors: 360 | Enabled: false 361 | 362 | Style/UnlessElse: 363 | Enabled: false 364 | 365 | Style/VariableInterpolation: 366 | Enabled: false 367 | 368 | Style/VariableName: 369 | Enabled: false 370 | 371 | Style/WhileUntilDo: 372 | Enabled: false 373 | 374 | Style/EvenOdd: 375 | Enabled: false 376 | 377 | Style/FileName: 378 | Enabled: false 379 | 380 | Style/For: 381 | Enabled: false 382 | 383 | Style/Lambda: 384 | Enabled: false 385 | 386 | Style/MethodName: 387 | Enabled: false 388 | 389 | Style/MultilineTernaryOperator: 390 | Enabled: false 391 | 392 | Style/NestedTernaryOperator: 393 | Enabled: false 394 | 395 | Style/NilComparison: 396 | Enabled: false 397 | 398 | Style/FormatString: 399 | Enabled: false 400 | 401 | Style/MultilineBlockChain: 402 | Enabled: false 403 | 404 | Style/Semicolon: 405 | Enabled: false 406 | 407 | Style/SignalException: 408 | Enabled: false 409 | 410 | Style/NonNilCheck: 411 | Enabled: false 412 | 413 | Style/Not: 414 | Enabled: false 415 | 416 | Style/NumericLiterals: 417 | Enabled: false 418 | 419 | Style/OneLineConditional: 420 | Enabled: false 421 | 422 | Style/OpMethod: 423 | Enabled: false 424 | 425 | Style/ParenthesesAroundCondition: 426 | Enabled: false 427 | 428 | Style/PercentLiteralDelimiters: 429 | Enabled: false 430 | 431 | Style/PerlBackrefs: 432 | Enabled: false 433 | 434 | Style/PredicateName: 435 | Enabled: false 436 | 437 | Style/RedundantException: 438 | Enabled: false 439 | 440 | Style/SelfAssignment: 441 | Enabled: false 442 | 443 | Style/Proc: 444 | Enabled: false 445 | 446 | Style/RaiseArgs: 447 | Enabled: false 448 | 449 | Style/RedundantBegin: 450 | Enabled: false 451 | 452 | Style/RescueModifier: 453 | Enabled: false 454 | 455 | Style/RegexpLiteral: 456 | Enabled: false 457 | 458 | Lint/UnderscorePrefixedVariableName: 459 | Enabled: false 460 | 461 | Metrics/ParameterLists: 462 | Enabled: false 463 | 464 | Lint/RequireParentheses: 465 | Enabled: false 466 | 467 | Lint/SpaceBeforeFirstArg: 468 | Enabled: false 469 | 470 | Style/ModuleFunction: 471 | Enabled: false 472 | 473 | Lint/Debugger: 474 | Enabled: false 475 | 476 | Style/IfWithSemicolon: 477 | Enabled: false 478 | 479 | Style/Encoding: 480 | Enabled: false 481 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | sudo: false 2 | language: ruby 3 | bundler_args: --without development integration openstack system_tests 4 | before_install: rm Gemfile.lock || true 5 | rvm: 6 | - 1.9.3 7 | - 2.0.0 8 | - 2.1.0 9 | script: bundle exec rake test 10 | env: 11 | - PUPPET_VERSION="~> 4.5.0" 12 | - PUPPET_VERSION="~> 4.4.0" 13 | - PUPPET_VERSION="~> 4.3.0" 14 | - PUPPET_VERSION="~> 4.2.0" 15 | - PUPPET_VERSION="~> 4.1.0" 16 | - PUPPET_VERSION="~> 4.0.0" 17 | - PUPPET_VERSION="~> 3.7.5" 18 | - PUPPET_VERSION="~> 3.6.2" 19 | - PUPPET_VERSION="~> 2.7.0" 20 | matrix: 21 | fast_finish: true 22 | exclude: 23 | - rvm: 1.9.3 24 | env: PUPPET_VERSION="~> 2.7.0" 25 | - rvm: 2.0.0 26 | env: PUPPET_VERSION="~> 2.7.0" 27 | - rvm: 2.1.0 28 | env: PUPPET_VERSION="~> 2.7.0" 29 | - rvm: 2.1.0 30 | env: PUPPET_VERSION="~> 3.2.0" 31 | - rvm: 2.1.0 32 | env: PUPPET_VERSION="~> 3.3.0" 33 | - rvm: 2.1.0 34 | env: PUPPET_VERSION="~> 3.4.0" 35 | -------------------------------------------------------------------------------- /Gemfile: -------------------------------------------------------------------------------- 1 | source ENV['GEM_SOURCE'] || 'https://rubygems.org' 2 | 3 | puppetversion = ENV['PUPPET_VERSION'] 4 | if puppetversion 5 | gem 'puppet', puppetversion, :require => false 6 | else 7 | gem 'puppet', :require => false 8 | end 9 | 10 | group :test do 11 | gem 'rake' 12 | gem 'rspec', '< 3.13.2' 13 | gem 'rspec-puppet', :git => 'https://github.com/rodjek/rspec-puppet.git' 14 | gem 'puppetlabs_spec_helper' 15 | gem 'metadata-json-lint' 16 | gem 'rspec-puppet-facts' 17 | gem 'rubocop', '1.75.8' 18 | gem 'puppet-lint' 19 | end 20 | 21 | group :development do 22 | gem 'travis' 23 | gem 'travis-lint' 24 | gem 'puppet-blacksmith' 25 | gem 'guard-rake' 26 | gem 'listen', '< 3.9.1' 27 | end 28 | 29 | group :integration do 30 | gem 'test-kitchen' 31 | gem 'kitchen-vagrant' 32 | gem 'kitchen-puppet' 33 | gem 'librarian-puppet' 34 | gem 'kitchen-sharedtests', '~> 0.2.0' 35 | end 36 | 37 | group :openstack do 38 | gem 'kitchen-openstack' 39 | end 40 | 41 | group :system_tests do 42 | gem 'beaker' 43 | gem 'beaker-rspec' 44 | gem 'beaker-puppet_install_helper' 45 | end 46 | -------------------------------------------------------------------------------- /Guardfile: -------------------------------------------------------------------------------- 1 | notification :off 2 | 3 | guard 'rake', :task => 'test' do 4 | watch(%r{^manifests\/(.+)\.pp$}) 5 | end 6 | -------------------------------------------------------------------------------- /Modulefile: -------------------------------------------------------------------------------- 1 | name 'hardening/apache_hardening' 2 | version '0.1.0' 3 | source 'https://github.com/TelekomLabs/puppet-apache-hardening' 4 | author 'Markus Schmall' 5 | license 'Apache License, Version 2.0' 6 | summary 'Configures Apache for security hardening' 7 | description 'Configures Apache for security hardening' 8 | project_page 'https://github.com/TelekomLabs/puppet-apache-hardening' 9 | 10 | dependency 'puppetlabs/apache' 11 | 12 | 13 | -------------------------------------------------------------------------------- /Puppetfile: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env ruby 2 | #^syntax detection 3 | 4 | forge "http://forge.puppetlabs.com" 5 | 6 | # use dependencies defined in Modulefile 7 | modulefile 8 | 9 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # apache_hardening (Puppet module) 2 | 3 | [![Puppet Forge](https://img.shields.io/puppetforge/dt/hardening/apache_hardening.svg)][1] 4 | [![Build Status](http://img.shields.io/travis/hardening-io/puppet-apache-hardening.svg)][2] 5 | [![Gitter Chat](https://badges.gitter.im/Join%20Chat.svg)][3] 6 | 7 | ## Description 8 | 9 | This module provides hardening configuration for Apache2 web server. 10 | 11 | ## Requirements 12 | 13 | * Puppet 14 | * Supported module: `puppetlabs/apache` 15 | 16 | 17 | ## Parameters 18 | 19 | none 20 | 21 | ## Usage 22 | 23 | Include the module 24 | 25 | ``` 26 | class { 'apache': 27 | default_mods => false, 28 | } 29 | 30 | class { 'apache_hardening': 31 | provider => 'puppetlabs/apache' 32 | } 33 | ``` 34 | 35 | ## Local Testing 36 | 37 | For local testing you can use vagrant and Virtualbox of VMWare to run tests locally. You will have to install Virtualbox and Vagrant on your system. See [Vagrant Downloads](http://downloads.vagrantup.com/) for a vagrant package suitable for your system. For all our tests we use `test-kitchen`. If you are not familiar with `test-kitchen` please have a look at [their guide](http://kitchen.ci/docs/getting-started). 38 | 39 | Next install test-kitchen: 40 | 41 | ```bash 42 | # Install dependencies 43 | gem install bundler 44 | bundle install 45 | 46 | # Fetch tests 47 | bundle exec thor kitchen:fetch-remote-tests 48 | 49 | # Do lint checks 50 | bundle exec rake lint 51 | 52 | # Do spec checks 53 | bundle exec rake lint 54 | 55 | # fast test on one machine 56 | bundle exec kitchen test default-ubuntu-1204 57 | 58 | # for development 59 | bundle exec kitchen create default-ubuntu-1204 60 | bundle exec kitchen converge default-ubuntu-1204 61 | ``` 62 | 63 | For more information see [test-kitchen](http://kitchen.ci/docs/getting-started) 64 | 65 | ## Contributors + Kudos 66 | 67 | * Edmund Haselwanter [ehaselwanter](https://github.com/ehaselwanter) 68 | 69 | ## License and Author 70 | 71 | * Author:: Markus Schmall 72 | * Author:: Deutsche Telekom AG 73 | 74 | Licensed under the Apache License, Version 2.0 (the "License"); 75 | you may not use this file except in compliance with the License. 76 | You may obtain a copy of the License at 77 | 78 | http://www.apache.org/licenses/LICENSE-2.0 79 | 80 | Unless required by applicable law or agreed to in writing, software 81 | distributed under the License is distributed on an "AS IS" BASIS, 82 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 83 | See the License for the specific language governing permissions and 84 | limitations under the License. 85 | 86 | [1]: https://forge.puppetlabs.com/hardening/apache_hardening 87 | [2]: http://travis-ci.org/hardening-io/puppet-apache-hardening 88 | [3]: https://gitter.im/hardening-io/general 89 | -------------------------------------------------------------------------------- /Rakefile: -------------------------------------------------------------------------------- 1 | require 'rubygems' 2 | require 'bundler/setup' 3 | 4 | require 'puppetlabs_spec_helper/rake_tasks' 5 | require 'puppet/version' 6 | require 'puppet/vendor/semantic/lib/semantic' unless Puppet.version.to_f < 3.6 7 | require 'puppet-lint/tasks/puppet-lint' 8 | require 'puppet-syntax/tasks/puppet-syntax' 9 | require 'metadata-json-lint/rake_task' 10 | require 'rubocop/rake_task' 11 | 12 | # These gems aren't always present, for instance 13 | # on Travis with --without development 14 | begin 15 | require 'puppet_blacksmith/rake_tasks' 16 | rescue LoadError # rubocop:disable Lint/HandleExceptions 17 | end 18 | 19 | RuboCop::RakeTask.new 20 | 21 | exclude_paths = [ 22 | "bundle/**/*", 23 | "pkg/**/*", 24 | "vendor/**/*", 25 | "spec/**/*", 26 | ] 27 | 28 | # Coverage from puppetlabs-spec-helper requires rcov which 29 | # doesn't work in anything since 1.8.7 30 | Rake::Task[:coverage].clear 31 | 32 | Rake::Task[:lint].clear 33 | 34 | PuppetLint.configuration.relative = true 35 | PuppetLint.configuration.disable_80chars 36 | PuppetLint.configuration.disable_class_inherits_from_params_class 37 | PuppetLint.configuration.disable_class_parameter_defaults 38 | PuppetLint.configuration.fail_on_warnings = true 39 | 40 | PuppetLint::RakeTask.new :lint do |config| 41 | config.ignore_paths = exclude_paths 42 | end 43 | 44 | PuppetSyntax.exclude_paths = exclude_paths 45 | 46 | desc "Run acceptance tests" 47 | RSpec::Core::RakeTask.new(:acceptance) do |t| 48 | t.pattern = 'spec/acceptance' 49 | end 50 | 51 | desc "Populate CONTRIBUTORS file" 52 | task :contributors do 53 | system("git log --format='%aN' | sort -u > CONTRIBUTORS") 54 | end 55 | 56 | desc "Run syntax, lint, and spec tests." 57 | task :test => [ 58 | :metadata_lint, 59 | :syntax, 60 | :lint, 61 | :rubocop, 62 | :spec, 63 | ] 64 | -------------------------------------------------------------------------------- /Thorfile: -------------------------------------------------------------------------------- 1 | require 'bundler' 2 | require 'bundler/setup' 3 | require 'kitchen_sharedtests' 4 | require 'kitchen/sharedtests_thor_tasks' 5 | 6 | Kitchen::SharedtestsThorTasks.new 7 | -------------------------------------------------------------------------------- /manifests/init.pp: -------------------------------------------------------------------------------- 1 | # === Copyright 2 | # 3 | # Copyright 2014, Deutsche Telekom AG 4 | # Licensed under the Apache License, Version 2.0 (the "License"); 5 | # http://www.apache.org/licenses/LICENSE-2.0 6 | # 7 | 8 | # == Class: apache_hardening 9 | # 10 | # Configures overlay hardening 11 | # 12 | # === Parameters 13 | # 14 | # [*provider*] 15 | # The name of the provider you use to install nginx. 16 | # Supported: `puppetlabs/apache` 17 | # 18 | class apache_hardening( 19 | $provider = 'none', 20 | ) { 21 | case $provider { 22 | 'puppetlabs/apache': { 23 | class{'::apache_hardening::puppetlabs': } 24 | } 25 | 'none': { 26 | fail('You haven\'t configured a Apache provider for hardening.') 27 | } 28 | default: { 29 | fail('Unrecognized/Unsupported Apache provider for hardening.') 30 | } 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /manifests/puppetlabs.pp: -------------------------------------------------------------------------------- 1 | # === Copyright 2 | # 3 | # Copyright 2014, Deutsche Telekom AG 4 | # Licensed under the Apache License, Version 2.0 (the "License"); 5 | # http://www.apache.org/licenses/LICENSE-2.0 6 | # 7 | 8 | # == Class: apache_hardening::puppetlabs 9 | # 10 | # Overlay provider for puppetlabs/apache 11 | # 12 | # === Parameters 13 | # 14 | # none 15 | # 16 | class apache_hardening::puppetlabs( 17 | $allowed_http_methods = [ 18 | 'GET', 19 | 'POST', 20 | ] 21 | ) { 22 | 23 | # make sure our options are written to the config file 24 | class{'::apache_hardening::puppetlabs_override': } 25 | 26 | # additional configuration 27 | 28 | # add hardening parameters 29 | 30 | $apache_version = $apache::apache_version 31 | $confd_dir = $apache::confd_dir 32 | $conf_dir = $apache::conf_dir 33 | $mod_dir = $apache::mod_dir 34 | 35 | file { "${confd_dir}/90.hardening.conf": 36 | ensure => file, 37 | content => template('apache_hardening/hardening.conf.erb'), 38 | mode => '0640', 39 | } 40 | 41 | File <| notify == Service['httpd'] or notify == Class['::apache::service'] or require == Package['httpd'] |> { 42 | mode => '0640' 43 | } 44 | 45 | Concat <| require == Package['httpd'] |> { 46 | mode => '0640' 47 | } -> Exec["chmod -R o-rw ${conf_dir}"] ~> Service['httpd'] 48 | 49 | 50 | exec { "chmod -R o-rw ${conf_dir}": 51 | path => ['/bin','/usr/bin', '/usr/sbin'], 52 | unless => "find ${conf_dir} -perm -o+r -type f -o -perm -o+w -type f | wc -l | egrep '^0$'", 53 | } 54 | 55 | File <| title == 'alias.conf' |> { 56 | content => template('apache_hardening/mod/alias.conf.erb'), 57 | mode => '0640', 58 | } 59 | 60 | } 61 | -------------------------------------------------------------------------------- /manifests/puppetlabs_override.pp: -------------------------------------------------------------------------------- 1 | # === Copyright 2 | # 3 | # Copyright 2014, Deutsche Telekom AG 4 | # Licensed under the Apache License, Version 2.0 (the "License"); 5 | # http://www.apache.org/licenses/LICENSE-2.0 6 | # 7 | 8 | # == Class: apache_hardening::puppetlabs_override 9 | # 10 | # Overlay provider for puppetlabs/apache 11 | # 12 | # === Parameters 13 | # 14 | # none 15 | # 16 | class apache_hardening::puppetlabs_override ( 17 | 18 | $server_signature = 'Off', 19 | $server_tokens = 'Prod', 20 | $trace_enable = 'Off', 21 | 22 | ) inherits ::apache { 23 | 24 | File["${::apache::conf_dir}/${::apache::params::conf_file}"]{ 25 | content => template('apache_hardening/httpd.conf.erb'), 26 | mode => '0640', 27 | } 28 | } 29 | -------------------------------------------------------------------------------- /metadata.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "hardening-apache_hardening", 3 | "version": "0.1.0", 4 | "source": "https://github.com/TelekomLabs/puppet-apache-hardening", 5 | "author": "Markus Schmall", 6 | "license": "Apache-2.0", 7 | "summary": "Configures Apache for security hardening", 8 | "description": "Configures Apache for security hardening", 9 | "project_page": "https://github.com/TelekomLabs/puppet-apache-hardening", 10 | "dependencies": [ 11 | { 12 | "name": "puppetlabs/apache" 13 | } 14 | ] 15 | } 16 | -------------------------------------------------------------------------------- /renovate.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://docs.renovatebot.com/renovate-schema.json", 3 | "extends": [ 4 | "config:base", 5 | ":gitSignOff" 6 | ], 7 | "dependencyDashboard": true, 8 | "dependencyDashboardAutoclose": true, 9 | "packageRules": [ 10 | { 11 | "matchUpdateTypes": ["patch", "minor"], 12 | "automerge": true 13 | } 14 | ] 15 | } 16 | -------------------------------------------------------------------------------- /templates/hardening.conf.erb: -------------------------------------------------------------------------------- 1 | # Additional configuration for Apache. 2 | # 3 | # Generated by Puppet 4 | # Generated by apache-hardening module 5 | 6 | 7 | > 8 | # http://httpd.apache.org/docs/2.4/upgrading.html 9 | <% if @apache_version > '2.2' -%> 10 | Require all granted 11 | <% else -%> 12 | Order Allow,Deny 13 | Deny from all 14 | <% end -%> 15 | 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /templates/httpd.conf.erb: -------------------------------------------------------------------------------- 1 | # Security 2 | ServerTokens <%= @server_tokens %> 3 | ServerSignature <%= @server_signature %> 4 | TraceEnable <%= @trace_enable %> 5 | 6 | ServerName "<%= @servername %>" 7 | ServerRoot "<%= @server_root %>" 8 | PidFile <%= @pidfile %> 9 | Timeout <%= @timeout %> 10 | KeepAlive <%= @keepalive %> 11 | MaxKeepAliveRequests <%= @max_keepalive_requests %> 12 | KeepAliveTimeout <%= @keepalive_timeout %> 13 | 14 | User <%= @user %> 15 | Group <%= @group %> 16 | 17 | AccessFileName .htaccess 18 | 19 | <%- if scope.function_versioncmp([@apache_version, '2.4']) >= 0 -%> 20 | Require all denied 21 | <%- else -%> 22 | Order allow,deny 23 | Deny from all 24 | Satisfy all 25 | <%- end -%> 26 | 27 | 28 | 29 | Options -Indexes -FollowSymLinks 30 | AllowOverride None 31 | 32 | 33 | DefaultType none 34 | HostnameLookups Off 35 | ErrorLog "<%= @logroot %>/<%= @error_log %>" 36 | LogLevel <%= @log_level %> 37 | EnableSendfile <%= @sendfile %> 38 | <%- if @allow_encoded_slashes -%> 39 | AllowEncodedSlashes <%= @allow_encoded_slashes %> 40 | <%- end -%> 41 | 42 | #Listen 80 43 | 44 | <% if @apxs_workaround -%> 45 | # Workaround: without this hack apxs would be confused about where to put 46 | # LoadModule directives and fail entire procedure of apache package 47 | # installation/reinstallation. This problem was observed on FreeBSD (apache22). 48 | #LoadModule fake_module libexec/apache22/mod_fake.so 49 | <% end -%> 50 | 51 | Include "<%= @mod_load_dir %>/*.load" 52 | <% if @mod_load_dir != @confd_dir and @mod_load_dir != @vhost_load_dir -%> 53 | Include "<%= @mod_load_dir %>/*.conf" 54 | <% end -%> 55 | Include "<%= @ports_file %>" 56 | 57 | LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"" combined 58 | LogFormat "%h %l %u %t \"%r\" %>s %b" common 59 | LogFormat "%{Referer}i -> %U" referer 60 | LogFormat "%{User-agent}i" agent 61 | <% if @log_formats and !@log_formats.empty? -%> 62 | <%- @log_formats.sort.each do |nickname,format| -%> 63 | LogFormat "<%= format -%>" <%= nickname %> 64 | <%- end -%> 65 | <% end -%> 66 | 67 | <%- if scope.function_versioncmp([@apache_version, '2.4']) >= 0 -%> 68 | IncludeOptional "<%= @confd_dir %>/*.conf" 69 | <%- else -%> 70 | Include "<%= @confd_dir %>/*.conf" 71 | <%- end -%> 72 | <% if @vhost_load_dir != @confd_dir -%> 73 | <%- if scope.function_versioncmp([@apache_version, '2.4']) >= 0 -%> 74 | IncludeOptional "<%= @vhost_load_dir %>/*" 75 | <%- else -%> 76 | Include "<%= @vhost_load_dir %>/*" 77 | <%- end -%> 78 | <% end -%> 79 | 80 | <% if @error_documents -%> 81 | # /usr/share/apache2/error on debian 82 | Alias /error/ "<%= @error_documents_path %>/" 83 | 84 | "> 85 | AllowOverride None 86 | Options IncludesNoExec 87 | AddOutputFilter Includes html 88 | AddHandler type-map var 89 | <%- if scope.function_versioncmp([@apache_version, '2.4']) >= 0 -%> 90 | Require all granted 91 | <%- else -%> 92 | Order allow,deny 93 | Allow from all 94 | <%- end -%> 95 | LanguagePriority en cs de es fr it nl sv pt-br ro 96 | ForceLanguagePriority Prefer Fallback 97 | 98 | 99 | ErrorDocument 400 /error/HTTP_BAD_REQUEST.html.var 100 | ErrorDocument 401 /error/HTTP_UNAUTHORIZED.html.var 101 | ErrorDocument 403 /error/HTTP_FORBIDDEN.html.var 102 | ErrorDocument 404 /error/HTTP_NOT_FOUND.html.var 103 | ErrorDocument 405 /error/HTTP_METHOD_NOT_ALLOWED.html.var 104 | ErrorDocument 408 /error/HTTP_REQUEST_TIME_OUT.html.var 105 | ErrorDocument 410 /error/HTTP_GONE.html.var 106 | ErrorDocument 411 /error/HTTP_LENGTH_REQUIRED.html.var 107 | ErrorDocument 412 /error/HTTP_PRECONDITION_FAILED.html.var 108 | ErrorDocument 413 /error/HTTP_REQUEST_ENTITY_TOO_LARGE.html.var 109 | ErrorDocument 414 /error/HTTP_REQUEST_URI_TOO_LARGE.html.var 110 | ErrorDocument 415 /error/HTTP_UNSUPPORTED_MEDIA_TYPE.html.var 111 | ErrorDocument 500 /error/HTTP_INTERNAL_SERVER_ERROR.html.var 112 | ErrorDocument 501 /error/HTTP_NOT_IMPLEMENTED.html.var 113 | ErrorDocument 502 /error/HTTP_BAD_GATEWAY.html.var 114 | ErrorDocument 503 /error/HTTP_SERVICE_UNAVAILABLE.html.var 115 | ErrorDocument 506 /error/HTTP_VARIANT_ALSO_VARIES.html.var 116 | <% end -%> -------------------------------------------------------------------------------- /templates/mod/alias.conf.erb: -------------------------------------------------------------------------------- 1 | 2 | Alias /icons/ "<%= @icons_path %>/" 3 | "> 4 | Options -Indexes +MultiViews -FollowSymLinks 5 | AllowOverride None 6 | <%- if scope.function_versioncmp([@apache_version, '2.4']) >= 0 -%> 7 | Require all granted 8 | <%- else -%> 9 | Order allow,deny 10 | Allow from all 11 | <%- end -%> 12 | 13 | --------------------------------------------------------------------------------