├── .editorconfig ├── .fixtures.yml ├── .github ├── CONTRIBUTING.md ├── ISSUE_TEMPLATE.md ├── PULL_REQUEST_TEMPLATE.md └── SECURITY.md ├── .gitignore ├── .msync.yml ├── .overcommit.yml ├── .pmtignore ├── .rspec ├── .rspec_parallel ├── .rubocop.yml ├── .sync.yml ├── .travis.yml ├── .yardopts ├── CHANGELOG.md ├── Dockerfile ├── Gemfile ├── HISTORY.md ├── LICENSE ├── README.md ├── REFERENCE.md ├── Rakefile ├── Vagrantfile ├── examples ├── alt_storage.pp ├── apache.pp ├── default_template_settings.pp ├── facts.pp ├── getting_started.pp ├── single_dc.pp └── system_settings.pp ├── files └── CASSANDRA-9822 │ └── cassandra ├── lib └── facter │ ├── cassandracmsheapnewsize.rb │ ├── cassandracmsmaxheapsize.rb │ ├── cassandraheapnewsize.rb │ ├── cassandramajorversion.rb │ ├── cassandramaxheapsize.rb │ ├── cassandraminorversion.rb │ ├── cassandrapatchversion.rb │ └── cassandrarelease.rb ├── manifests ├── apache_repo.pp ├── datastax_agent.pp ├── datastax_repo.pp ├── dse.pp ├── file.pp ├── firewall_ports.pp ├── init.pp ├── java.pp ├── optutils.pp ├── params.pp ├── private │ └── firewall_ports │ │ └── rule.pp ├── schema.pp ├── schema │ ├── cql_type.pp │ ├── index.pp │ ├── keyspace.pp │ ├── permission.pp │ ├── table.pp │ └── user.pp └── system │ ├── swapoff.pp │ ├── sysctl.pp │ └── transparent_hugepage.pp ├── metadata.json ├── spec ├── acceptance │ ├── bootstrap_spec.rb │ ├── cassandra_spec.rb │ └── hieradata │ │ └── environments │ │ └── production │ │ └── data │ │ ├── common.yaml │ │ ├── modules │ │ └── cassandra.yaml │ │ └── osfamily │ │ └── Debian │ │ ├── 12.04.yaml │ │ ├── 16.04.yaml │ │ ├── 7.yaml │ │ └── 8.yaml ├── classes │ ├── apache_repo_spec.rb │ ├── datastax_agent_spec.rb │ ├── datastax_repo_spec.rb │ ├── dse_spec.rb │ ├── firewall_ports_spec.rb │ ├── init_spec.rb │ ├── java_spec.rb │ ├── optutils_spec.rb │ ├── params_spec.rb │ ├── schema_spec.rb │ └── system │ │ ├── swapoff_spec.rb │ │ ├── sysctl_spec.rb │ │ └── transparent_hugepage_spec.rb ├── defines │ ├── file_spec.rb │ ├── private │ │ └── firewall_ports │ │ │ └── rule_spec.rb │ └── schema │ │ ├── cql_type_spec.rb │ │ ├── index_spec.rb │ │ ├── keyspace_spec.rb │ │ ├── permission_spec.rb │ │ ├── table_spec.rb │ │ └── user_spec.rb ├── spec_helper.rb ├── spec_helper_acceptance.rb └── unit │ └── facter │ ├── cassandracmsheapnewsize_spec.rb │ ├── cassandracmsmaxheapsize_spec.rb │ ├── cassandraheapnewsize_spec.rb │ ├── cassandramajorversion_spec.rb │ ├── cassandramaxheapsize_spec.rb │ ├── cassandraminorversion_spec.rb │ ├── cassandrapatchversion_spec.rb │ └── cassandrarelease_spec.rb ├── templates ├── cassandra-rackdc.properties.erb ├── cassandra.yaml.erb ├── cqlshrc.erb └── dse.yaml.erb └── vagrant ├── environment.conf ├── hiera.yaml └── manifests └── site.pp /.editorconfig: -------------------------------------------------------------------------------- 1 | # editorconfig.org 2 | 3 | # MANAGED BY MODULESYNC 4 | 5 | root = true 6 | 7 | [*] 8 | charset = utf-8 9 | end_of_line = lf 10 | indent_size = 2 11 | tab_width = 2 12 | indent_style = space 13 | insert_final_newline = true 14 | trim_trailing_whitespace = true 15 | -------------------------------------------------------------------------------- /.fixtures.yml: -------------------------------------------------------------------------------- 1 | fixtures: 2 | repositories: 3 | apt: https://github.com/puppetlabs/puppetlabs-apt.git 4 | translate: https://github.com/puppetlabs/puppetlabs-translate.git 5 | firewall: https://github.com/puppetlabs/puppetlabs-firewall.git 6 | inifile: https://github.com/puppetlabs/puppetlabs-inifile.git 7 | stdlib: https://github.com/puppetlabs/puppetlabs-stdlib.git 8 | yumrepo_core: https://github.com/puppetlabs/puppetlabs-yumrepo_core.git 9 | mount_core: https://github.com/puppetlabs/puppetlabs-mount_core.git 10 | -------------------------------------------------------------------------------- /.github/CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contribution guidelines 2 | 3 | ## Table of contents 4 | 5 | * [Contributing](#contributing) 6 | * [Writing proper commits - short version](#writing-proper-commits-short-version) 7 | * [Writing proper commits - long version](#writing-proper-commits-long-version) 8 | * [Dependencies](#dependencies) 9 | * [Note for OS X users](#note-for-os-x-users) 10 | * [The test matrix](#the-test-matrix) 11 | * [Syntax and style](#syntax-and-style) 12 | * [Running the unit tests](#running-the-unit-tests) 13 | * [Unit tests in docker](#unit-tests-in-docker) 14 | * [Integration tests](#integration-tests) 15 | 16 | This module has grown over time based on a range of contributions from 17 | people using it. If you follow these contributing guidelines your patch 18 | will likely make it into a release a little more quickly. 19 | 20 | ## Contributing 21 | 22 | Please note that this project is released with a Contributor Code of Conduct. 23 | By participating in this project you agree to abide by its terms. 24 | [Contributor Code of Conduct](https://voxpupuli.org/coc/). 25 | 26 | * Fork the repo. 27 | * Create a separate branch for your change. 28 | * We only take pull requests with passing tests, and documentation. [travis-ci](http://travis-ci.org) runs the tests for us. You can also execute them locally. This is explained [in a later section](#the-test-matrix). 29 | * Checkout [our docs](https://voxpupuli.org/docs/reviewing_pr/) we use to review a module and the [official styleguide](https://puppet.com/docs/puppet/6.0/style_guide.html). They provide some guidance for new code that might help you before you submit a pull request. 30 | * Add a test for your change. Only refactoring and documentation changes require no new tests. If you are adding functionality or fixing a bug, please add a test. 31 | * Squash your commits down into logical components. Make sure to rebase against our current master. 32 | * Push the branch to your fork and submit a pull request. 33 | 34 | Please be prepared to repeat some of these steps as our contributors review your code. 35 | 36 | Also consider sending in your profile code that calls this component module as an acceptance test or provide it via an issue. This helps reviewers a lot to test your use case and prevents future regressions! 37 | 38 | ## Writing proper commits - short version 39 | 40 | * Make commits of logical units. 41 | * Check for unnecessary whitespace with "git diff --check" before committing. 42 | * Commit using Unix line endings (check the settings around "crlf" in git-config(1)). 43 | * Do not check in commented out code or unneeded files. 44 | * The first line of the commit message should be a short description (50 characters is the soft limit, excluding ticket number(s)), and should skip the full stop. 45 | * Associate the issue in the message. The first line should include the issue number in the form "(#XXXX) Rest of message". 46 | * The body should provide a meaningful commit message, which: 47 | *uses the imperative, present tense: `change`, not `changed` or `changes`. 48 | * includes motivation for the change, and contrasts its implementation with the previous behavior. 49 | * Make sure that you have tests for the bug you are fixing, or feature you are adding. 50 | * Make sure the test suites passes after your commit: 51 | * When introducing a new feature, make sure it is properly documented in the README.md 52 | 53 | ## Writing proper commits - long version 54 | 55 | 1. Make separate commits for logically separate changes. 56 | 57 | Please break your commits down into logically consistent units 58 | which include new or changed tests relevant to the rest of the 59 | change. The goal of doing this is to make the diff easier to 60 | read for whoever is reviewing your code. In general, the easier 61 | your diff is to read, the more likely someone will be happy to 62 | review it and get it into the code base. 63 | 64 | If you are going to refactor a piece of code, please do so as a 65 | separate commit from your feature or bug fix changes. 66 | 67 | We also really appreciate changes that include tests to make 68 | sure the bug is not re-introduced, and that the feature is not 69 | accidentally broken. 70 | 71 | Describe the technical detail of the change(s). If your 72 | description starts to get too long, that is a good sign that you 73 | probably need to split up your commit into more finely grained 74 | pieces. 75 | 76 | Commits which plainly describe the things which help 77 | reviewers check the patch and future developers understand the 78 | code are much more likely to be merged in with a minimum of 79 | bike-shedding or requested changes. Ideally, the commit message 80 | would include information, and be in a form suitable for 81 | inclusion in the release notes for the version of Puppet that 82 | includes them. 83 | 84 | Please also check that you are not introducing any trailing 85 | whitespace or other "whitespace errors". You can do this by 86 | running "git diff --check" on your changes before you commit. 87 | 88 | 2. Sending your patches 89 | 90 | To submit your changes via a GitHub pull request, we _highly_ 91 | recommend that you have them on a topic branch, instead of 92 | directly on `master`. 93 | It makes things much easier to keep track of, especially if 94 | you decide to work on another thing before your first change 95 | is merged in. 96 | 97 | GitHub has some pretty good 98 | [general documentation](http://help.github.com/) on using 99 | their site. They also have documentation on 100 | [creating pull requests](http://help.github.com/send-pull-requests/). 101 | 102 | In general, after pushing your topic branch up to your 103 | repository on GitHub, you can switch to the branch in the 104 | GitHub UI and click "Pull Request" towards the top of the page 105 | in order to open a pull request. 106 | 107 | 108 | 3. Update the related GitHub issue. 109 | 110 | If there is a GitHub issue associated with the change you 111 | submitted, then you should update the ticket to include the 112 | location of your branch, along with any other commentary you 113 | may wish to make. 114 | 115 | ## Dependencies 116 | 117 | The testing and development tools have a bunch of dependencies, 118 | all managed by [bundler](http://bundler.io/) according to the 119 | [Puppet support matrix](http://docs.puppetlabs.com/guides/platforms.html#ruby-versions). 120 | 121 | By default the tests use a baseline version of Puppet. 122 | 123 | If you have Ruby 2.x or want a specific version of Puppet, 124 | you must set an environment variable such as: 125 | 126 | ```sh 127 | export PUPPET_VERSION="~> 5.5.6" 128 | ``` 129 | 130 | You can install all needed gems for spec tests into the modules directory by 131 | running: 132 | 133 | ```sh 134 | bundle install --path .vendor/ --without development system_tests release --jobs "$(nproc)" 135 | ``` 136 | 137 | If you also want to run acceptance tests: 138 | 139 | ```sh 140 | bundle install --path .vendor/ --with system_tests --without development release --jobs "$(nproc)" 141 | ``` 142 | 143 | Our all in one solution if you don't know if you need to install or update gems: 144 | 145 | ```sh 146 | bundle install --path .vendor/ --with system_tests --without development release --jobs "$(nproc)"; bundle update; bundle clean 147 | ``` 148 | 149 | As an alternative to the `--jobs "$(nproc)` parameter, you can set an 150 | environment variable: 151 | 152 | ```sh 153 | BUNDLE_JOBS="$(nproc)" 154 | ``` 155 | 156 | ### Note for OS X users 157 | 158 | `nproc` isn't a valid command under OS x. As an alternative, you can do: 159 | 160 | ```sh 161 | --jobs "$(sysctl -n hw.ncpu)" 162 | ``` 163 | 164 | ## The test matrix 165 | 166 | ### Syntax and style 167 | 168 | The test suite will run [Puppet Lint](http://puppet-lint.com/) and 169 | [Puppet Syntax](https://github.com/gds-operations/puppet-syntax) to 170 | check various syntax and style things. You can run these locally with: 171 | 172 | ```sh 173 | bundle exec rake lint 174 | bundle exec rake validate 175 | ``` 176 | 177 | It will also run some [Rubocop](http://batsov.com/rubocop/) tests 178 | against it. You can run those locally ahead of time with: 179 | 180 | ```sh 181 | bundle exec rake rubocop 182 | ``` 183 | 184 | ### Running the unit tests 185 | 186 | The unit test suite covers most of the code, as mentioned above please 187 | add tests if you're adding new functionality. If you've not used 188 | [rspec-puppet](http://rspec-puppet.com/) before then feel free to ask 189 | about how best to test your new feature. 190 | 191 | To run the linter, the syntax checker and the unit tests: 192 | 193 | ```sh 194 | bundle exec rake test 195 | ``` 196 | 197 | To run your all the unit tests 198 | 199 | ```sh 200 | bundle exec rake spec 201 | ``` 202 | 203 | To run a specific spec test set the `SPEC` variable: 204 | 205 | ```sh 206 | bundle exec rake spec SPEC=spec/foo_spec.rb 207 | ``` 208 | 209 | #### Unit tests in docker 210 | 211 | Some people don't want to run the dependencies locally or don't want to install 212 | ruby. We ship a Dockerfile that enables you to run all unit tests and linting. 213 | You only need to run: 214 | 215 | ```sh 216 | docker build . 217 | ``` 218 | 219 | Please ensure that a docker daemon is running and that your user has the 220 | permission to talk to it. You can specify a remote docker host by setting the 221 | `DOCKER_HOST` environment variable. it will copy the content of the module into 222 | the docker image. So it will not work if a Gemfile.lock exists. 223 | 224 | ### Integration tests 225 | 226 | The unit tests just check the code runs, not that it does exactly what 227 | we want on a real machine. For that we're using 228 | [beaker](https://github.com/puppetlabs/beaker). 229 | 230 | This fires up a new virtual machine (using vagrant) and runs a series of 231 | simple tests against it after applying the module. You can run this 232 | with: 233 | 234 | ```sh 235 | bundle exec rake acceptance 236 | ``` 237 | 238 | This will run the tests on the module's default nodeset. You can override the 239 | nodeset used, e.g., 240 | 241 | ```sh 242 | BEAKER_set=centos-7-x64 bundle exec rake acceptance 243 | ``` 244 | 245 | There are default rake tasks for the various acceptance test modules, e.g., 246 | 247 | ```sh 248 | bundle exec rake beaker:centos-7-x64 249 | bundle exec rake beaker:ssh:centos-7-x64 250 | ``` 251 | 252 | If you don't want to have to recreate the virtual machine every time you can 253 | use `BEAKER_destroy=no` and `BEAKER_provision=no`. On the first run you will at 254 | least need `BEAKER_provision` set to yes (the default). The Vagrantfile for the 255 | created virtual machines will be in `.vagrant/beaker_vagrant_files`. 256 | 257 | Beaker also supports docker containers. We also use that in our automated CI 258 | pipeline at [travis-ci](http://travis-ci.org). To use that instead of Vagrant: 259 | 260 | ```sh 261 | PUPPET_INSTALL_TYPE=agent BEAKER_IS_PE=no BEAKER_PUPPET_COLLECTION=puppet6 BEAKER_debug=true BEAKER_setfile=debian10-64{hypervisor=docker} BEAKER_destroy=yes bundle exec rake beaker 262 | ``` 263 | 264 | You can replace the string `debian10` with any common operating system. 265 | The following strings are known to work: 266 | 267 | * ubuntu1604 268 | * ubuntu1804 269 | * ubuntu2004 270 | * debian9 271 | * debian10 272 | * centos6 273 | * centos7 274 | * centos8 275 | 276 | The easiest way to debug in a docker container is to open a shell: 277 | 278 | ```sh 279 | docker exec -it -u root ${container_id_or_name} bash 280 | ``` 281 | 282 | The source of this file is in our [modulesync_config](https://github.com/voxpupuli/modulesync_config/blob/master/moduleroot/.github/CONTRIBUTING.md.erb) 283 | repository. 284 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | 10 | 11 | ## Affected Puppet, Ruby, OS and module versions/distributions 12 | 13 | - Puppet: 14 | - Ruby: 15 | - Distribution: 16 | - Module version: 17 | 18 | ## How to reproduce (e.g Puppet code you use) 19 | 20 | ## What are you seeing 21 | 22 | ## What behaviour did you expect instead 23 | 24 | ## Output log 25 | 26 | ## Any additional information you'd like to impart 27 | -------------------------------------------------------------------------------- /.github/PULL_REQUEST_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | 9 | #### Pull Request (PR) description 10 | 13 | 14 | #### This Pull Request (PR) fixes the following issues 15 | 21 | -------------------------------------------------------------------------------- /.github/SECURITY.md: -------------------------------------------------------------------------------- 1 | # Vox Pupuli Security Policy 2 | 3 | Our vulnerabilities reporting process is at https://voxpupuli.org/security/ 4 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | pkg/ 2 | Gemfile.lock 3 | Gemfile.local 4 | vendor/ 5 | .vendor/ 6 | spec/fixtures/manifests/ 7 | spec/fixtures/modules/ 8 | .vagrant/ 9 | .bundle/ 10 | .ruby-version 11 | coverage/ 12 | log/ 13 | .idea/ 14 | .dependencies/ 15 | .librarian/ 16 | Puppetfile.lock 17 | *.iml 18 | .*.sw? 19 | .yardoc/ 20 | Guardfile 21 | -------------------------------------------------------------------------------- /.msync.yml: -------------------------------------------------------------------------------- 1 | --- 2 | modulesync_config_version: '3.1.0' 3 | -------------------------------------------------------------------------------- /.overcommit.yml: -------------------------------------------------------------------------------- 1 | # Managed by https://github.com/voxpupuli/modulesync_configs 2 | # 3 | # Hooks are only enabled if you take action. 4 | # 5 | # To enable the hooks run: 6 | # 7 | # ``` 8 | # bundle exec overcommit --install 9 | # # ensure .overcommit.yml does not harm to you and then 10 | # bundle exec overcommit --sign 11 | # ``` 12 | # 13 | # (it will manage the .git/hooks directory): 14 | # 15 | # Examples howto skip a test for a commit or push: 16 | # 17 | # ``` 18 | # SKIP=RuboCop git commit 19 | # SKIP=PuppetLint git commit 20 | # SKIP=RakeTask git push 21 | # ``` 22 | # 23 | # Don't invoke overcommit at all: 24 | # 25 | # ``` 26 | # OVERCOMMIT_DISABLE=1 git commit 27 | # ``` 28 | # 29 | # Read more about overcommit: https://github.com/brigade/overcommit 30 | # 31 | # To manage this config yourself in your module add 32 | # 33 | # ``` 34 | # .overcommit.yml: 35 | # unmanaged: true 36 | # ``` 37 | # 38 | # to your modules .sync.yml config 39 | --- 40 | PreCommit: 41 | RuboCop: 42 | enabled: true 43 | description: 'Runs rubocop on modified files only' 44 | command: ['bundle', 'exec', 'rubocop'] 45 | PuppetLint: 46 | enabled: true 47 | description: 'Runs puppet-lint on modified files only' 48 | command: ['bundle', 'exec', 'puppet-lint'] 49 | YamlSyntax: 50 | enabled: true 51 | JsonSyntax: 52 | enabled: true 53 | TrailingWhitespace: 54 | enabled: true 55 | 56 | PrePush: 57 | RakeTarget: 58 | enabled: true 59 | description: 'Run rake targets' 60 | targets: 61 | - 'validate' 62 | - 'test' 63 | - 'rubocop' 64 | command: ['bundle', 'exec', 'rake'] 65 | -------------------------------------------------------------------------------- /.pmtignore: -------------------------------------------------------------------------------- 1 | docs/ 2 | pkg/ 3 | Gemfile.lock 4 | Gemfile.local 5 | vendor/ 6 | .vendor/ 7 | spec/fixtures/manifests/ 8 | spec/fixtures/modules/ 9 | .vagrant/ 10 | .bundle/ 11 | .ruby-version 12 | coverage/ 13 | log/ 14 | .idea/ 15 | .dependencies/ 16 | .librarian/ 17 | Puppetfile.lock 18 | *.iml 19 | .*.sw? 20 | .yardoc/ 21 | Dockerfile 22 | -------------------------------------------------------------------------------- /.rspec: -------------------------------------------------------------------------------- 1 | --format documentation 2 | --color 3 | -------------------------------------------------------------------------------- /.rspec_parallel: -------------------------------------------------------------------------------- 1 | --format progress 2 | -------------------------------------------------------------------------------- /.rubocop.yml: -------------------------------------------------------------------------------- 1 | --- 2 | inherit_gem: 3 | voxpupuli-test: rubocop.yml 4 | -------------------------------------------------------------------------------- /.sync.yml: -------------------------------------------------------------------------------- 1 | --- 2 | .travis.yml: 3 | secure: "I/IK9bG88UOVll0hpuxluGp6IY5gicLaDHug/jGwfuWlN4R3coPAqWO/sGOyaEMbc9V5/Fw0H0ThQdYY3eI3rW5M4a1r9TSg/Z9d46JximPat/XvcpLvUc0G+QxCVhTRmYqD7u0wuX5VSric0PQU6KSjH84ZbKgAA8l04NGObgUI6ugjaNBhkaoIP3glYcHY1fgn5vwER2T/iiXZ5q3qDtYboR2GWLUODLWSpXWZRy7oYvp/RGTSe1fKjDwkbtrZiFvRoyzQvDhEAr+0MFDxJiOLdoKJFeBs6BrF2lyUJ6udlOmEYV94DfKoxEhhlZbxkPCh4SedT79i3c3xkKlf9wfAsEyGSTfc9OtyYBfoHcE9GMRZIvLf2Jn2mpHMO2694Fil4d7JdhLYQ/9Gv9VgFrYosQdVlDh+RxE2CXzrO39LhA1GeOY/n1r+DdvuCJs1fZfBZ1ORb7eQNp1BknurJ8FoYCKlEgihS223IJEnGueDdYkchMSRjS6C3a/HIzBz0RvEDGXD3WgrY5edRIaGziSoSr5eXzumK7N1FFBlpfY/7j38zI1ibWN4PRakmZppeeWOb1xiuVS5JkngCLoYerxLJEEjt8+klXhwnqqJukFuObaVsyprSWp+aAu/UHD/4w/6/lC6Elv+VzccLpITOR5b7VdAuCttQ5PGse6fits=" 4 | spec/spec_helper.rb: 5 | mock_with: ':mocha' 6 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | --- 2 | # yamllint disable rule:line-length rule:truthy 3 | os: linux 4 | dist: focal 5 | language: ruby 6 | cache: bundler 7 | before_install: 8 | - yes | gem update --system 9 | - bundle --version 10 | script: 11 | - 'bundle exec rake $CHECK' 12 | jobs: 13 | fast_finish: true 14 | include: 15 | - rvm: 2.4.4 16 | bundler_args: --without system_tests development release 17 | env: PUPPET_VERSION="~> 5.0" CHECK=test 18 | - rvm: 2.5.3 19 | bundler_args: --without system_tests development release 20 | env: PUPPET_VERSION="~> 6.0" CHECK=test_with_coveralls 21 | - rvm: 2.5.3 22 | bundler_args: --without system_tests development release 23 | env: PUPPET_VERSION="~> 6.0" CHECK=rubocop 24 | - rvm: 2.4.4 25 | bundler_args: --without system_tests development release 26 | env: PUPPET_VERSION="~> 5.0" CHECK=build DEPLOY_TO_FORGE=yes 27 | branches: 28 | only: 29 | - master 30 | - /^v\d/ 31 | notifications: 32 | email: false 33 | webhooks: https://voxpupu.li/incoming/travis 34 | irc: 35 | on_success: always 36 | on_failure: always 37 | channels: 38 | - "chat.freenode.org#voxpupuli-notifications" 39 | deploy: 40 | provider: puppetforge 41 | username: puppet 42 | password: 43 | secure: "I/IK9bG88UOVll0hpuxluGp6IY5gicLaDHug/jGwfuWlN4R3coPAqWO/sGOyaEMbc9V5/Fw0H0ThQdYY3eI3rW5M4a1r9TSg/Z9d46JximPat/XvcpLvUc0G+QxCVhTRmYqD7u0wuX5VSric0PQU6KSjH84ZbKgAA8l04NGObgUI6ugjaNBhkaoIP3glYcHY1fgn5vwER2T/iiXZ5q3qDtYboR2GWLUODLWSpXWZRy7oYvp/RGTSe1fKjDwkbtrZiFvRoyzQvDhEAr+0MFDxJiOLdoKJFeBs6BrF2lyUJ6udlOmEYV94DfKoxEhhlZbxkPCh4SedT79i3c3xkKlf9wfAsEyGSTfc9OtyYBfoHcE9GMRZIvLf2Jn2mpHMO2694Fil4d7JdhLYQ/9Gv9VgFrYosQdVlDh+RxE2CXzrO39LhA1GeOY/n1r+DdvuCJs1fZfBZ1ORb7eQNp1BknurJ8FoYCKlEgihS223IJEnGueDdYkchMSRjS6C3a/HIzBz0RvEDGXD3WgrY5edRIaGziSoSr5eXzumK7N1FFBlpfY/7j38zI1ibWN4PRakmZppeeWOb1xiuVS5JkngCLoYerxLJEEjt8+klXhwnqqJukFuObaVsyprSWp+aAu/UHD/4w/6/lC6Elv+VzccLpITOR5b7VdAuCttQ5PGse6fits=" 44 | on: 45 | tags: true 46 | # all_branches is required to use tags 47 | all_branches: true 48 | # Only publish the build marked with "DEPLOY_TO_FORGE" 49 | condition: "$DEPLOY_TO_FORGE = yes" 50 | -------------------------------------------------------------------------------- /.yardopts: -------------------------------------------------------------------------------- 1 | --markup markdown 2 | --output-dir docs/ 3 | -------------------------------------------------------------------------------- /Dockerfile: -------------------------------------------------------------------------------- 1 | FROM ruby:2.5.3 2 | 3 | WORKDIR /opt/puppet 4 | 5 | # https://github.com/puppetlabs/puppet/blob/06ad255754a38f22fb3a22c7c4f1e2ce453d01cb/lib/puppet/provider/service/runit.rb#L39 6 | RUN mkdir -p /etc/sv 7 | 8 | ARG PUPPET_VERSION="~> 6.0" 9 | ARG PARALLEL_TEST_PROCESSORS=4 10 | 11 | # Cache gems 12 | COPY Gemfile . 13 | RUN bundle install --without system_tests development release --path=${BUNDLE_PATH:-vendor/bundle} 14 | 15 | COPY . . 16 | 17 | RUN bundle install 18 | RUN bundle exec rake release_checks 19 | 20 | # Container should not saved 21 | RUN exit 1 22 | -------------------------------------------------------------------------------- /Gemfile: -------------------------------------------------------------------------------- 1 | source ENV['GEM_SOURCE'] || "https://rubygems.org" 2 | 3 | def location_for(place, fake_version = nil) 4 | if place =~ /^(git[:@][^#]*)#(.*)/ 5 | [fake_version, { :git => $1, :branch => $2, :require => false }].compact 6 | elsif place =~ /^file:\/\/(.*)/ 7 | ['>= 0', { :path => File.expand_path($1), :require => false }] 8 | else 9 | [place, { :require => false }] 10 | end 11 | end 12 | 13 | group :test do 14 | gem 'voxpupuli-test', '~> 2.1', :require => false 15 | gem 'coveralls', :require => false 16 | gem 'simplecov-console', :require => false 17 | end 18 | 19 | group :development do 20 | gem 'travis', :require => false 21 | gem 'travis-lint', :require => false 22 | gem 'guard-rake', :require => false 23 | gem 'overcommit', '>= 0.39.1', :require => false 24 | end 25 | 26 | group :system_tests do 27 | gem 'voxpupuli-acceptance', :require => false 28 | end 29 | 30 | group :release do 31 | gem 'github_changelog_generator', :require => false, :git => 'https://github.com/voxpupuli/github-changelog-generator', :branch => 'voxpupuli_essential_fixes' 32 | gem 'puppet-blacksmith', :require => false 33 | gem 'voxpupuli-release', :require => false 34 | gem 'puppet-strings', '>= 2.2', :require => false 35 | end 36 | 37 | 38 | 39 | if facterversion = ENV['FACTER_GEM_VERSION'] 40 | gem 'facter', facterversion.to_s, :require => false, :groups => [:test] 41 | else 42 | gem 'facter', :require => false, :groups => [:test] 43 | end 44 | 45 | ENV['PUPPET_VERSION'].nil? ? puppetversion = '~> 6.0' : puppetversion = ENV['PUPPET_VERSION'].to_s 46 | gem 'puppet', puppetversion, :require => false, :groups => [:test] 47 | 48 | # vim: syntax=ruby 49 | -------------------------------------------------------------------------------- /Rakefile: -------------------------------------------------------------------------------- 1 | require 'voxpupuli/test/rake' 2 | 3 | # load optional tasks for releases 4 | # only available if gem group releases is installed 5 | begin 6 | require 'voxpupuli/release/rake_tasks' 7 | rescue LoadError 8 | end 9 | 10 | desc "Run main 'test' task and report merged results to coveralls" 11 | task test_with_coveralls: [:test] do 12 | if Dir.exist?(File.expand_path('../lib', __FILE__)) 13 | require 'coveralls/rake/task' 14 | Coveralls::RakeTask.new 15 | Rake::Task['coveralls:push'].invoke 16 | else 17 | puts 'Skipping reporting to coveralls. Module has no lib dir' 18 | end 19 | end 20 | 21 | desc 'Generate REFERENCE.md' 22 | task :reference, [:debug, :backtrace] do |t, args| 23 | patterns = '' 24 | Rake::Task['strings:generate:reference'].invoke(patterns, args[:debug], args[:backtrace]) 25 | end 26 | 27 | begin 28 | require 'github_changelog_generator/task' 29 | GitHubChangelogGenerator::RakeTask.new :changelog do |config| 30 | version = (Blacksmith::Modulefile.new).version 31 | config.future_release = "v#{version}" if version =~ /^\d+\.\d+.\d+$/ 32 | config.header = "# Changelog\n\nAll notable changes to this project will be documented in this file.\nEach new release typically also includes the latest modulesync defaults.\nThese should not affect the functionality of the module." 33 | config.exclude_labels = %w{duplicate question invalid wontfix wont-fix modulesync skip-changelog} 34 | config.user = 'voxpupuli' 35 | metadata_json = File.join(File.dirname(__FILE__), 'metadata.json') 36 | metadata = JSON.load(File.read(metadata_json)) 37 | config.project = metadata['name'] 38 | end 39 | 40 | # Workaround for https://github.com/github-changelog-generator/github-changelog-generator/issues/715 41 | require 'rbconfig' 42 | if RbConfig::CONFIG['host_os'] =~ /linux/ 43 | task :changelog do 44 | puts 'Fixing line endings...' 45 | changelog_file = File.join(__dir__, 'CHANGELOG.md') 46 | changelog_txt = File.read(changelog_file) 47 | new_contents = changelog_txt.gsub(%r{\r\n}, "\n") 48 | File.open(changelog_file, "w") {|file| file.puts new_contents } 49 | end 50 | end 51 | 52 | rescue LoadError 53 | end 54 | # vim: syntax=ruby 55 | -------------------------------------------------------------------------------- /Vagrantfile: -------------------------------------------------------------------------------- 1 | # rubocop:disable Style/FileName 2 | # TODO: Find out why cassandra::params not working with vagrant and CentOS 6.2 3 | # TODO: Find out why cassandra::params not working with vagrant and CentOS 7.0 4 | # TODO: Find out why cassandra::params not working with vagrant and Ubuntu 12.04. 5 | Vagrant.configure('2') do |config| 6 | # config.vm.box = 'puppetlabs/centos-6.6-64-puppet' 7 | # config.vm.box = 'puppetlabs/centos-7.0-64-puppet' 8 | # config.vm.box = 'puppetlabs/debian-7.8-64-puppet' 9 | # config.vm.box = 'puppetlabs/debian-8.2-64-puppet' 10 | # config.vm.box = "puppetlabs/ubuntu-12.04-64-puppet" 11 | config.vm.box = 'puppetlabs/ubuntu-14.04-64-puppet' 12 | # config.vm.box = "puppetlabs/ubuntu-16.04-64-puppet" 13 | 14 | config.vm.provider 'virtualbox' do |vm| 15 | vm.memory = 2048 16 | vm.cpus = 2 17 | end 18 | 19 | puppet_environment = 'vagrant' 20 | puppet_environment_path_on_guest = "/etc/puppetlabs/code/environments/#{puppet_environment}" 21 | module_path_on_guest = "#{puppet_environment_path_on_guest}/modules" 22 | 23 | config.vm.synced_folder './vagrant', 24 | '/etc/puppetlabs/code/environments/vagrant' 25 | config.vm.synced_folder '.', 26 | '/etc/puppetlabs/code/environments/vagrant/modules/cassandra' 27 | config.vm.synced_folder './spec/acceptance/hieradata', 28 | '/etc/puppetlabs/code/environments/vagrant/hieradata' 29 | 30 | metadata_json_file = "#{File.dirname(__FILE__)}/metadata.json" 31 | config.vm.provision :shell, 32 | inline: "test -d #{module_path_on_guest}/ || mkdir #{puppet_environment_path_on_guest}" 33 | 34 | if File.exist?(metadata_json_file) 35 | JSON.parse(File.read(metadata_json_file))['dependencies'].each do |key, _value| 36 | module_name = key['name'].to_s 37 | short_name = module_name.split('-')[1] 38 | config.vm.provision :shell, 39 | inline: "test -d #{module_path_on_guest}/#{short_name} || puppet module install #{module_name} --environment=#{puppet_environment}" 40 | end 41 | else 42 | puts 'metadata.json not found; skipping install of dependencies' 43 | end 44 | 45 | config.vm.provision :puppet do |puppet| 46 | puppet.options = ENV['PUPPET_OPTS'].split(' ') if ENV.key?('PUPPET_OPTS') # See http://stackoverflow.com/a/27540417/224334 47 | puppet.options = '--verbose --debug' if ENV['PUPPET_VERBOSE'] 48 | puppet.hiera_config_path = 'vagrant/hiera.yaml' 49 | puppet.environment = puppet_environment 50 | puppet.environment_path = './' 51 | puppet.manifests_path = "#{puppet_environment}/manifests" 52 | puppet.manifest_file = 'site.pp' 53 | puppet.facter = { 54 | project_name: 'ENGLISH NAME Of PROJECT', # EDIT THIS LINE 55 | } 56 | end 57 | 58 | config.vm.network :forwarded_port, guest: 22, host: 2223, auto_correct: true, id: 'ssh' 59 | # config.vm.network :forwarded_port, guest: 3000, host: 3000 60 | end 61 | -------------------------------------------------------------------------------- /examples/alt_storage.pp: -------------------------------------------------------------------------------- 1 | ############################################################################# 2 | # Specify different storage locations 3 | ############################################################################# 4 | 5 | # Cassandra pre-requisites 6 | include cassandra::datastax_repo 7 | include cassandra::java 8 | 9 | # Specify the storage locations 10 | $commitlog_directory = '/appdata/cassandra/commitlog' 11 | $data_file_directory = '/appdata/cassandra/data' 12 | $saved_caches_directory = '/appdata/cassandra/saved_caches' 13 | 14 | file { '/appdata': 15 | ensure => directory, 16 | mode => '0755', 17 | before => File['/appdata/cassandra'], 18 | } 19 | 20 | file { '/appdata/cassandra': 21 | ensure => directory, 22 | mode => '0755', 23 | before => Class['cassandra'], 24 | } 25 | 26 | # Create a cluster called MyCassandraCluster which uses the 27 | # GossipingPropertyFileSnitch. In this very basic example 28 | # the node itself becomes a seed for the cluster. 29 | 30 | class { 'cassandra': 31 | commitlog_directory => $commitlog_directory, 32 | data_file_directories => [$data_file_directory], 33 | saved_caches_directory => $saved_caches_directory, 34 | settings => { 35 | 'authenticator' => 'PasswordAuthenticator', 36 | 'cluster_name' => 'MyCassandraCluster', 37 | 'commitlog_sync' => 'periodic', 38 | 'commitlog_sync_period_in_ms' => 10000, 39 | 'endpoint_snitch' => 'GossipingPropertyFileSnitch', 40 | 'listen_address' => $facts['networking']['ip'], 41 | 'partitioner' => 'org.apache.cassandra.dht.Murmur3Partitioner', 42 | 'seed_provider' => [ 43 | { 44 | 'class_name' => 'org.apache.cassandra.locator.SimpleSeedProvider', 45 | 'parameters' => [ 46 | { 47 | 'seeds' => $facts['networking']['ip'], 48 | }, 49 | ], 50 | }, 51 | ], 52 | 'start_native_transport' => true, 53 | }, 54 | service_ensure => running, 55 | require => Class['cassandra::datastax_repo', 'cassandra::java'], 56 | } 57 | -------------------------------------------------------------------------------- /examples/apache.pp: -------------------------------------------------------------------------------- 1 | # Cassandra pre-requisites 2 | require cassandra::system::sysctl 3 | require cassandra::system::transparent_hugepage 4 | require cassandra::java 5 | -------------------------------------------------------------------------------- /examples/default_template_settings.pp: -------------------------------------------------------------------------------- 1 | # The defaults as set by the 1.Y.Z template. 2 | 3 | # Cassandra pre-requisites 4 | include cassandra::datastax_repo 5 | include cassandra::java 6 | 7 | class { 'cassandra': 8 | settings => { 9 | 'authenticator' => 'AllowAllAuthenticator', 10 | 'authorizer' => 'AllowAllAuthorizer', 11 | 'auto_snapshot' => true, 12 | 'batch_size_warn_threshold_in_kb' => 5, 13 | 'batchlog_replay_throttle_in_kb' => 1024, 14 | 'cas_contention_timeout_in_ms' => 1000, 15 | 'client_encryption_options' => { 16 | 'enabled' => false, 17 | 'keystore' => 'conf/.keystore', 18 | 'keystore_password' => 'cassandra', 19 | }, 20 | 'cluster_name' => 'Test Cluster', 21 | 'column_index_size_in_kb' => 64, 22 | 'commit_failure_policy' => 'stop', 23 | 'commitlog_directory' => '/var/lib/cassandra/commitlog', 24 | 'commitlog_segment_size_in_mb' => 32, 25 | 'commitlog_sync' => 'periodic', 26 | 'commitlog_sync_period_in_ms' => 10000, 27 | 'compaction_throughput_mb_per_sec' => 16, 28 | 'concurrent_counter_writes' => 32, 29 | 'concurrent_reads' => 32, 30 | 'concurrent_writes' => 32, 31 | 'counter_cache_save_period' => 7200, 32 | 'counter_cache_size_in_mb' => '', 33 | 'counter_write_request_timeout_in_ms' => 5000, 34 | 'cross_node_timeout' => false, 35 | 'data_file_directories' => ['/var/lib/cassandra/data'], 36 | 'disk_failure_policy' => 'stop', 37 | 'dynamic_snitch_badness_threshold' => 0.1, 38 | 'dynamic_snitch_reset_interval_in_ms' => 600000, 39 | 'dynamic_snitch_update_interval_in_ms' => 100, 40 | 'endpoint_snitch' => 'SimpleSnitch', 41 | 'hinted_handoff_enabled' => true, 42 | 'hinted_handoff_throttle_in_kb' => 1024, 43 | 'incremental_backups' => false, 44 | 'index_summary_capacity_in_mb' => '', 45 | 'index_summary_resize_interval_in_minutes' => 60, 46 | 'inter_dc_tcp_nodelay' => false, 47 | 'internode_compression' => 'all', 48 | 'key_cache_save_period' => 14400, 49 | 'key_cache_size_in_mb' => '', 50 | 'listen_address' => 'localhost', 51 | 'max_hint_window_in_ms' => 10800000, 52 | 'max_hints_delivery_threads' => 2, 53 | 'memtable_allocation_type' => 'heap_buffers', 54 | 'native_transport_port' => 9042, 55 | 'num_tokens' => 256, 56 | 'partitioner' => 'org.apache.cassandra.dht.Murmur3Partitioner', 57 | 'permissions_validity_in_ms' => 2000, 58 | 'range_request_timeout_in_ms' => 10000, 59 | 'read_request_timeout_in_ms' => 5000, 60 | 'request_scheduler' => 'org.apache.cassandra.scheduler.NoScheduler', 61 | 'request_timeout_in_ms' => 10000, 62 | 'row_cache_save_period' => 0, 63 | 'row_cache_size_in_mb' => 0, 64 | 'rpc_address' => 'localhost', 65 | 'rpc_keepalive' => true, 66 | 'rpc_port' => 9160, 67 | 'rpc_server_type' => 'sync', 68 | 'saved_caches_directory' => '/var/lib/cassandra/saved_caches', 69 | 'seed_provider' => [ 70 | { 71 | 'class_name' => 'org.apache.cassandra.locator.SimpleSeedProvider', 72 | 'parameters' => [ 73 | { 74 | 'seeds' => '127.0.0.1', 75 | }, 76 | ], 77 | } 78 | ], 79 | 'server_encryption_options' => { 80 | 'internode_encryption' => 'none', 81 | 'keystore' => 'conf/.keystore', 82 | 'keystore_password' => 'cassandra', 83 | 'truststore' => 'conf/.truststore', 84 | 'truststore_password' => 'cassandra', 85 | }, 86 | 'snapshot_before_compaction' => false, 87 | 'ssl_storage_port' => 7001, 88 | 'sstable_preemptive_open_interval_in_mb' => 50, 89 | 'start_native_transport' => true, 90 | 'start_rpc' => true, 91 | 'storage_port' => 7000, 92 | 'thrift_framed_transport_size_in_mb' => 15, 93 | 'tombstone_failure_threshold' => 100000, 94 | 'tombstone_warn_threshold' => 1000, 95 | 'trickle_fsync' => false, 96 | 'trickle_fsync_interval_in_kb' => 10240, 97 | 'truncate_request_timeout_in_ms' => 60000, 98 | 'write_request_timeout_in_ms' => 2000, 99 | }, 100 | require => Class['cassandra::datastax_repo', 'cassandra::java'], 101 | } 102 | -------------------------------------------------------------------------------- /examples/facts.pp: -------------------------------------------------------------------------------- 1 | if $facts['cassandrarelease'] { 2 | notify { "Cassandra release: ${facts['cassandrarelease']}": } 3 | } else { 4 | warning('cassandrarelease is not set!') 5 | } 6 | 7 | if $facts['cassandramajorversion'] { 8 | notify { "Cassandra major version: ${facts['cassandramajorversion']}": } 9 | } else { 10 | warning('cassandramajorversion is not set!') 11 | } 12 | 13 | if $facts['cassandraminorversion'] { 14 | notify { "Cassandra minor version: ${facts['cassandraminorversion']}": } 15 | } else { 16 | warning('cassandraminorversion is not set!') 17 | } 18 | 19 | if $facts['cassandrapatchversion'] { 20 | notify { "Cassandra patch version: ${facts['cassandrapatchversion']}": } 21 | } else { 22 | warning('cassandrapatchversion is not set!') 23 | } 24 | -------------------------------------------------------------------------------- /examples/getting_started.pp: -------------------------------------------------------------------------------- 1 | ############################################################################# 2 | # This is for placing in the getting started section of the README file. 3 | ############################################################################# 4 | # Install Cassandra 2.2.5 onto a system and create a basic keyspace, table 5 | # and index. The node itself becomes a seed for the cluster. 6 | # 7 | # Tested on CentOS 7 8 | ############################################################################# 9 | 10 | # Cassandra pre-requisites 11 | require cassandra::datastax_repo 12 | require cassandra::system::sysctl 13 | require cassandra::system::transparent_hugepage 14 | require cassandra::java 15 | 16 | class { 'cassandra::system::swapoff': 17 | device => '/dev/mapper/centos-swap', 18 | before => Class['cassandra'], 19 | } 20 | 21 | # Create a cluster called MyCassandraCluster which uses the 22 | # GossipingPropertyFileSnitch. In this very basic example 23 | # the node itself becomes a seed for the cluster. 24 | 25 | class { 'cassandra': 26 | commitlog_directory => '/var/lib/cassandra/commitlog', 27 | data_file_directories => ['/var/lib/cassandra/data'], 28 | hints_directory => '/var/lib/cassandra/hints', 29 | package_name => 'cassandra30', 30 | saved_caches_directory => '/var/lib/cassandra/saved_caches', 31 | settings => { 32 | 'authenticator' => 'PasswordAuthenticator', 33 | 'authorizer' => 'CassandraAuthorizer', 34 | 'cluster_name' => 'MyCassandraCluster', 35 | 'commitlog_sync' => 'periodic', 36 | 'commitlog_sync_period_in_ms' => 10000, 37 | 'endpoint_snitch' => 'GossipingPropertyFileSnitch', 38 | 'listen_address' => $facts['networking']['ip'], 39 | 'partitioner' => 'org.apache.cassandra.dht.Murmur3Partitioner', 40 | 'seed_provider' => [ 41 | { 42 | 'class_name' => 'org.apache.cassandra.locator.SimpleSeedProvider', 43 | 'parameters' => [ 44 | { 45 | 'seeds' => $facts['networking']['ip'], 46 | }, 47 | ], 48 | }, 49 | ], 50 | 'start_native_transport' => true, 51 | }, 52 | service_ensure => running, 53 | require => Class['cassandra::datastax_repo', 'cassandra::system::sysctl', 'cassandra::java'], 54 | } 55 | 56 | class { 'cassandra::datastax_agent': 57 | settings => { 58 | 'agent_alias' => { 59 | 'setting' => 'agent_alias', 60 | 'value' => 'foobar', 61 | }, 62 | 'stomp_interface' => { 63 | 'setting' => 'stomp_interface', 64 | 'value' => 'localhost', 65 | }, 66 | 'async_pool_size' => { 67 | 'ensure' => absent, 68 | }, 69 | }, 70 | require => Class['cassandra'], 71 | } 72 | 73 | class { 'cassandra::optutils': 74 | package_name => 'cassandra30-tools', 75 | require => Class['cassandra'], 76 | } 77 | 78 | class { 'cassandra::schema': 79 | cqlsh_password => 'cassandra', 80 | cqlsh_user => 'cassandra', 81 | cqlsh_host => $facts['networking']['ip'], 82 | indexes => { 83 | 'users_lname_idx' => { 84 | table => 'users', 85 | keys => 'lname', 86 | keyspace => 'mykeyspace', 87 | }, 88 | }, 89 | keyspaces => { 90 | 'mykeyspace' => { 91 | durable_writes => false, 92 | replication_map => { 93 | keyspace_class => 'SimpleStrategy', 94 | replication_factor => 1, 95 | }, 96 | }, 97 | }, 98 | permissions => { 99 | 'Grant select permissions to spillman to all keyspaces' => { 100 | permission_name => 'SELECT', 101 | user_name => 'spillman', 102 | }, 103 | 'Grant modify to to keyspace mykeyspace to akers' => { 104 | keyspace_name => 'mykeyspace', 105 | permission_name => 'MODIFY', 106 | user_name => 'akers', 107 | }, 108 | 'Grant alter permissions to mykeyspace to boone' => { 109 | keyspace_name => 'mykeyspace', 110 | permission_name => 'ALTER', 111 | user_name => 'boone', 112 | }, 113 | 'Grant ALL permissions to mykeyspace.users to gbennet' => { 114 | keyspace_name => 'mykeyspace', 115 | permission_name => 'ALTER', 116 | table_name => 'users', 117 | user_name => 'gbennet', 118 | }, 119 | }, 120 | tables => { 121 | 'users' => { 122 | columns => { 123 | user_id => 'int', 124 | fname => 'text', 125 | lname => 'text', 126 | 'PRIMARY KEY' => '(user_id)', 127 | }, 128 | keyspace => 'mykeyspace', 129 | }, 130 | }, 131 | users => { 132 | 'spillman' => { 133 | password => 'Niner27', 134 | }, 135 | 'akers' => { 136 | password => 'Niner2', 137 | superuser => true, 138 | }, 139 | 'boone' => { 140 | password => 'Niner75', 141 | }, 142 | 'gbennet' => { 143 | 'password' => 'foobar', 144 | }, 145 | 'lucan' => { 146 | 'ensure' => absent, 147 | }, 148 | }, 149 | } 150 | 151 | $ram_sz_mb = floor($facts['memory']['system']['total_bytes'] / (1024*1024)) 152 | $half_of_ram = floor($ram_sz_mb / 2) 153 | $quarter_of_ram = floor($ram_sz_mb / 4) 154 | $max_heap_size_in_mb = max(min($half_of_ram, 1024), min($quarter_of_ram, 8192)) 155 | $heap_new_size = $facts['processors']['count'] * 100 156 | 157 | cassandra::file { "Set Java/Cassandra max heap size to ${max_heap_size_in_mb}.": 158 | file => 'cassandra-env.sh', 159 | file_lines => { 160 | 'MAX_HEAP_SIZE' => { 161 | line => "MAX_HEAP_SIZE='${max_heap_size_in_mb}M'", 162 | match => '^#?MAX_HEAP_SIZE=.*', 163 | }, 164 | }, 165 | } 166 | 167 | cassandra::file { "Set Java/Cassandra heap new size to ${heap_new_size}.": 168 | file => 'cassandra-env.sh', 169 | file_lines => { 170 | 'HEAP_NEWSIZE' => { 171 | line => "HEAP_NEWSIZE='${heap_new_size}M'", 172 | match => '^#?HEAP_NEWSIZE=.*', 173 | }, 174 | }, 175 | } 176 | 177 | $tmpdir = '/var/lib/cassandra/tmp' 178 | 179 | file { $tmpdir: 180 | ensure => directory, 181 | owner => 'cassandra', 182 | group => 'cassandra', 183 | require => Package['cassandra'], 184 | } 185 | 186 | cassandra::file { 'Set java.io.tmpdir': 187 | file => 'jvm.options', 188 | file_lines => { 189 | 'java.io.tmpdir' => { 190 | line => "-Djava.io.tmpdir=${tmpdir}", 191 | }, 192 | }, 193 | require => File[$tmpdir], 194 | } 195 | -------------------------------------------------------------------------------- /examples/single_dc.pp: -------------------------------------------------------------------------------- 1 | # Cassandra pre-requisites 2 | include cassandra::datastax_repo 3 | include cassandra::java 4 | 5 | class { 'cassandra': 6 | package_name => 'cassandra30', 7 | settings => { 8 | 'authenticator' => 'AllowAllAuthenticator', 9 | 'auto_bootstrap' => false, 10 | 'cluster_name' => 'MyCassandraCluster', 11 | 'commitlog_directory' => '/var/lib/cassandra/commitlog', 12 | 'commitlog_sync' => 'periodic', 13 | 'commitlog_sync_period_in_ms' => 10000, 14 | 'data_file_directories' => ['/var/lib/cassandra/data'], 15 | 'endpoint_snitch' => 'GossipingPropertyFileSnitch', 16 | 'hints_directory' => '/var/lib/cassandra/hints', 17 | 'listen_interface' => 'eth1', 18 | 'num_tokens' => 256, 19 | 'partitioner' => 'org.apache.cassandra.dht.Murmur3Partitioner', 20 | 'saved_caches_directory' => '/var/lib/cassandra/saved_caches', 21 | 'seed_provider' => [ 22 | { 23 | 'class_name' => 'org.apache.cassandra.locator.SimpleSeedProvider', 24 | 'parameters' => [ 25 | { 26 | 'seeds' => $facts['networking']['ip'], 27 | }, 28 | ], 29 | }, 30 | ], 31 | 'start_native_transport' => true, 32 | }, 33 | service_ensure => running, 34 | require => Class['cassandra::datastax_repo', 'cassandra::java'], 35 | } 36 | -------------------------------------------------------------------------------- /examples/system_settings.pp: -------------------------------------------------------------------------------- 1 | # Cassandra pre-requisites 2 | require cassandra::datastax_repo 3 | require cassandra::system::transparent_hugepage 4 | 5 | case "${facts['os']['name']}-${operatingsystemmajrelease}" { 6 | 'CentOS-6': { 7 | $device = '/dev/mapper/VolGroup-lv_swap' 8 | $sysctl_args = '-e -p' 9 | } 10 | 'CentOS-7': { 11 | $device = '/dev/mapper/centos-swap' 12 | } 13 | default: {} 14 | } 15 | 16 | class { 'cassandra::system::swapoff': 17 | device => $device, 18 | } 19 | 20 | if $sysctl_args { 21 | class { 'cassandra::system::sysctl': 22 | sysctl_args => $sysctl_args, 23 | } 24 | } else { 25 | require cassandra::system::sysctl 26 | } 27 | -------------------------------------------------------------------------------- /files/CASSANDRA-9822/cassandra: -------------------------------------------------------------------------------- 1 | #! /bin/sh 2 | ### BEGIN INIT INFO 3 | # Provides: cassandra 4 | # Required-Start: $remote_fs $network $named $time 5 | # Required-Stop: $remote_fs $network $named $time 6 | # Should-Start: ntp mdadm 7 | # Should-Stop: ntp mdadm 8 | # Default-Start: 2 3 4 5 9 | # Default-Stop: 0 1 6 10 | # Short-Description: distributed storage system for structured data 11 | # Description: Cassandra is a distributed (peer-to-peer) system for 12 | # the management and storage of structured data. 13 | ### END INIT INFO 14 | 15 | # Author: Eric Evans 16 | 17 | DESC="Cassandra" 18 | NAME=cassandra 19 | PIDFILE=/var/run/$NAME/$NAME.pid 20 | SCRIPTNAME=/etc/init.d/$NAME 21 | CONFDIR=/etc/cassandra 22 | WAIT_FOR_START=10 23 | CASSANDRA_HOME=/usr/share/cassandra 24 | FD_LIMIT=100000 25 | 26 | [ -e /usr/share/cassandra/apache-cassandra.jar ] || exit 0 27 | [ -e /etc/cassandra/cassandra.yaml ] || exit 0 28 | [ -e /etc/cassandra/cassandra-env.sh ] || exit 0 29 | 30 | # Read configuration variable file if it is present 31 | [ -r /etc/default/$NAME ] && . /etc/default/$NAME 32 | 33 | # Read Cassandra environment file. 34 | . /etc/cassandra/cassandra-env.sh 35 | 36 | if [ -z "$JVM_OPTS" ]; then 37 | echo "Initialization failed; \$JVM_OPTS not set!" >&2 38 | exit 3 39 | fi 40 | 41 | export JVM_OPTS 42 | 43 | # Export JAVA_HOME, if set. 44 | [ -n "$JAVA_HOME" ] && export JAVA_HOME 45 | 46 | # Load the VERBOSE setting and other rcS variables 47 | . /lib/init/vars.sh 48 | 49 | # Define LSB log_* functions. 50 | # Depend on lsb-base (>= 3.0-6) to ensure that this file is present. 51 | . /lib/lsb/init-functions 52 | 53 | # 54 | # Function that returns 0 if process is running, or nonzero if not. 55 | # 56 | # The nonzero value is 3 if the process is simply not running, and 1 if the 57 | # process is not running but the pidfile exists (to match the exit codes for 58 | # the "status" command; see LSB core spec 3.1, section 20.2) 59 | # 60 | CMD_PATT="cassandra" 61 | is_running() 62 | { 63 | if [ -f $PIDFILE ]; then 64 | pid=`cat $PIDFILE` 65 | grep -Eq "$CMD_PATT" "/proc/$pid/cmdline" 2>/dev/null && return 0 66 | return 1 67 | fi 68 | return 3 69 | } 70 | 71 | # 72 | # Function that starts the daemon/service 73 | # 74 | do_start() 75 | { 76 | # Return 77 | # 0 if daemon has been started 78 | # 1 if daemon was already running 79 | # 2 if daemon could not be started 80 | 81 | ulimit -l unlimited 82 | ulimit -n "$FD_LIMIT" 83 | 84 | cassandra_home=`getent passwd cassandra | awk -F ':' '{ print $6; }'` 85 | heap_dump_f="$cassandra_home/java_`date +%s`.hprof" 86 | error_log_f="$cassandra_home/hs_err_`date +%s`.log" 87 | 88 | [ -e `dirname "$PIDFILE"` ] || \ 89 | install -d -ocassandra -gcassandra -m755 `dirname $PIDFILE` 90 | 91 | 92 | 93 | start-stop-daemon -S -c cassandra -a /usr/sbin/cassandra -q -p "$PIDFILE" -t >/dev/null || return 1 94 | 95 | start-stop-daemon -S -c cassandra -a /usr/sbin/cassandra -b -p "$PIDFILE" -- \ 96 | -p "$PIDFILE" -H "$heap_dump_f" -E "$error_log_f" >/dev/null || return 2 97 | 98 | } 99 | 100 | # 101 | # Function that stops the daemon/service 102 | # 103 | do_stop() 104 | { 105 | # Return 106 | # 0 if daemon has been stopped 107 | # 1 if daemon was already stopped 108 | # 2 if daemon could not be stopped 109 | # other if a failure occurred 110 | start-stop-daemon -K -p "$PIDFILE" -R TERM/30/KILL/5 >/dev/null 111 | RET=$? 112 | rm -f "$PIDFILE" 113 | return $RET 114 | } 115 | 116 | case "$1" in 117 | start) 118 | [ "$VERBOSE" != no ] && log_daemon_msg "Starting $DESC" "$NAME" 119 | do_start 120 | case "$?" in 121 | 0|1) [ "$VERBOSE" != no ] && log_end_msg 0 ;; 122 | 2) [ "$VERBOSE" != no ] && log_end_msg 1 ;; 123 | esac 124 | ;; 125 | stop) 126 | [ "$VERBOSE" != no ] && log_daemon_msg "Stopping $DESC" "$NAME" 127 | do_stop 128 | case "$?" in 129 | 0|1) [ "$VERBOSE" != no ] && log_end_msg 0 ;; 130 | 2) [ "$VERBOSE" != no ] && log_end_msg 1 ;; 131 | esac 132 | ;; 133 | restart|force-reload) 134 | log_daemon_msg "Restarting $DESC" "$NAME" 135 | do_stop 136 | case "$?" in 137 | 0|1) 138 | do_start 139 | case "$?" in 140 | 0) log_end_msg 0 ;; 141 | 1) log_end_msg 1 ;; # Old process is still running 142 | *) log_end_msg 1 ;; # Failed to start 143 | esac 144 | ;; 145 | *) 146 | # Failed to stop 147 | log_end_msg 1 148 | ;; 149 | esac 150 | ;; 151 | status) 152 | is_running 153 | stat=$? 154 | case "$stat" in 155 | 0) log_success_msg "$DESC is running" ;; 156 | 1) log_failure_msg "could not access pidfile for $DESC" ;; 157 | *) log_success_msg "$DESC is not running" ;; 158 | esac 159 | exit "$stat" 160 | ;; 161 | *) 162 | echo "Usage: $SCRIPTNAME {start|stop|restart|force-reload|status}" >&2 163 | exit 3 164 | ;; 165 | esac 166 | 167 | : 168 | 169 | # vi:ai sw=4 ts=4 tw=0 et 170 | -------------------------------------------------------------------------------- /lib/facter/cassandracmsheapnewsize.rb: -------------------------------------------------------------------------------- 1 | # Returns a value (MB) that might be suitable to set the HEAP_NEWSIZE when using 2 | # the Concurrent Mark Sweep (CMS) Collector. 3 | # See [Tuning Java resources] 4 | # (https://docs.datastax.com/en/cassandra/2.1/cassandra/operations/ops_tune_jvm_c.html) 5 | # for more details. 6 | # 7 | # @return [integer] min(100 times the number of cores, 1/4 CMS MAX_HEAP_SIZE) 8 | # @see cassandracmsmaxheapsize 9 | # @see cassandramaxheapsize 10 | # @see cassandracmsheapnewsize 11 | Facter.add('cassandracmsheapnewsize') do 12 | setcode do 13 | maxheapsize = Facter.value(:cassandracmsmaxheapsize).to_f 14 | processorcount = Facter.value(:processorcount).to_f 15 | heapnewsize = [100 * processorcount, maxheapsize * 0.25].min 16 | heapnewsize.round 17 | end 18 | end 19 | -------------------------------------------------------------------------------- /lib/facter/cassandracmsmaxheapsize.rb: -------------------------------------------------------------------------------- 1 | # Returns a value (MB) that might be suitable to set the MAX_HEAP_SIZE when using 2 | # the Concurrent Mark Sweep (CMS) Collector. 3 | # See [Tuning Java resources] 4 | # (https://docs.datastax.com/en/cassandra/2.1/cassandra/operations/ops_tune_jvm_c.html) 5 | # for more details. 6 | # 7 | # @return [integer] max(min(1/2 ram, 1024), min(1/4 ram, 14336)) 8 | # @see cassandracmsheapnewsize 9 | # @see cassandraheapnewsize 10 | # @see cassandramaxheapsize 11 | Facter.add('cassandracmsmaxheapsize') do 12 | setcode do 13 | memorysize_mb = Facter.value(:memorysize_mb).to_f 14 | calc1 = [memorysize_mb * 0.5, 1024].min 15 | calc2 = [memorysize_mb * 0.25, 14_336].min 16 | maxheapsize = [calc1, calc2].max 17 | maxheapsize.round 18 | end 19 | end 20 | -------------------------------------------------------------------------------- /lib/facter/cassandraheapnewsize.rb: -------------------------------------------------------------------------------- 1 | # Returns a value (MB) that might be suitable to set the HEAP_NEWSIZE. 2 | # See [Tuning Java resources] 3 | # (https://docs.datastax.com/en/cassandra/2.1/cassandra/operations/ops_tune_jvm_c.html) 4 | # for more details. 5 | # 6 | # @return [integer] min(100 times the number of cores, 1/4 MAX_HEAP_SIZE) 7 | # @see cassandracmsheapnewsize 8 | # @see cassandracmsmaxheapsize 9 | # @see cassandramaxheapsize 10 | Facter.add('cassandraheapnewsize') do 11 | setcode do 12 | maxheapsize = Facter.value(:cassandramaxheapsize).to_f 13 | processorcount = Facter.value(:processorcount).to_f 14 | heapnewsize = [100 * processorcount, maxheapsize * 0.25].min 15 | heapnewsize.round 16 | end 17 | end 18 | -------------------------------------------------------------------------------- /lib/facter/cassandramajorversion.rb: -------------------------------------------------------------------------------- 1 | # Extract the major version from the cassandrarelease fact. 2 | # @caveats 3 | # Requires that the cassandrarelease has been successfully retrieved. 4 | # @return [integer] The major version of the Cassandra instance. 5 | # @see cassandrarelease 6 | Facter.add('cassandramajorversion') do 7 | setcode do 8 | release = Facter.value(:cassandrarelease) 9 | release.split('.')[0].to_i if release 10 | end 11 | end 12 | -------------------------------------------------------------------------------- /lib/facter/cassandramaxheapsize.rb: -------------------------------------------------------------------------------- 1 | # Returns a value (MB) that might be suitable to set the MAX_HEAP_SIZE. 2 | # See [Tuning Java resources] 3 | # (https://docs.datastax.com/en/cassandra/2.1/cassandra/operations/ops_tune_jvm_c.html) 4 | # for more details. 5 | # 6 | # @return [integer] max(min(1/2 ram, 1024), min(1/4 ram, 8192)) 7 | # @see cassandracmsheapnewsize 8 | # @see cassandracmsmaxheapsize 9 | # @see cassandraheapnewsize 10 | Facter.add('cassandramaxheapsize') do 11 | setcode do 12 | memorysize_mb = Facter.value(:memorysize_mb).to_f 13 | calc1 = [memorysize_mb * 0.5, 1024].min 14 | calc2 = [memorysize_mb * 0.25, 8192].min 15 | maxheapsize = [calc1, calc2].max 16 | maxheapsize.round 17 | end 18 | end 19 | -------------------------------------------------------------------------------- /lib/facter/cassandraminorversion.rb: -------------------------------------------------------------------------------- 1 | # Extract the minor version from the cassandrarelease fact. 2 | # @caveats 3 | # Requires that the cassandrarelease has been successfully retrieved. 4 | # @return [integer] The minor version of the Cassandra instance. 5 | # @see cassandrarelease 6 | Facter.add('cassandraminorversion') do 7 | setcode do 8 | release = Facter.value(:cassandrarelease) 9 | release.split('.')[1].to_i if release 10 | end 11 | end 12 | -------------------------------------------------------------------------------- /lib/facter/cassandrapatchversion.rb: -------------------------------------------------------------------------------- 1 | # Extract the patch version from the cassandrarelease fact. 2 | # @caveats 3 | # Requires that the cassandrarelease has been successfully retrieved. 4 | # @return [integer] The patch version of the Cassandra instance. 5 | # @see cassandrarelease 6 | Facter.add('cassandrapatchversion') do 7 | setcode do 8 | release = Facter.value(:cassandrarelease) 9 | release.split('.')[2].to_i if release 10 | end 11 | end 12 | -------------------------------------------------------------------------------- /lib/facter/cassandrarelease.rb: -------------------------------------------------------------------------------- 1 | # Extract the release string from the running Cassandra instance. 2 | # 3 | # @resolution 4 | # Runs the command "nodetool version". 5 | # @caveats 6 | # The Cassandra service needs to be running, otherwise the fact will be 7 | # undefined. 8 | # @return [string] The version string (e.g. 3.0.1). 9 | Facter.add('cassandrarelease') do 10 | setcode do 11 | version = Facter::Util::Resolution.exec('nodetool version') 12 | version.match(%r{\d+\.\d+\.\d+}).to_s if version && version != '' 13 | end 14 | end 15 | -------------------------------------------------------------------------------- /manifests/apache_repo.pp: -------------------------------------------------------------------------------- 1 | # An optional class that will allow a suitable repository to be configured 2 | # from which packages for Apache Cassandra can be downloaded. 3 | # @param descr [string] On the Red Hat family, this is passed as the `descr` 4 | # attribute to a `yumrepo` resource. On the Debian family, it is passed as 5 | # the `comment` attribute to an `apt::source` resource. 6 | # @param key_id [string] On the Debian family, this is passed as the `id` 7 | # attribute to an `apt::key` resource. On the Red Hat family, it is 8 | # ignored. 9 | # @param key_url [string] On the Debian family, this is passed as the 10 | # `source` attribute to an `apt::key` resource. On the Red Hat family, 11 | # it is set to the `gpgkey` attribute on the `yumrepo` resource. 12 | # @param pkg_url [string] On the Red Hat family, leaving this as default will 13 | # set the `baseurl` on the `yumrepo` resource to 14 | # 'http://www.apache.org/dist/cassandra/redhat' with whatever is set in the 15 | # 'release' attribute appended. 16 | # On the Debian family, leaving this as the default 17 | # will set the `location` attribute on an `apt::source` to 18 | # 'http://www.apache.org/dist/cassandra/debian'. 19 | # @param release [string] On the Debian family, this is passed as the `release` 20 | # attribute to an `apt::source` resource. On the Red Hat family, it is the 21 | # major version number of Cassandra, without dot, and with an appended 'x' 22 | # (e.g. '311x') 23 | class cassandra::apache_repo ( 24 | $descr = 'Repo for Apache Cassandra', 25 | $key_id = 'A26E528B271F19B9E5D8E19EA278B781FE4B2BDA', 26 | $key_url = 'https://www.apache.org/dist/cassandra/KEYS', 27 | $pkg_url = undef, 28 | $release = 'main', 29 | ) { 30 | case $facts['os']['family'] { 31 | 'RedHat': { 32 | if $pkg_url != undef { 33 | $baseurl = $pkg_url 34 | } else { 35 | $url = 'http://www.apache.org/dist/cassandra/redhat' 36 | $baseurl = "${url}/${release}" 37 | } 38 | 39 | yumrepo { 'cassandra_apache': 40 | ensure => present, 41 | descr => $descr, 42 | baseurl => $baseurl, 43 | enabled => 1, 44 | gpgcheck => 1, 45 | gpgkey => $key_url, 46 | } 47 | } 48 | 'Debian': { 49 | include apt 50 | include apt::update 51 | 52 | apt::key { 'apache.cassandra': 53 | id => $key_id, 54 | source => $key_url, 55 | before => Apt::Source['cassandra.sources'], 56 | } 57 | 58 | if $pkg_url != undef { 59 | $location = $pkg_url 60 | } else { 61 | $location = 'http://www.apache.org/dist/cassandra/debian' 62 | } 63 | 64 | apt::source { 'cassandra.sources': 65 | location => $location, 66 | comment => $descr, 67 | release => $release, 68 | include => { 69 | 'src' => false, 70 | }, 71 | notify => Exec['update-apache-cassandra-repo'], 72 | } 73 | 74 | # Required to wrap apt_update 75 | exec { 'update-apache-cassandra-repo': 76 | refreshonly => true, 77 | command => '/bin/true', 78 | require => Exec['apt_update'], 79 | } 80 | } 81 | default: { 82 | warning("OS family ${facts['os']['family']} not supported") 83 | } 84 | } 85 | } 86 | -------------------------------------------------------------------------------- /manifests/datastax_agent.pp: -------------------------------------------------------------------------------- 1 | # A class for installing the DataStax Agent and to point it at an OpsCenter 2 | # instance. 3 | # 4 | # @param address_config_file The full path to the address config file. 5 | # @param defaults_file The full path name to the file where `java_home` is set. 6 | # @param java_home If the value of this variable is left as *undef*, no 7 | # action is taken. Otherwise the value is set as JAVA_HOME in 8 | # `defaults_file`. 9 | # @param package_ensure Is passed to the package reference. Valid values are 10 | # **present** or a version number. 11 | # @param package_name Is passed to the package reference. 12 | # @param service_ensure Is passed to the service reference. 13 | # @param service_enable Is passed to the service reference. 14 | # @param service_name Is passed to the service reference. 15 | # @param service_provider The name of the provider that runs the service. 16 | # If left as *undef* then the OS family specific default will be used, 17 | # otherwise the specified value will be used instead. 18 | # @param settings A hash that is passed to 19 | # [create_ini_settings] 20 | # (https://github.com/puppetlabs/puppetlabs-inifile#function-create_ini_settings) 21 | # with the following additional defaults: 22 | # 23 | # ```puppet 24 | # { 25 | # path => $address_config_file, 26 | # key_val_separator => ': ', 27 | # require => Package[$package_name], 28 | # notify => Service['datastax-agent'], 29 | # } 30 | # ``` 31 | # 32 | # @example Set agent_alias to foobar, stomp_interface to localhost and ensure that async_pool_size is absent from the file. 33 | # class { 'cassandra::datastax_agent': 34 | # settings => { 35 | # 'agent_alias' => { 36 | # 'setting' => 'agent_alias', 37 | # 'value' => 'foobar', 38 | # }, 39 | # 'stomp_interface' => { 40 | # 'setting' => 'stomp_interface', 41 | # 'value' => 'localhost', 42 | # }, 43 | # 'async_pool_size' => { 44 | # 'ensure' => absent, 45 | # }, 46 | # }, 47 | # } 48 | class cassandra::datastax_agent ( 49 | $address_config_file = '/var/lib/datastax-agent/conf/address.yaml', 50 | $defaults_file = '/etc/default/datastax-agent', 51 | $java_home = undef, 52 | $package_ensure = 'present', 53 | $package_name = 'datastax-agent', 54 | $service_ensure = 'running', 55 | $service_enable = true, 56 | $service_name = 'datastax-agent', 57 | $service_provider = undef, 58 | $settings = {}, 59 | ) inherits cassandra::params { 60 | require 'cassandra' 61 | 62 | if $service_provider != undef { 63 | System { 64 | provider => $service_provider, 65 | } 66 | } 67 | 68 | package { $package_name: 69 | ensure => $package_ensure, 70 | require => Class['cassandra'], 71 | notify => Exec['datastax_agent_reload_systemctl'], 72 | } 73 | 74 | exec { 'datastax_agent_reload_systemctl': 75 | command => "${cassandra::params::systemctl} daemon-reload", 76 | onlyif => "test -x ${cassandra::params::systemctl}", 77 | path => ['/usr/bin', '/bin'], 78 | refreshonly => true, 79 | notify => Service['datastax-agent'], 80 | } 81 | 82 | file { $address_config_file: 83 | owner => 'cassandra', 84 | group => 'cassandra', 85 | mode => '0644', 86 | require => Package[$package_name], 87 | } 88 | 89 | if $java_home != undef { 90 | ini_setting { 'java_home': 91 | ensure => present, 92 | path => $defaults_file, 93 | section => '', 94 | key_val_separator => '=', 95 | setting => 'JAVA_HOME', 96 | value => $java_home, 97 | notify => Service['datastax-agent'], 98 | } 99 | } 100 | 101 | service { 'datastax-agent': 102 | ensure => $service_ensure, 103 | enable => $service_enable, 104 | name => $service_name, 105 | } 106 | 107 | if $settings { 108 | $defaults = { 109 | path => $address_config_file, 110 | key_val_separator => ': ', 111 | require => Package[$package_name], 112 | notify => Service['datastax-agent'], 113 | } 114 | 115 | $full_settings = { 116 | '' => $settings, 117 | } 118 | create_ini_settings($full_settings, $defaults) 119 | } 120 | } 121 | -------------------------------------------------------------------------------- /manifests/datastax_repo.pp: -------------------------------------------------------------------------------- 1 | # An optional class that will allow a suitable repository to be configured 2 | # from which packages for DataStax Community can be downloaded. Changing 3 | # the defaults will allow any Debian Apt or Red Hat Yum repository to be 4 | # configured. 5 | # @param descr [string] On the Red Hat family, this is passed as the `descr` 6 | # attribute to a `yumrepo` resource. On the Debian family, it is passed as 7 | # the `comment` attribute to an `apt::source` resource. 8 | # @param key_id [string] On the Debian family, this is passed as the `id` 9 | # attribute to an `apt::key` resource. On the Red Hat family, it is 10 | # ignored. 11 | # @param key_url [string] On the Debian family, this is passed as the 12 | # `source` attribute to an `apt::key` resource. On the Red Hat family, 13 | # it is ignored. 14 | # @param pkg_url [string] If left as the default, this will set the `baseurl` 15 | # to 'http://rpm.datastax.com/community' on a `yumrepo` resource 16 | # on the Red Hat family. On the Debian family, leaving this as the default 17 | # will set the `location` attribute on an `apt::source` to 18 | # 'http://debian.datastax.com/community'. 19 | # @param release [string] On the Debian family, this is passed as the `release` 20 | # attribute to an `apt::source` resource. On the Red Hat family, it is 21 | # ignored. 22 | class cassandra::datastax_repo ( 23 | $descr = 'DataStax Repo for Apache Cassandra', 24 | $key_id = '7E41C00F85BFC1706C4FFFB3350200F2B999A372', 25 | $key_url = 'http://debian.datastax.com/debian/repo_key', 26 | $pkg_url = undef, 27 | $release = 'stable', 28 | ) { 29 | case $facts['os']['family'] { 30 | 'RedHat': { 31 | if $pkg_url != undef { 32 | $baseurl = $pkg_url 33 | } else { 34 | $baseurl = 'http://rpm.datastax.com/community' 35 | } 36 | 37 | yumrepo { 'datastax': 38 | ensure => present, 39 | descr => $descr, 40 | baseurl => $baseurl, 41 | enabled => 1, 42 | gpgcheck => 0, 43 | } 44 | } 45 | 'Debian': { 46 | include apt 47 | include apt::update 48 | 49 | apt::key { 'datastaxkey': 50 | id => $key_id, 51 | source => $key_url, 52 | before => Apt::Source['datastax'], 53 | } 54 | 55 | if $pkg_url != undef { 56 | $location = $pkg_url 57 | } else { 58 | $location = 'http://debian.datastax.com/community' 59 | } 60 | 61 | apt::source { 'datastax': 62 | location => $location, 63 | comment => $descr, 64 | release => $release, 65 | include => { 66 | 'src' => false, 67 | }, 68 | notify => Exec['update-cassandra-repos'], 69 | } 70 | 71 | # Required to wrap apt_update 72 | exec { 'update-cassandra-repos': 73 | refreshonly => true, 74 | command => '/bin/true', 75 | require => Exec['apt_update'], 76 | } 77 | } 78 | default: { 79 | warning("OS family ${facts['os']['family']} not supported") 80 | } 81 | } 82 | } 83 | -------------------------------------------------------------------------------- /manifests/dse.pp: -------------------------------------------------------------------------------- 1 | # A class for configuring DataStax Enterprise (DSE) specific settings. 2 | # 3 | # @param config_file [string] The full path to the DSE configuration file. 4 | # @param config_file_mode [string] The mode for the DSE configuration file. 5 | # @param dse_yaml_tmpl [string] A path to a template for the `dse.yaml` file. 6 | # @param file_lines [hash] A hash of values that are passed to 7 | # `create_resources` as a `file_line` resource. 8 | # @param service_refresh [boolean] Whether or not the Cassandra service 9 | # should be refreshed if the DSE configuration files are changed. 10 | # @param settings [hash] Unless this attribute is set to a hash (which is 11 | # then placed as YAML inside `dse.yaml`) then the `dse.yaml` is left 12 | # unchanged. 13 | # @example Configure a cluster with LDAP authentication 14 | # class { 'cassandra::dse': 15 | # file_lines => { 16 | # 'Set HADOOP_LOG_DIR directory' => { 17 | # ensure => present, 18 | # path => '/etc/dse/dse-env.sh', 19 | # line => 'export HADOOP_LOG_DIR=/var/log/hadoop', 20 | # match => '^# export HADOOP_LOG_DIR=', 21 | # }, 22 | # 'Set DSE_HOME' => { 23 | # ensure => present, 24 | # path => '/etc/dse/dse-env.sh', 25 | # line => 'export DSE_HOME=/usr/share/dse', 26 | # match => '^#export DSE_HOME', 27 | # }, 28 | # }, 29 | # settings => { 30 | # ldap_options => { 31 | # server_host => localhost, 32 | # server_port => 389, 33 | # search_dn => 'cn=Admin', 34 | # search_password => secret, 35 | # use_ssl => false, 36 | # use_tls => false, 37 | # truststore_type => jks, 38 | # user_search_base => 'ou=users,dc=example,dc=com', 39 | # user_search_filter => '(uid={0})', 40 | # credentials_validity_in_ms => 0, 41 | # connection_pool => { 42 | # max_active => 8, 43 | # max_idle => 8, 44 | # } 45 | # } 46 | # } 47 | # } 48 | class cassandra::dse ( 49 | $config_file = '/etc/dse/dse.yaml', 50 | $config_file_mode = '0644', 51 | $dse_yaml_tmpl = 'cassandra/dse.yaml.erb', 52 | $file_lines = undef, 53 | $service_refresh = true, 54 | $settings = undef, 55 | ) { 56 | include cassandra 57 | include stdlib 58 | 59 | if $service_refresh { 60 | $notifications = Service['cassandra'] 61 | } else { 62 | $notifications = [] 63 | } 64 | 65 | if is_hash($file_lines) { 66 | $default_file_line = { 67 | require => Package['cassandra'], 68 | notify => $notifications, 69 | } 70 | 71 | create_resources(file_line, $file_lines, $default_file_line) 72 | } 73 | 74 | if is_hash($settings) { 75 | file { $config_file: 76 | ensure => file, 77 | owner => 'cassandra', 78 | group => 'cassandra', 79 | content => template($dse_yaml_tmpl), 80 | mode => $config_file_mode, 81 | require => Package['cassandra'], 82 | notify => $notifications, 83 | } 84 | } 85 | } 86 | -------------------------------------------------------------------------------- /manifests/file.pp: -------------------------------------------------------------------------------- 1 | # A defined type for altering files relative to the configuration directory. 2 | # @param file [string] The name of the file relative to the `config_path`. 3 | # @param config_path [string] The path to the configuration directory. 4 | # @param file_lines [string] If set, then the [create_resources] 5 | # (https://docs.puppet.com/puppet/latest/reference/function.html#createresources) 6 | # will be used to create an array of [file_line] 7 | # (https://forge.puppet.com/puppetlabs/stdlib#file_line) resources. 8 | # @param service_refresh [boolean] Is the Cassandra service is to be notified 9 | # if the environment file is changed. 10 | # @example 11 | # if $::memorysize_mb < 24576.0 { 12 | # $max_heap_size_in_mb = floor($::memorysize_mb / 2) 13 | # } elsif $::memorysize_mb < 8192.0 { 14 | # $max_heap_size_in_mb = floor($::memorysize_mb / 4) 15 | # } else { 16 | # $max_heap_size_in_mb = 8192 17 | # } 18 | # 19 | # $heap_new_size = $::processorcount * 100 20 | # 21 | # cassandra::file { "Set Java/Cassandra max heap size to ${max_heap_size_in_mb}.": 22 | # file => 'cassandra-env.sh', 23 | # file_lines => { 24 | # 'MAX_HEAP_SIZE' => { 25 | # line => "MAX_HEAP_SIZE='${max_heap_size_in_mb}M'", 26 | # match => '^#?MAX_HEAP_SIZE=.*', 27 | # }, 28 | # } 29 | # } 30 | # 31 | # cassandra::file { "Set Java/Cassandra heap new size to ${heap_new_size}.": 32 | # file => 'cassandra-env.sh', 33 | # file_lines => { 34 | # 'HEAP_NEWSIZE' => { 35 | # line => "HEAP_NEWSIZE='${heap_new_size}M'", 36 | # match => '^#?HEAP_NEWSIZE=.*', 37 | # } 38 | # } 39 | # } 40 | # $tmpdir = '/var/lib/cassandra/tmp' 41 | # 42 | # file { $tmpdir: 43 | # ensure => directory, 44 | # owner => 'cassandra', 45 | # group => 'cassandra', 46 | # } 47 | # 48 | # cassandra::file { 'Set java.io.tmpdir': 49 | # file => 'jvm.options', 50 | # file_lines => { 51 | # 'java.io.tmpdir' => { 52 | # line => "-Djava.io.tmpdir=${tmpdir}", 53 | # }, 54 | # }, 55 | # require => File[$tmpdir], 56 | # } 57 | define cassandra::file ( 58 | $file = $title, 59 | $config_path = $cassandra::config_path, 60 | $file_lines = undef, 61 | $service_refresh = true, 62 | ) { 63 | include cassandra 64 | include cassandra::params 65 | include stdlib 66 | 67 | $path = "${config_path}/${file}" 68 | 69 | if $file_lines != undef { 70 | if $service_refresh { 71 | $default_file_line = { 72 | path => $path, 73 | require => Package['cassandra'], 74 | notify => Service['cassandra'], 75 | } 76 | } else { 77 | $default_file_line = { 78 | path => $path, 79 | require => Package['cassandra'], 80 | } 81 | } 82 | 83 | create_resources(file_line, $file_lines, $default_file_line) 84 | } 85 | } 86 | -------------------------------------------------------------------------------- /manifests/firewall_ports.pp: -------------------------------------------------------------------------------- 1 | # An optional class to configure incoming network ports on the host that are 2 | # relevant to the Cassandra installation. If firewalls are being managed 3 | # already, simply do not include this module in your manifest. 4 | # 5 | # IMPORTANT: The full list of which ports should be configured is assessed at 6 | # evaluation time of the configuration. Therefore if one is to use this class, 7 | # it must be the final cassandra class included in the manifest. 8 | # @param client_ports [array] Only has any effect if the `cassandra` class is defined on the node. 9 | # Allow these TCP ports to be opened for traffic coming from the client 10 | # subnets. 11 | # @param client_subnets [array] Only has any effect if the `cassandra` class is defined on the node. 12 | # An array of the list of subnets that are to allowed connection to 13 | # cassandra::native_transport_port and cassandra::rpc_port. 14 | # @param inter_node_ports [array] Only has any effect if the `cassandra` class is defined on the node. 15 | # Allow these TCP ports to be opened for traffic between the Cassandra nodes. 16 | # @param inter_node_subnets [array] Only has any effect if the `cassandra` class is defined on the node. 17 | # An array of the list of subnets that are to allowed connection to 18 | # `cassandra::storage_port`, `cassandra::ssl_storage_port` and port 7199 19 | # for cassandra JMX monitoring. 20 | # @param public_ports [array] Allow these TCP ports to be opened for traffic 21 | # coming from public subnets the port specified in `$ssh_port` will be 22 | # appended to this list. 23 | # @param public_subnets [array] An array of the list of subnets that are to allowed connection to 24 | # cassandra::firewall_ports::ssh_port. 25 | # @param ssh_port [integer] Which port does SSH operate on. 26 | # @param opscenter_ports [array] Only has any effect if the `cassandra::datastax_agent` is defined. 27 | # Allow these TCP ports to be opened for traffic coming to or from OpsCenter 28 | # appended to this list. 29 | # @param opscenter_subnets [array] A list of subnets that are to be allowed connection to 30 | # port 61621 for nodes built with cassandra::datastax_agent. 31 | class cassandra::firewall_ports ( 32 | $client_ports = [9042, 9160], 33 | $client_subnets = ['0.0.0.0/0'], 34 | $inter_node_ports = [7000, 7001, 7199], 35 | $inter_node_subnets = ['0.0.0.0/0'], 36 | $public_ports = [8888], 37 | $public_subnets = ['0.0.0.0/0'], 38 | $ssh_port = 22, 39 | $opscenter_ports = [9042, 9160, 61620, 61621], 40 | $opscenter_subnets = ['0.0.0.0/0'], 41 | ) { 42 | # Public connections on any node. 43 | $public_subnets_array = prefix($public_subnets, '200_Public_') 44 | 45 | cassandra::private::firewall_ports::rule { $public_subnets_array: 46 | ports => concat($public_ports, [$ssh_port]), 47 | } 48 | 49 | # If this is a Cassandra node. 50 | if defined ( Class['cassandra']) { 51 | # Inter-node connections for Cassandra 52 | $inter_node_subnets_array = prefix($inter_node_subnets, '210_InterNode_') 53 | 54 | cassandra::private::firewall_ports::rule { $inter_node_subnets_array: 55 | ports => $inter_node_ports, 56 | } 57 | 58 | # Client connections for Cassandra 59 | $client_subnets_array = prefix($client_subnets, '220_Client_') 60 | 61 | cassandra::private::firewall_ports::rule { $client_subnets_array: 62 | ports => $client_ports, 63 | } 64 | } 65 | 66 | # Connections for DataStax Agent 67 | if defined ( Class['cassandra::datastax_agent']) or defined ( Class['cassandra::opscenter']) { 68 | $opscenter_subnets_opc_agent = prefix($opscenter_subnets, '230_OpsCenter_') 69 | 70 | cassandra::private::firewall_ports::rule { $opscenter_subnets_opc_agent: 71 | ports => $opscenter_ports, 72 | } 73 | } 74 | } 75 | -------------------------------------------------------------------------------- /manifests/java.pp: -------------------------------------------------------------------------------- 1 | # A class to install Java and JNA packages. 2 | # @param aptkey [hash] If supplied, this should be a hash of `apt::key` 3 | # resources that will be passed to the create_resources function. 4 | # This is ignored on non-Debian systems. 5 | # @param aptsource [hash] If supplied, this should be a hash of 6 | # `apt::source` resources that will be passed to the create_resources 7 | # function. This is ignored on non-Red Hat` 8 | # @param jna_ensure [string] Is passed to the package reference for the JNA 9 | # package. Valid values are `present` or a version number. 10 | # @param jna_package_name [string] The name of the JNA package. 11 | # @param package_ensure [string] Is passed to the package reference for the JRE/JDK 12 | # package. Valid values are `present` or a version number. 13 | # @param package_name [string] The name of the Java package to be installed. 14 | # @param yumrepo [hash] If supplied, this should be a hash of *yumrepo* 15 | # resources that will be passed to the create_resources function. 16 | # This is ignored on non-Red Hat systems. 17 | class cassandra::java ( 18 | $aptkey = undef, 19 | $aptsource = undef, 20 | $jna_ensure = present, 21 | $jna_package_name = $cassandra::params::jna_package_name, 22 | $package_ensure = present, 23 | $package_name = $cassandra::params::java_package, 24 | $yumrepo = undef, 25 | ) inherits cassandra::params { 26 | if $facts['os']['family'] == 'RedHat' and $yumrepo != undef { 27 | $yumrepo_defaults = { 28 | 'before' => Package[$package_name], 29 | } 30 | 31 | create_resources(yumrepo, $yumrepo, $yumrepo_defaults) 32 | } 33 | 34 | if $facts['os']['family'] == 'Debian' { 35 | if $aptkey != undef { 36 | $aptkey_defaults = { 37 | 'before' => Package[$package_name], 38 | } 39 | 40 | include apt 41 | create_resources(apt::key, $aptkey, $aptkey_defaults) 42 | } 43 | 44 | if $aptsource != undef { 45 | exec { 'cassandra::java::apt_update': 46 | refreshonly => true, 47 | command => '/bin/true', 48 | require => Exec['apt_update'], 49 | before => Package[$package_name], 50 | } 51 | 52 | $aptsource_defaults = { 53 | 'notify' => Exec['cassandra::java::apt_update'], 54 | } 55 | 56 | create_resources(apt::source, $aptsource, $aptsource_defaults) 57 | } 58 | } 59 | 60 | package { $package_name: 61 | ensure => $package_ensure, 62 | } 63 | 64 | package { $jna_package_name: 65 | ensure => $jna_ensure, 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /manifests/optutils.pp: -------------------------------------------------------------------------------- 1 | # A class to install the optional Cassandra tools package. 2 | # @param package_ensure [string] Can be `present`, `latest` or a specific 3 | # version number. 4 | # @param package_name [string] The name of the optional utilities package to 5 | # be installed. 6 | class cassandra::optutils ( 7 | $package_ensure = 'present', 8 | $package_name = $cassandra::params::optutils_package_name, 9 | ) inherits cassandra::params { 10 | include 'cassandra' 11 | 12 | package { $package_name: 13 | ensure => $package_ensure, 14 | require => Class['cassandra'], 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /manifests/params.pp: -------------------------------------------------------------------------------- 1 | # This class is meant to be called from the locp-cassandra module. 2 | # It sets variables according to platform. 3 | class cassandra::params { 4 | case $facts['os']['family'] { 5 | 'Debian': { 6 | case $facts['os']['release']['major'] { 7 | '12.04': { 8 | $net_ipv4_tcp_rmem = '4096 87380 16777216' 9 | $net_ipv4_tcp_wmem = '4096 65536 16777216' 10 | $java_package = 'openjdk-7-jre-headless' 11 | } 12 | '18.04': { 13 | $net_ipv4_tcp_rmem = '4096 87380 16777216' 14 | $net_ipv4_tcp_wmem = '4096 65536 16777216' 15 | $java_package = 'openjdk-8-jre-headless' 16 | } 17 | # non-Ubuntu Debian is just... Debian 18 | default: { 19 | $net_ipv4_tcp_rmem = '4096, 87380, 16777216' 20 | $net_ipv4_tcp_wmem = '4096, 65536, 16777216' 21 | $java_package = 'openjdk-7-jre-headless' 22 | } 23 | } 24 | 25 | $cassandra_pkg = 'cassandra' 26 | $config_path = '/etc/cassandra' 27 | $jna_package_name = 'libjna-java' 28 | $optutils_package_name = 'cassandra-tools' 29 | $sysctl_file = '/etc/sysctl.d/10-cassandra.conf' 30 | $systemctl = '/bin/systemctl' 31 | $use_scl = false 32 | $scl_name = 'nodefault' 33 | } 34 | 'RedHat': { 35 | case $facts['os']['release']['major'] { 36 | '6': { 37 | $net_ipv4_tcp_rmem = '4096 87380 16777216' 38 | $net_ipv4_tcp_wmem = '4096 65536 16777216' 39 | $sysctl_file = '/etc/sysctl.conf' 40 | } 41 | '7': { 42 | $net_ipv4_tcp_rmem = '4096, 87380, 16777216' 43 | $net_ipv4_tcp_wmem = '4096, 65536, 16777216' 44 | $sysctl_file = '/etc/sysctl.d/10-cassandra.conf' 45 | } 46 | default: {} 47 | } 48 | 49 | $cassandra_pkg = 'cassandra22' 50 | $config_path = '/etc/cassandra/default.conf' 51 | $java_package = 'java-1.8.0-openjdk-headless' 52 | $jna_package_name = 'jna' 53 | $optutils_package_name = 'cassandra22-tools' 54 | $systemctl = '/usr/bin/systemctl' 55 | $use_scl = false 56 | $scl_name = 'nodefault' 57 | } 58 | default: { 59 | $config_path_parents = [] 60 | } 61 | } 62 | } 63 | -------------------------------------------------------------------------------- /manifests/private/firewall_ports/rule.pp: -------------------------------------------------------------------------------- 1 | # A defined type to be used as a macro for setting host based firewall 2 | # rules. This is not intended to be used by a user (who should use the 3 | # API provided by cassandra::firewall_ports instead) but is documented 4 | # here for completeness. 5 | # @param ports [integer] The number(s) of the port(s) to be opened. 6 | define cassandra::private::firewall_ports::rule ( 7 | $ports, 8 | ) { 9 | $array_var1 = split($title, '_') 10 | $rule_number = $array_var1[0] 11 | $rule_description = $array_var1[1] 12 | $source = $array_var1[2] 13 | 14 | if size($ports) > 0 { 15 | firewall { "${rule_number} - Cassandra (${rule_description}) - ${source}": 16 | action => 'accept', 17 | dport => $ports, 18 | proto => 'tcp', 19 | source => $source, 20 | } 21 | } 22 | } 23 | -------------------------------------------------------------------------------- /manifests/schema.pp: -------------------------------------------------------------------------------- 1 | # 2 | # @summary A class to maintain the database schema. Please note that cqlsh expects Python 2.7 to be installed. This may be a problem of older distributions (CentOS 6 for example). 3 | # 4 | # @param connection_tries [integer] How many times do try to connect to 5 | # Cassandra. See also `connection_try_sleep`. 6 | # @param connection_try_sleep [integer] How much time to allow between the 7 | # number of tries specified in `connection_tries`. 8 | # @param cql_types [hash] Creates new `cassandra::schema::cql_type` resources. 9 | # @param cqlsh_additional_options [string] Any additional options to be passed 10 | # to the `cqlsh` command. 11 | # @param cqlsh_client_config [string] Set this to a file name 12 | # (e.g. '/root/.puppetcqlshrc') that will then be used to contain the 13 | # the credentials for connecting to Cassandra. This is a more secure option 14 | # than having the credentials appearing on the command line. This option 15 | # is only available in Cassandra >= 2.1. 16 | # @param cqlsh_client_tmpl [string] The location of the template for configuring 17 | # the credentials for the cqlsh client. This is ignored unless 18 | # `cqlsh_client_config` is set. 19 | # @param cqlsh_command [string] The full path to the `cqlsh` command. 20 | # @param cqlsh_host [string] The host for the `cqlsh` command to connect to. 21 | # See also `cqlsh_port`. 22 | # @param cqlsh_password [string] If credentials are require for connecting, 23 | # specify the password here. See also `cqlsh_user`, `cqlsh_client_config`. 24 | # @param cqlsh_port [integer] The host for the `cqlsh` command to connect to. 25 | # See also `cqlsh_host`. 26 | # @param cqlsh_user [string] If credentials are required for connecting, 27 | # specify the password here. See also `cqlsh_password`, 28 | # `cqlsh_client_config` 29 | # @param indexes [hash] Creates new `cassandra::schema::index` resources. 30 | # @param keyspaces [hash] Creates new `cassandra::schema::keyspace` resources. 31 | # @param permissions [hash] Creates new `cassandra::schema::permission` 32 | # resources. 33 | # @param tables [hash] Creates new `cassandra::schema::table` resources. 34 | # @param users [hash] Creates new `cassandra::schema::user` resources. 35 | class cassandra::schema ( 36 | $connection_tries = 6, 37 | $connection_try_sleep = 30, 38 | $cql_types = {}, 39 | $cqlsh_additional_options = '', 40 | $cqlsh_client_config = undef, 41 | $cqlsh_client_tmpl = 'cassandra/cqlshrc.erb', 42 | $cqlsh_command = '/usr/bin/cqlsh', 43 | $cqlsh_host = 'localhost', 44 | $cqlsh_password = undef, 45 | $cqlsh_port = 9042, 46 | $cqlsh_user = 'cassandra', 47 | $indexes = {}, 48 | $keyspaces = {}, 49 | $permissions = {}, 50 | $tables = {}, 51 | $users = {}, 52 | Boolean $use_scl = $cassandra::params::use_scl, 53 | String[1] $scl_name = $cassandra::params::scl_name, 54 | ) inherits cassandra::params { 55 | require 'cassandra' 56 | 57 | # Pass the SCL info to create_resources below as a hash 58 | $scl = { 59 | 'use_scl' => $use_scl, 60 | 'scl_name' => $scl_name, 61 | } 62 | 63 | if $cqlsh_client_config != undef { 64 | file { $cqlsh_client_config : 65 | ensure => file, 66 | group => $facts['identity']['gid'], 67 | mode => '0600', 68 | owner => $facts['identity']['uid'], 69 | content => template( $cqlsh_client_tmpl ), 70 | before => Exec['cassandra::schema connection test'], 71 | } 72 | 73 | $cmdline_login = "--cqlshrc=${cqlsh_client_config}" 74 | } else { 75 | if $cqlsh_password != undef { 76 | warning('You may want to consider using the cqlsh_client_config attribute') 77 | $cmdline_login = "-u ${cqlsh_user} -p ${cqlsh_password}" 78 | } else { 79 | $cmdline_login = '' 80 | } 81 | } 82 | 83 | $cqlsh_opts = "${cqlsh_command} ${cmdline_login} ${cqlsh_additional_options}" 84 | $cqlsh_conn = "${cqlsh_host} ${cqlsh_port}" 85 | 86 | # See if we can make a connection to Cassandra. Try $connection_tries 87 | # number of times with $connection_try_sleep in seconds between each try. 88 | $connection_test_tmp = "${cqlsh_opts} -e 'DESC KEYSPACES' ${cqlsh_conn}" 89 | if $use_scl { 90 | $connection_test = "/usr/bin/scl enable ${scl_name} \"${connection_test_tmp}\"" 91 | } else { 92 | $connection_test = $connection_test_tmp 93 | } 94 | 95 | exec { 'cassandra::schema connection test': 96 | command => $connection_test, 97 | returns => 0, 98 | tries => $connection_tries, 99 | try_sleep => $connection_try_sleep, 100 | unless => $connection_test, 101 | } 102 | 103 | # manage keyspaces if present 104 | if $keyspaces { 105 | create_resources('cassandra::schema::keyspace', $keyspaces, $scl) 106 | } 107 | 108 | # manage cql_types if present 109 | if $cql_types { 110 | create_resources('cassandra::schema::cql_type', $cql_types, $scl) 111 | } 112 | 113 | # manage tables if present 114 | if $tables { 115 | create_resources('cassandra::schema::table', $tables, $scl) 116 | } 117 | 118 | # manage indexes if present 119 | if $indexes { 120 | create_resources('cassandra::schema::index', $indexes, $scl) 121 | } 122 | 123 | # manage users if present 124 | if $users { 125 | create_resources('cassandra::schema::user', $users, $scl) 126 | } 127 | 128 | # manage permissions if present 129 | if $permissions { 130 | create_resources('cassandra::schema::permission', $permissions, $scl) 131 | } 132 | 133 | # Resource Ordering 134 | Cassandra::Schema::Keyspace <| |> -> Cassandra::Schema::Cql_type <| |> 135 | Cassandra::Schema::Keyspace <| |> -> Cassandra::Schema::Table <| |> 136 | Cassandra::Schema::Keyspace <| |> -> Cassandra::Schema::Permission <| |> 137 | Cassandra::Schema::Cql_type <| |> -> Cassandra::Schema::Table <| |> 138 | Cassandra::Schema::Table <| |> -> Cassandra::Schema::Index <| |> 139 | Cassandra::Schema::Table <| |> -> Cassandra::Schema::Permission <| |> 140 | Cassandra::Schema::Index <| |> -> Cassandra::Schema::User <| |> 141 | Cassandra::Schema::User <| |> -> Cassandra::Schema::Permission <| |> 142 | } 143 | -------------------------------------------------------------------------------- /manifests/schema/cql_type.pp: -------------------------------------------------------------------------------- 1 | # Create or drop user defined data types within the schema. 2 | # @param keyspace [string] The name of the keyspace that the data type is to be associated with. 3 | # @param ensure [present|absent] ensure the data type is created, or is dropped. 4 | # @param fields [hash] A hash of the fields that will be components for the data type. 5 | # @param cql_type_name [string] The name of the CQL type to be created. 6 | # @example 7 | # cassandra::schema::cql_type { 'fullname': 8 | # keyspace => 'mykeyspace', 9 | # fields => { 10 | # 'fname' => 'text', 11 | # 'lname' => 'text', 12 | # }, 13 | # } 14 | define cassandra::schema::cql_type ( 15 | $keyspace, 16 | $ensure = present, 17 | $fields = {}, 18 | $cql_type_name = $title, 19 | Boolean $use_scl = $cassandra::params::use_scl, 20 | String[1] $scl_name = $cassandra::params::scl_name, 21 | ) { 22 | include 'cassandra::schema' 23 | 24 | if $use_scl { 25 | $quote = '\"' 26 | } else { 27 | $quote = '"' 28 | } 29 | 30 | $read_script = "DESC TYPE ${keyspace}.${cql_type_name}" 31 | $read_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${read_script}${quote} ${cassandra::schema::cqlsh_conn}" 32 | if $use_scl { 33 | $read_command = "/usr/bin/scl enable ${scl_name} \"${read_command_tmp}\"" 34 | } else { 35 | $read_command = $read_command_tmp 36 | } 37 | 38 | if $ensure == present { 39 | $create_script1 = "CREATE TYPE IF NOT EXISTS ${keyspace}.${cql_type_name}" 40 | $create_script2 = join(join_keys_to_values($fields, ' '), ', ') 41 | $create_script = "${create_script1} (${create_script2})" 42 | $create_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${create_script}${quote} ${cassandra::schema::cqlsh_conn}" 43 | if $use_scl { 44 | $create_command = "/usr/bin/scl enable ${scl_name} \"${create_command_tmp}\"" 45 | } else { 46 | $create_command = $create_command_tmp 47 | } 48 | exec { $create_command: 49 | unless => $read_command, 50 | require => Exec['cassandra::schema connection test'], 51 | } 52 | } elsif $ensure == absent { 53 | $delete_script = "DROP type ${keyspace}.${cql_type_name}" 54 | $delete_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${delete_script}${quote} ${cassandra::schema::cqlsh_conn}" 55 | if $use_scl { 56 | $delete_command = "/usr/bin/scl enable ${scl_name} \"${delete_command_tmp}\"" 57 | } else { 58 | $delete_command = $delete_command_tmp 59 | } 60 | exec { $delete_command: 61 | onlyif => $read_command, 62 | require => Exec['cassandra::schema connection test'], 63 | } 64 | } else { 65 | fail("Unknown action (${ensure}) for ensure attribute.") 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /manifests/schema/index.pp: -------------------------------------------------------------------------------- 1 | # Create or drop indexes within the schema. 2 | # @param ensure [present|absent] Create or dro[ the index. 3 | # @param class_name [string] The name of the class to be associated with an 4 | # index when creating a custom index. 5 | # @param index [string] The name of the index. Defaults to the name of the 6 | # resource. 7 | # @param keys [string] The columns that the index is being created on. 8 | # @param keyspace [string] The name the keyspace that the index is to be associated 9 | # with. 10 | # @param options [string] Any options to be added to the index. 11 | # @param table [string] The name of the table that the index is to be associated with. 12 | define cassandra::schema::index ( 13 | $keyspace, 14 | $table, 15 | $ensure = present, 16 | $class_name = undef, 17 | $index = $title, 18 | $keys = undef, 19 | $options = undef, 20 | Boolean $use_scl = $cassandra::params::use_scl, 21 | String[1] $scl_name = $cassandra::params::scl_name, 22 | ) { 23 | include 'cassandra::schema' 24 | 25 | if $use_scl { 26 | $quote = '\"' 27 | } else { 28 | $quote = '"' 29 | } 30 | 31 | # Fully qualified index name. 32 | $fqin = "${keyspace}.${index}" 33 | # Fully qualified table name. 34 | $fqtn = "${keyspace}.${table}" 35 | 36 | $read_script = "DESC INDEX ${fqin}" 37 | $read_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${read_script}${quote} ${cassandra::schema::cqlsh_conn}" 38 | if $use_scl { 39 | $read_command = "/usr/bin/scl enable ${scl_name} \"${read_command_tmp}\"" 40 | } else { 41 | $read_command = $read_command_tmp 42 | } 43 | 44 | if $ensure == present { 45 | if $class_name != undef { 46 | $create_part1 = "CREATE CUSTOM INDEX IF NOT EXISTS ${index} ON ${keyspace}.${table}" 47 | } else { 48 | $create_part1 = "CREATE INDEX IF NOT EXISTS ${index} ON ${keyspace}.${table}" 49 | } 50 | 51 | if $class_name != undef { 52 | $create_part2 = "${create_part1} (${keys}) USING '${class_name}'" 53 | } else { 54 | $create_part2 = "${create_part1} (${keys})" 55 | } 56 | 57 | if $options != undef { 58 | $create_script = "${create_part2} WITH OPTIONS = ${options}" 59 | } else { 60 | $create_script = $create_part2 61 | } 62 | 63 | $create_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${create_script}${quote} ${cassandra::schema::cqlsh_conn}" 64 | if $use_scl { 65 | $create_command = "/usr/bin/scl enable ${scl_name} \"${create_command_tmp}\"" 66 | } else { 67 | $create_command = $create_command_tmp 68 | } 69 | 70 | exec { $create_command: 71 | unless => $read_command, 72 | require => Exec['cassandra::schema connection test'], 73 | } 74 | } elsif $ensure == absent { 75 | $delete_script = "DROP INDEX ${fqin}" 76 | $delete_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${delete_script}${quote} ${cassandra::schema::cqlsh_conn}" 77 | if $use_scl { 78 | $delete_command = "/usr/bin/scl enable ${scl_name} \"${delete_command_tmp}\"" 79 | } else { 80 | $delete_command = $delete_command_tmp 81 | } 82 | exec { $delete_command: 83 | onlyif => $read_command, 84 | require => Exec['cassandra::schema connection test'], 85 | } 86 | } else { 87 | fail("Unknown action (${ensure}) for ensure attribute.") 88 | } 89 | } 90 | -------------------------------------------------------------------------------- /manifests/schema/keyspace.pp: -------------------------------------------------------------------------------- 1 | # Create or drop keyspaces within the schema. 2 | # @param ensure [present|absent] Create or drop the keyspace. 3 | # @param durable_writes [boolean] When set to false, data written to the 4 | # keyspace bypasses the commit log. Be careful using this option 5 | # because you risk losing data. Set this attribute to false on a keyspace 6 | # using the SimpleStrategy. 7 | # @param keyspace_name [string] The name of the keyspace to be created. 8 | # @param replication_map [hash] Needed if the keyspace is to be present. 9 | # Optional if it is to be absent. 10 | # @example 11 | # $network_topology_strategy = { 12 | # keyspace_class => 'NetworkTopologyStrategy', 13 | # dc1 => 3, 14 | # dc2 => 2 15 | # } 16 | # @example 17 | # cassandra::schema::keyspace { 'mykeyspace': 18 | # replication_map => { 19 | # keyspace_class => 'SimpleStrategy', 20 | # replication_factor => 1, 21 | # }, 22 | # durable_writes => false, 23 | # } 24 | define cassandra::schema::keyspace ( 25 | $ensure = present, 26 | $durable_writes = true, 27 | $keyspace_name = $title, 28 | $replication_map = {}, 29 | Boolean $use_scl = $cassandra::params::use_scl, 30 | String[1] $scl_name = $cassandra::params::scl_name, 31 | ) { 32 | include 'cassandra::schema' 33 | 34 | if $use_scl { 35 | $quote = '\"' 36 | } else { 37 | $quote = '"' 38 | } 39 | 40 | $read_script = "DESC KEYSPACE ${keyspace_name}" 41 | $read_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${read_script}${quote} ${cassandra::schema::cqlsh_conn}" 42 | if $use_scl { 43 | $read_command = "/usr/bin/scl enable ${scl_name} \"${read_command_tmp}\"" 44 | } else { 45 | $read_command = $read_command_tmp 46 | } 47 | 48 | if $ensure == present { 49 | $keyspace_class = $replication_map[keyspace_class] 50 | 51 | case $keyspace_class { 52 | 'SimpleStrategy': { 53 | $replication_factor = $replication_map[replication_factor] 54 | $map_str = "{ 'class' : 'SimpleStrategy', 'replication_factor' : ${replication_factor} }" 55 | } 56 | 'NetworkTopologyStrategy': { 57 | $map_str1 = "{ 'class' : 'NetworkTopologyStrategy'" 58 | $new_map = prefix(delete($replication_map, 'keyspace_class'), "'") 59 | $map_str2 = join(join_keys_to_values($new_map, "': "), ', ') 60 | $map_str = "${map_str1}, ${map_str2} }" 61 | } 62 | default: { 63 | $msg_part1 = "Invalid or no class (${keyspace_class}) specified for" 64 | $msg_part2 = "keyspace ${keyspace_name}." 65 | fail("${msg_part1} ${msg_part2}") 66 | } 67 | } 68 | 69 | $create_script1 = "CREATE KEYSPACE IF NOT EXISTS ${keyspace_name}" 70 | $create_script2 = "WITH REPLICATION = ${map_str}" 71 | $create_script3 = "AND DURABLE_WRITES = ${durable_writes}" 72 | $create_script = "${create_script1} ${create_script2} ${create_script3}" 73 | $create_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${create_script}${quote} ${cassandra::schema::cqlsh_conn}" 74 | if $use_scl { 75 | $create_command = "/usr/bin/scl enable ${scl_name} \"${create_command_tmp}\"" 76 | } else { 77 | $create_command = $create_command_tmp 78 | } 79 | exec { $create_command: 80 | unless => $read_command, 81 | require => Exec['cassandra::schema connection test'], 82 | } 83 | } elsif $ensure == absent { 84 | $delete_script = "DROP KEYSPACE ${keyspace_name}" 85 | $delete_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${delete_script}${quote} ${cassandra::schema::cqlsh_conn}" 86 | if $use_scl { 87 | $delete_command = "/usr/bin/scl enable ${scl_name} \"${delete_command_tmp}\"" 88 | } else { 89 | $delete_command = $delete_command_tmp 90 | } 91 | exec { $delete_command: 92 | onlyif => $read_command, 93 | require => Exec['cassandra::schema connection test'], 94 | } 95 | } else { 96 | fail("Unknown action (${ensure}) for ensure attribute.") 97 | } 98 | } 99 | -------------------------------------------------------------------------------- /manifests/schema/permission.pp: -------------------------------------------------------------------------------- 1 | # Grant or revoke permissions. 2 | # To use this class, a suitable `authenticator` (e.g. PasswordAuthenticator) 3 | # and `authorizer` (e.g. CassandraAuthorizer) must be set in the Cassandra 4 | # class. 5 | # 6 | # WARNING: Specifying keyspace 'ALL' and 'ALL' for permissions at the same 7 | # time is not currently supported by this module. 8 | # 9 | # @param user_name [string] The name of the user who is to be granted or 10 | # revoked. 11 | # @param ensure [ present | absent ] Set to present to grant a permission or 12 | # absent to revoke it. 13 | # @param keyspace_name [string] The name of the keyspace to grant/revoke the 14 | # permissions on. If set to 'ALL' then the permission will be applied to 15 | # all of the keyspaces. 16 | # @param permission_name [string] Can be one of the following: 17 | # 18 | # * 'ALTER' - ALTER KEYSPACE, ALTER TABLE, CREATE INDEX, DROP INDEX. 19 | # * 'AUTHORIZE' - GRANT, REVOKE. 20 | # * 'CREATE' - CREATE KEYSPACE, CREATE TABLE. 21 | # * 'DROP' - DROP KEYSPACE, DROP TABLE. 22 | # * 'MODIFY' - INSERT, DELETE, UPDATE, TRUNCATE. 23 | # * 'SELECT' - SELECT. 24 | # 25 | # If the permission_name is set to 'ALL', this will set all of the specific 26 | # permissions listed. 27 | # @param table_name [string] The name of a table within the specified 28 | # keyspace. If left unspecified, the procedure will be applied to all 29 | # tables within the keyspace. 30 | define cassandra::schema::permission ( 31 | $user_name, 32 | $ensure = present, 33 | $keyspace_name = 'ALL', 34 | $permission_name = 'ALL', 35 | $table_name = undef, 36 | Boolean $use_scl = $cassandra::params::use_scl, 37 | String[1] $scl_name = $cassandra::params::scl_name, 38 | ) { 39 | include 'cassandra::schema' 40 | 41 | if $use_scl { 42 | $quote = '\"' 43 | } else { 44 | $quote = '"' 45 | } 46 | 47 | if upcase($keyspace_name) == 'ALL' and upcase($permission_name) == 'ALL' { 48 | fail('"ALL" keyspaces AND "ALL" permissions are mutually exclusive.') 49 | } elsif $table_name { 50 | $resource = "TABLE ${keyspace_name}.${table_name}" 51 | } elsif upcase($keyspace_name) == 'ALL' { 52 | $resource = 'ALL KEYSPACES' 53 | } else { 54 | $resource = "KEYSPACE ${keyspace_name}" 55 | } 56 | 57 | $read_script = "LIST ALL PERMISSIONS ON ${resource}" 58 | $upcase_permission_name = upcase($permission_name) 59 | $pattern = "\s${user_name} |\s*${user_name} |\s.*\s${upcase_permission_name}$" 60 | $read_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${read_script}${quote} ${cassandra::schema::cqlsh_conn} | grep '${pattern}'" 61 | if $use_scl { 62 | $read_command = "/usr/bin/scl enable ${scl_name} \"${read_command_tmp}\"" 63 | } else { 64 | $read_command = $read_command_tmp 65 | } 66 | 67 | if upcase($permission_name) == 'ALL' { 68 | cassandra::schema::permission { "${title} - ALTER": 69 | ensure => $ensure, 70 | user_name => $user_name, 71 | keyspace_name => $keyspace_name, 72 | permission_name => 'ALTER', 73 | table_name => $table_name, 74 | use_scl => $use_scl, 75 | scl_name => $scl_name, 76 | } 77 | 78 | cassandra::schema::permission { "${title} - AUTHORIZE": 79 | ensure => $ensure, 80 | user_name => $user_name, 81 | keyspace_name => $keyspace_name, 82 | permission_name => 'AUTHORIZE', 83 | table_name => $table_name, 84 | use_scl => $use_scl, 85 | scl_name => $scl_name, 86 | } 87 | 88 | # The CREATE permission is not relevant to tables. 89 | if !$table_name { 90 | cassandra::schema::permission { "${title} - CREATE": 91 | ensure => $ensure, 92 | user_name => $user_name, 93 | keyspace_name => $keyspace_name, 94 | permission_name => 'CREATE', 95 | table_name => $table_name, 96 | use_scl => $use_scl, 97 | scl_name => $scl_name, 98 | } 99 | } 100 | 101 | cassandra::schema::permission { "${title} - DROP": 102 | ensure => $ensure, 103 | user_name => $user_name, 104 | keyspace_name => $keyspace_name, 105 | permission_name => 'DROP', 106 | table_name => $table_name, 107 | use_scl => $use_scl, 108 | scl_name => $scl_name, 109 | } 110 | 111 | cassandra::schema::permission { "${title} - MODIFY": 112 | ensure => $ensure, 113 | user_name => $user_name, 114 | keyspace_name => $keyspace_name, 115 | permission_name => 'MODIFY', 116 | table_name => $table_name, 117 | use_scl => $use_scl, 118 | scl_name => $scl_name, 119 | } 120 | 121 | cassandra::schema::permission { "${title} - SELECT": 122 | ensure => $ensure, 123 | user_name => $user_name, 124 | keyspace_name => $keyspace_name, 125 | permission_name => 'SELECT', 126 | table_name => $table_name, 127 | use_scl => $use_scl, 128 | scl_name => $scl_name, 129 | } 130 | } elsif $ensure == present { 131 | $create_script = "GRANT ${permission_name} ON ${resource} TO ${user_name}" 132 | $create_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${create_script}${quote} ${cassandra::schema::cqlsh_conn}" 133 | if $use_scl { 134 | $create_command = "/usr/bin/scl enable ${scl_name} \"${create_command_tmp}\"" 135 | } else { 136 | $create_command = $create_command_tmp 137 | } 138 | 139 | exec { $create_script: 140 | command => $create_command, 141 | unless => $read_command, 142 | require => Exec['cassandra::schema connection test'], 143 | } 144 | } elsif $ensure == absent { 145 | $delete_script = "REVOKE ${permission_name} ON ${resource} FROM ${user_name}" 146 | $delete_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${delete_script}${quote} ${cassandra::schema::cqlsh_conn}" 147 | if $use_scl { 148 | $delete_command = "/usr/bin/scl enable ${scl_name} \"${delete_command_tmp}\"" 149 | } else { 150 | $delete_command = $delete_command_tmp 151 | } 152 | 153 | exec { $delete_script: 154 | command => $delete_command, 155 | onlyif => $read_command, 156 | require => Exec['cassandra::schema connection test'], 157 | } 158 | } else { 159 | fail("Unknown action (${ensure}) for ensure attribute.") 160 | } 161 | } 162 | -------------------------------------------------------------------------------- /manifests/schema/table.pp: -------------------------------------------------------------------------------- 1 | # Create or drop tables within the schema. 2 | # @param keyspace [string] The name of the keyspace. 3 | # @param columns [hash] A hash of the columns to be placed in the table. 4 | # Optional if the table is to be absent. 5 | # @param ensure [present|absent] Ensure a keyspace is created or dropped. 6 | # @param options [array] Options to be added to the table creation. 7 | # @param table [string] The name of the table. Defaults to the name of the 8 | # resource. 9 | # @example 10 | # cassandra::schema::table { 'users': 11 | # keyspace => 'mykeyspace', 12 | # columns => { 13 | # 'userid' => 'int', 14 | # 'fname' => 'text', 15 | # 'lname' => 'text', 16 | # 'PRIMARY KEY' => '(userid)', 17 | # }, 18 | # } 19 | define cassandra::schema::table ( 20 | $keyspace, 21 | $ensure = present, 22 | $columns = {}, 23 | $options = [], 24 | $table = $title, 25 | Boolean $use_scl = $cassandra::params::use_scl, 26 | String[1] $scl_name = $cassandra::params::scl_name, 27 | ) { 28 | include 'cassandra::schema' 29 | 30 | if $use_scl { 31 | $quote = '\"' 32 | } else { 33 | $quote = '"' 34 | } 35 | 36 | $read_script = "DESC TABLE ${keyspace}.${table}" 37 | $read_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${read_script}${quote} ${cassandra::schema::cqlsh_conn}" 38 | if $use_scl { 39 | $read_command = "/usr/bin/scl enable ${scl_name} \"${read_command_tmp}\"" 40 | } else { 41 | $read_command = $read_command_tmp 42 | } 43 | 44 | if $ensure == present { 45 | $create_script1 = "CREATE TABLE IF NOT EXISTS ${keyspace}.${table}" 46 | $cols_def = join(join_keys_to_values($columns, ' '), ', ') 47 | $cols_def_rm_collection_type = delete($cols_def, 'COLLECTION-TYPE ') 48 | 49 | if count($options) > 0 { 50 | $options_def = join($options, ' AND ') 51 | $create_script = "${create_script1} (${cols_def_rm_collection_type}) WITH ${options_def}" 52 | } else { 53 | $create_script = "${create_script1} (${cols_def_rm_collection_type})" 54 | } 55 | 56 | $create_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${create_script}${quote} ${cassandra::schema::cqlsh_conn}" 57 | if $use_scl { 58 | $create_command = "/usr/bin/scl enable ${scl_name} \"${create_command_tmp}\"" 59 | } else { 60 | $create_command = $create_command_tmp 61 | } 62 | exec { $create_command: 63 | unless => $read_command, 64 | require => Exec['cassandra::schema connection test'], 65 | } 66 | } elsif $ensure == absent { 67 | $delete_script = "DROP TABLE IF EXISTS ${keyspace}.${table}" 68 | $delete_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${delete_script}${quote} ${cassandra::schema::cqlsh_conn}" 69 | if $use_scl { 70 | $delete_command = "/usr/bin/scl enable ${scl_name} \"${delete_command_tmp}\"" 71 | } else { 72 | $delete_command = $delete_command_tmp 73 | } 74 | exec { $delete_command: 75 | onlyif => $read_command, 76 | require => Exec['cassandra::schema connection test'], 77 | } 78 | } else { 79 | fail("Unknown action (${ensure}) for ensure attribute.") 80 | } 81 | } 82 | -------------------------------------------------------------------------------- /manifests/schema/user.pp: -------------------------------------------------------------------------------- 1 | # Create or drop users. 2 | # To use this class, a suitable `authenticator` (e.g. PasswordAuthenticator) 3 | # must be set in the Cassandra class. 4 | # @param ensure [ present | absent ] Valid values can be **present** to 5 | # ensure a user is created, or **absent** to remove the user if it exists. 6 | # @param password [string] A password for the user. 7 | # @param superuser [boolean] If the user is to be a super-user on the system. 8 | # @param login [boolean] Allows the role to log in. 9 | # @param user_name [string] The name of the user. 10 | # @example 11 | # cassandra::schema::user { 'akers': 12 | # password => 'Niner2', 13 | # superuser => true, 14 | # } 15 | # 16 | # cassandra::schema::user { 'lucan': 17 | # ensure => absent, 18 | # } 19 | define cassandra::schema::user ( 20 | $ensure = present, 21 | $login = true, 22 | $password = undef, 23 | $superuser = false, 24 | $user_name = $title, 25 | Boolean $use_scl = $cassandra::params::use_scl, 26 | String[1] $scl_name = $cassandra::params::scl_name, 27 | ) { 28 | include 'cassandra::schema' 29 | 30 | if $use_scl { 31 | $quote = '\"' 32 | } else { 33 | $quote = '"' 34 | } 35 | 36 | if $facts['cassandrarelease'] != undef { 37 | if versioncmp($facts['cassandrarelease'], '2.2') < 0 { 38 | $operate_with_roles = false 39 | } else { 40 | $operate_with_roles = true 41 | } 42 | } else { 43 | $operate_with_roles = false 44 | } 45 | 46 | if $operate_with_roles { 47 | $read_script = 'LIST ROLES' 48 | } else { 49 | $read_script = 'LIST USERS' 50 | } 51 | $str_match = '\s' 52 | $read_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${read_script}${quote} ${cassandra::schema::cqlsh_conn} | grep '${str_match}*${user_name} |'" 53 | if $use_scl { 54 | $read_command = "/usr/bin/scl enable ${scl_name} \"${read_command_tmp}\"" 55 | } else { 56 | $read_command = $read_command_tmp 57 | } 58 | 59 | if $ensure == present { 60 | if $operate_with_roles { 61 | # we are running cassandra > 2.2 62 | $create_script1 = "CREATE ROLE IF NOT EXISTS ${user_name}" 63 | 64 | if $password != undef { 65 | $create_script2 = "${create_script1} WITH PASSWORD = '${password}'" 66 | } else { 67 | $create_script2 = $create_script1 68 | } 69 | 70 | if $superuser { 71 | if $password != undef { 72 | $create_script3 = "${create_script2} AND SUPERUSER = true" 73 | } else { 74 | $create_script3 = "${create_script2} WITH SUPERUSER = true" 75 | } 76 | } else { 77 | $create_script3 = $create_script2 78 | } 79 | 80 | if $login { 81 | if $superuser or $password != undef { 82 | $create_script = "${create_script3} AND LOGIN = true" 83 | } 84 | else { 85 | $create_script = "${create_script3} WITH LOGIN = true" 86 | } 87 | } else { 88 | $create_script = $create_script3 89 | } 90 | } else { 91 | $create_script1 = "CREATE USER IF NOT EXISTS ${user_name}" 92 | 93 | if $password != undef { 94 | $create_script2 = "${create_script1} WITH PASSWORD '${password}'" 95 | } else { 96 | $create_script2 = $create_script1 97 | } 98 | 99 | if $superuser { 100 | $create_script = "${create_script2} SUPERUSER" 101 | } else { 102 | $create_script = "${create_script2} NOSUPERUSER" 103 | } 104 | } 105 | 106 | $create_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${create_script}${quote} ${cassandra::schema::cqlsh_conn}" 107 | if $use_scl { 108 | $create_command = "/usr/bin/scl enable ${scl_name} \"${create_command_tmp}\"" 109 | } else { 110 | $create_command = $create_command_tmp 111 | } 112 | exec { "Create user (${user_name})": 113 | command => $create_command, 114 | unless => $read_command, 115 | require => Exec['cassandra::schema connection test'], 116 | } 117 | } elsif $ensure == absent { 118 | if $operate_with_roles { 119 | $delete_script = "DROP ROLE ${user_name}" 120 | } else { 121 | $delete_script = "DROP USER ${user_name}" 122 | } 123 | $delete_command_tmp = "${cassandra::schema::cqlsh_opts} -e ${quote}${delete_script}${quote} ${cassandra::schema::cqlsh_conn}" 124 | if $use_scl { 125 | $delete_command = "/usr/bin/scl enable ${scl_name} \"${delete_command_tmp}\"" 126 | } else { 127 | $delete_command = $delete_command_tmp 128 | } 129 | exec { "Delete user (${user_name})": 130 | command => $delete_command, 131 | onlyif => $read_command, 132 | require => Exec['cassandra::schema connection test'], 133 | } 134 | } else { 135 | fail("Unknown action (${ensure}) for ensure attribute.") 136 | } 137 | } 138 | -------------------------------------------------------------------------------- /manifests/system/swapoff.pp: -------------------------------------------------------------------------------- 1 | # Disable swap on the node as suggested at 2 | # http://docs.datastax.com/en/landing_page/doc/landing_page/recommendedSettingsLinux.html 3 | # @param device [string] If provided a mount resource will be created to 4 | # ensure that the device is absent from /etc/fstab to permanently disable swap. 5 | # @param mount [string] The name of the swap mount point. Ignored unless 6 | # `device` has been set. 7 | # @param path [string] The full path to the file to check if swap is enabled. 8 | # @see cassandra::params 9 | class cassandra::system::swapoff ( 10 | $device = undef, 11 | $mount = 'swap', 12 | $path = '/proc/swaps', 13 | ) { 14 | exec { 'Disable Swap': 15 | command => 'swapoff --all', 16 | onlyif => "grep -q '^/' ${path}", 17 | path => ['/bin', '/sbin', '/usr/bin', '/usr/sbin'], 18 | } 19 | 20 | if $device { 21 | mount { $mount: 22 | ensure => absent, 23 | device => $device, 24 | fstype => 'swap', 25 | } 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /manifests/system/sysctl.pp: -------------------------------------------------------------------------------- 1 | # Set Sysctl (kernel runtime parameters) as suggested in 2 | # http://docs.datastax.com/en/landing_page/doc/landing_page/recommendedSettingsLinux.html 3 | # 4 | # If any of the values is set into the target file, the sysctl command will 5 | # be called with the provided file name as an argument. 6 | # 7 | # @example Basic requirement 8 | # require cassandra::system::sysctl 9 | # 10 | # @param sysctl_args [string] Passed to the `sysctl` command 11 | # @param sysctl_file [string] Path to the file to insert the settings into. 12 | # @param net_core_optmem_max [integer] The value to set for 13 | # net.core.optmem_max 14 | # @param net_core_rmem_default [integer] The value to set for 15 | # net.core.rmem_default. 16 | # @param net_core_rmem_max [integer] The value to set for net_core_rmem_max. 17 | # @param net_core_wmem_default [integer] The value to set for 18 | # net.core.wmem_default. 19 | # @param net_core_wmem_max [integer] The value to set for net.core.wmem_max. 20 | # @param net_ipv4_tcp_rmem [string] The value to set for net.ipv4.tcp_rmem. 21 | # @param net_ipv4_tcp_wmem [string] The value to set for net.ipv4.tcp_wmem. 22 | # @param vm_max_map_count [integer] The value to set for vm.max_map_count. 23 | # @see cassandra::params 24 | class cassandra::system::sysctl ( 25 | $sysctl_args = '-p', 26 | $sysctl_file = $cassandra::params::sysctl_file, 27 | $net_core_optmem_max = 40960, 28 | $net_core_rmem_default = 16777216, 29 | $net_core_rmem_max = 16777216, 30 | $net_core_wmem_default = 16777216, 31 | $net_core_wmem_max = 16777216, 32 | $net_ipv4_tcp_rmem = $cassandra::params::net_ipv4_tcp_rmem, 33 | $net_ipv4_tcp_wmem = $cassandra::params::net_ipv4_tcp_wmem, 34 | $vm_max_map_count = 1048575, 35 | ) inherits cassandra::params { 36 | ini_setting { "net.core.rmem_max = ${net_core_rmem_max}": 37 | ensure => present, 38 | path => $sysctl_file, 39 | section => '', 40 | setting => 'net.core.rmem_max', 41 | value => $net_core_rmem_max, 42 | notify => Exec['Apply sysctl changes'], 43 | } 44 | 45 | ini_setting { "net.core.wmem_max = ${net_core_wmem_max}": 46 | ensure => present, 47 | path => $sysctl_file, 48 | section => '', 49 | setting => 'net.core.wmem_max', 50 | value => $net_core_wmem_max, 51 | notify => Exec['Apply sysctl changes'], 52 | } 53 | 54 | ini_setting { "net.core.rmem_default = ${net_core_rmem_default}": 55 | ensure => present, 56 | path => $sysctl_file, 57 | section => '', 58 | setting => 'net.core.rmem_default', 59 | value => $net_core_rmem_default, 60 | notify => Exec['Apply sysctl changes'], 61 | } 62 | 63 | ini_setting { "net.core.wmem_default = ${net_core_wmem_default}": 64 | ensure => present, 65 | path => $sysctl_file, 66 | section => '', 67 | setting => 'net.core.wmem_default', 68 | value => $net_core_wmem_default, 69 | notify => Exec['Apply sysctl changes'], 70 | } 71 | 72 | ini_setting { "net.core.optmem_max = ${net_core_optmem_max}": 73 | ensure => present, 74 | path => $sysctl_file, 75 | section => '', 76 | setting => 'net.core.optmem_max', 77 | value => $net_core_optmem_max, 78 | notify => Exec['Apply sysctl changes'], 79 | } 80 | 81 | ini_setting { "net.ipv4.tcp_rmem = ${net_ipv4_tcp_rmem}": 82 | ensure => present, 83 | path => $sysctl_file, 84 | section => '', 85 | setting => 'net.ipv4.tcp_rmem', 86 | value => $net_ipv4_tcp_rmem, 87 | notify => Exec['Apply sysctl changes'], 88 | } 89 | 90 | ini_setting { "net.ipv4.tcp_wmem = ${net_ipv4_tcp_wmem}": 91 | ensure => present, 92 | path => $sysctl_file, 93 | section => '', 94 | setting => 'net.ipv4.tcp_wmem', 95 | value => $net_ipv4_tcp_wmem, 96 | notify => Exec['Apply sysctl changes'], 97 | } 98 | 99 | ini_setting { "vm.max_map_count = ${vm_max_map_count}": 100 | ensure => present, 101 | path => $sysctl_file, 102 | section => '', 103 | setting => 'vm.max_map_count', 104 | value => $vm_max_map_count, 105 | notify => Exec['Apply sysctl changes'], 106 | } 107 | 108 | exec { 'Apply sysctl changes': 109 | command => "/sbin/sysctl ${sysctl_args} ${sysctl_file}", 110 | refreshonly => true, 111 | } 112 | } 113 | -------------------------------------------------------------------------------- /manifests/system/transparent_hugepage.pp: -------------------------------------------------------------------------------- 1 | # Disable Transparant Huge Pages as suggested in 2 | # http://docs.datastax.com/en/landing_page/doc/landing_page/recommendedSettingsLinux.html. 3 | # @param path [string] The full path to the file for checking/setting 4 | # if Transparent Hugepages is enabled. 5 | # @see cassandra::params 6 | class cassandra::system::transparent_hugepage ( 7 | $path = '/sys/kernel/mm/transparent_hugepage/defrag', 8 | ) inherits cassandra::params { 9 | exec { 'Disable Java Hugepages': 10 | command => "/bin/echo never > ${path}", 11 | path => ['/bin', '/usr/bin'], 12 | unless => "grep -q '\\[never\\]' ${path}", 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /metadata.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "puppet-cassandra", 3 | "version": "3.1.1-rc0", 4 | "author": "Vox Pupuli", 5 | "summary": "Installs Cassandra & DataStax Agent on RHEL/Ubuntu/Debian.", 6 | "license": "Apache-2.0", 7 | "source": "https://github.com/voxpupuli/puppet-cassandra", 8 | "project_page": "https://github.com/voxpupuli/puppet-cassandra", 9 | "issues_url": "https://github.com/voxpupuli/puppet-cassandra/issues", 10 | "tags": [ 11 | "Apache", 12 | "cassandra", 13 | "cluster", 14 | "database", 15 | "datastax", 16 | "datastax-agent", 17 | "nosql" 18 | ], 19 | "dependencies": [ 20 | { 21 | "name": "puppetlabs-apt", 22 | "version_requirement": ">= 2.0.0 < 11.0.0" 23 | }, 24 | { 25 | "name": "puppetlabs-firewall", 26 | "version_requirement": ">= 1.0.0 < 3.0.0" 27 | }, 28 | { 29 | "name": "puppetlabs-inifile", 30 | "version_requirement": ">= 1.5.0 < 5.0.0" 31 | }, 32 | { 33 | "name": "puppetlabs-stdlib", 34 | "version_requirement": ">= 3.0.0 < 10.0.0" 35 | } 36 | ], 37 | "operatingsystem_support": [ 38 | { 39 | "operatingsystem": "CentOS", 40 | "operatingsystemrelease": [ 41 | "7" 42 | ] 43 | }, 44 | { 45 | "operatingsystem": "OracleLinux", 46 | "operatingsystemrelease": [ 47 | "7" 48 | ] 49 | }, 50 | { 51 | "operatingsystem": "RedHat", 52 | "operatingsystemrelease": [ 53 | "7" 54 | ] 55 | }, 56 | { 57 | "operatingsystem": "Debian", 58 | "operatingsystemrelease": [ 59 | "8" 60 | ] 61 | }, 62 | { 63 | "operatingsystem": "Scientific", 64 | "operatingsystemrelease": [ 65 | "7" 66 | ] 67 | }, 68 | { 69 | "operatingsystem": "Ubuntu", 70 | "operatingsystemrelease": [ 71 | "20.04", 72 | "22.04" 73 | ] 74 | } 75 | ], 76 | "requirements": [ 77 | { 78 | "name": "puppet", 79 | "version_requirement": ">= 7.0.0 < 9.0.0" 80 | } 81 | ] 82 | } 83 | -------------------------------------------------------------------------------- /spec/acceptance/bootstrap_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper_acceptance' 2 | 3 | osfamily = fact('osfamily') 4 | roles = hosts[0]['roles'] 5 | t = TestManifests.new(roles, 0, 0) 6 | bootstrap_pp = t.bootstrap_pp() 7 | 8 | describe 'Test Entry Criteria' do 9 | it "Should work with no errors (#{osfamily})" do 10 | apply_manifest(bootstrap_pp, catch_failures: true) 11 | shell('[ -d /opt/rh/ruby200 ] && /usr/bin/gem install puppet -v 3.8.7 --no-rdoc --no-ri; true') 12 | end 13 | end 14 | -------------------------------------------------------------------------------- /spec/acceptance/cassandra_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper_acceptance' 2 | 3 | describe 'cassandra' do 4 | roles = hosts[0]['roles'] 5 | versions = [] 6 | versions.push(2.1) if roles.include? 'cassandra2' 7 | versions.push(2.2) if roles.include? 'cassandra2' 8 | versions.push(3.0) if roles.include? 'cassandra3' 9 | 10 | versions.each do |version| 11 | t = TestManifests.new(roles, version, fact('operatingsystemmajrelease')) 12 | 13 | describe "Cassandra #{version} installation." do 14 | # firewall_pp = t.firewall_pp() 15 | cassandra_install_pp = t.cassandra_install_pp 16 | 17 | it 'works with no errors' do 18 | apply_manifest(cassandra_install_pp, catch_failures: true) 19 | end 20 | 21 | it 'check code is idempotent' do 22 | expect(apply_manifest(cassandra_install_pp, 23 | catch_failures: true).exit_code).to be_zero 24 | end 25 | end 26 | 27 | describe service('cassandra') do 28 | it "check Cassandra-#{version} is running and enabled" do 29 | is_expected.to be_running 30 | is_expected.to be_enabled 31 | end 32 | end 33 | 34 | if fact('osfamily') == 'RedHat' 35 | describe service('datastax-agent') do 36 | it 'check service status' do 37 | is_expected.to be_running 38 | is_expected.to be_enabled 39 | end 40 | end 41 | end 42 | 43 | describe "Create schema for #{version}." do 44 | it 'works with no errors' do 45 | apply_manifest(t.schema_create_pp, catch_failures: true) 46 | end 47 | 48 | if version != 2.1 49 | it 'check code is idempotent' do 50 | expect(apply_manifest(t.schema_create_pp, catch_failures: true).exit_code).to be_zero 51 | end 52 | end 53 | end 54 | 55 | describe "Schema drop type for #{version}." do 56 | it 'works with no errors' do 57 | apply_manifest(t.schema_drop_type_pp, catch_failures: true) 58 | end 59 | 60 | it 'check code is idempotent' do 61 | expect(apply_manifest(t.schema_drop_type_pp, catch_failures: true).exit_code).to be_zero 62 | end 63 | end 64 | 65 | describe "Revoke permissions for #{version}." do 66 | it 'works with no errors' do 67 | apply_manifest(t.permissions_revoke_pp, catch_failures: true) 68 | end 69 | 70 | it 'check code is idempotent' do 71 | expect(apply_manifest(t.permissions_revoke_pp, catch_failures: true).exit_code).to be_zero 72 | end 73 | end 74 | 75 | describe "Drop user for #{version}" do 76 | it 'works with no errors' do 77 | apply_manifest(t.schema_drop_user_pp, catch_failures: true) 78 | end 79 | 80 | it 'check code is idempotent' do 81 | expect(apply_manifest(t.schema_drop_user_pp, catch_failures: true).exit_code).to be_zero 82 | end 83 | end 84 | 85 | describe "Drop index for #{version}" do 86 | it 'works with no errors' do 87 | apply_manifest(t.schema_drop_index_pp, catch_failures: true) 88 | end 89 | 90 | it 'check code is idempotent' do 91 | expect(apply_manifest(t.schema_drop_index_pp, catch_failures: true).exit_code).to be_zero 92 | end 93 | end 94 | 95 | describe "Drop table for #{version}" do 96 | it 'works with no errors' do 97 | apply_manifest(t.schema_drop_table_pp, catch_failures: true) 98 | end 99 | 100 | it 'check code is idempotent' do 101 | expect(apply_manifest(t.schema_drop_table_pp, catch_failures: true).exit_code).to be_zero 102 | end 103 | end 104 | 105 | describe "Drop keyspace for #{version}" do 106 | it 'works with no errors' do 107 | apply_manifest(t.schema_drop_keyspace_pp, catch_failures: true) 108 | end 109 | 110 | it 'check code is idempotent' do 111 | expect(apply_manifest(t.schema_drop_keyspace_pp, catch_failures: true).exit_code).to be_zero 112 | end 113 | end 114 | 115 | describe "Facts Tests for #{version}" do 116 | it 'works with no errors' do 117 | apply_manifest(t.facts_testing_pp, catch_failures: true) 118 | end 119 | end 120 | 121 | next unless version != 3.0 122 | describe "Uninstall #{version}." do 123 | it 'works with no errors' do 124 | apply_manifest(t.cassandra_uninstall_pp, catch_failures: true) 125 | end 126 | end 127 | end 128 | end 129 | -------------------------------------------------------------------------------- /spec/acceptance/hieradata/environments/production/data/common.yaml: -------------------------------------------------------------------------------- 1 | --- 2 | ############################################################################# 3 | # common.yaml 4 | # =========== 5 | # 6 | # A file for hiera data that is relevant to all test nodes. 7 | ############################################################################# 8 | 9 | cassandra::baseline_settings: 10 | authenticator: AllowAllAuthenticator 11 | authorizer: AllowAllAuthorizer 12 | auto_snapshot: true 13 | batch_size_warn_threshold_in_kb: 5 14 | batchlog_replay_throttle_in_kb: 1024 15 | cas_contention_timeout_in_ms: 1000 16 | client_encryption_options: 17 | enabled: false 18 | keystore: conf/.keystore 19 | keystore_password: cassandra 20 | cluster_name: "Test Cluster" 21 | column_index_size_in_kb: 64 22 | commit_failure_policy: stop 23 | commitlog_directory: /var/lib/cassandra/commitlog 24 | commitlog_segment_size_in_mb: 32 25 | commitlog_sync: periodic 26 | commitlog_sync_period_in_ms: 10000 27 | compaction_throughput_mb_per_sec: 16 28 | concurrent_counter_writes: 32 29 | concurrent_reads: 32 30 | concurrent_writes: 32 31 | counter_cache_save_period: 7200 32 | counter_write_request_timeout_in_ms: 5000 33 | cross_node_timeout: false 34 | data_file_directories: 35 | - /var/lib/cassandra/data 36 | disk_failure_policy: stop 37 | dynamic_snitch_badness_threshold: 0.1 38 | dynamic_snitch_reset_interval_in_ms: 600000 39 | dynamic_snitch_update_interval_in_ms: 100 40 | endpoint_snitch: SimpleSnitch 41 | hinted_handoff_enabled: true 42 | hinted_handoff_throttle_in_kb: 1024 43 | incremental_backups: false 44 | index_summary_resize_interval_in_minutes: 60 45 | inter_dc_tcp_nodelay: false 46 | internode_compression: all 47 | key_cache_save_period: 14400 48 | listen_address: localhost 49 | max_hint_window_in_ms: 10800000 50 | max_hints_delivery_threads: 2 51 | memtable_allocation_type: heap_buffers 52 | native_transport_port: 9042 53 | num_tokens: 256 54 | partitioner: org.apache.cassandra.dht.Murmur3Partitioner 55 | permissions_validity_in_ms: 2000 56 | range_request_timeout_in_ms: 10000 57 | read_request_timeout_in_ms: 5000 58 | request_scheduler: org.apache.cassandra.scheduler.NoScheduler 59 | request_timeout_in_ms: 10000 60 | row_cache_save_period: 0 61 | row_cache_size_in_mb: 0 62 | rpc_address: localhost 63 | rpc_keepalive: true 64 | rpc_port: 9160 65 | rpc_server_type: sync 66 | saved_caches_directory: /var/lib/cassandra/saved_caches 67 | seed_provider: 68 | - class_name: org.apache.cassandra.locator.SimpleSeedProvider 69 | parameters: 70 | - seeds: "127.0.0.1" 71 | server_encryption_options: 72 | internode_encryption: none 73 | keystore: conf/.keystore 74 | keystore_password: cassandra 75 | truststore: conf/.truststore 76 | truststore_password: cassandra 77 | snapshot_before_compaction: false 78 | ssl_storage_port: 7001 79 | sstable_preemptive_open_interval_in_mb: 50 80 | start_native_transport: true 81 | start_rpc: true 82 | storage_port: 7000 83 | thrift_framed_transport_size_in_mb: 15 84 | tombstone_failure_threshold: 100000 85 | tombstone_warn_threshold: 1000 86 | trickle_fsync: false 87 | trickle_fsync_interval_in_kb: 10240 88 | truncate_request_timeout_in_ms: 60000 89 | write_request_timeout_in_ms: 2000 90 | cassandra::cassandra_9822: true 91 | cassandra::dc: LON 92 | 93 | cassandra::dse: 94 | file_lines: 95 | 'Set HADOOP_LOG_DIR directory': 96 | ensure: present 97 | path: '/etc/dse/dse-env.sh' 98 | line: 'export HADOOP_LOG_DIR=/var/log/hadoop' 99 | match: '^# export HADOOP_LOG_DIR=' 100 | 'Set DSE_HOME': 101 | ensure: present 102 | path: '/etc/dse/dse-env.sh' 103 | line: 'export DSE_HOME=/usr/share/dse' 104 | match: '^#export DSE_HOME' 105 | settings: 106 | ldap_options: 107 | server_host: localhost 108 | server_port: 389 109 | search_dn: 'cn=Admin' 110 | search_password: 'secret' 111 | use_ssl: false 112 | use_tls: false 113 | truststore_type: jks 114 | user_search_base: 'ou=users,dc=example,dc=com' 115 | user_search_filter: '(uid={0})' 116 | credentials_validity_in_ms: 0 117 | connection_pool: 118 | max_active: 8 119 | max_idle: 8 120 | 121 | cassandra::rack: R101 122 | cassandra::service_ensure: running 123 | -------------------------------------------------------------------------------- /spec/acceptance/hieradata/environments/production/data/modules/cassandra.yaml: -------------------------------------------------------------------------------- 1 | --- 2 | cassandra::settings: 3 | authenticator: PasswordAuthenticator 4 | authorizer: CassandraAuthorizer 5 | cluster_name: BEAKER 6 | endpoint_snitch: GossipingPropertyFileSnitch 7 | -------------------------------------------------------------------------------- /spec/acceptance/hieradata/environments/production/data/osfamily/Debian/12.04.yaml: -------------------------------------------------------------------------------- 1 | --- 2 | cassandra::java::aptkey: 3 | OpenJDK: 4 | id: 'DA1A4A13543B466853BAF164EB9B1D8886F44E2A' 5 | server: 'keyserver.ubuntu.com' 6 | 7 | cassandra::java::aptsource: 8 | OpenJDK: 9 | comment: 'OpenJDK builds (all archs)' 10 | location: 'http://ppa.launchpad.net/openjdk-r/ppa/ubuntu' 11 | release: 'precise' 12 | 13 | cassandra::java::package_name: 'openjdk-8-jdk' 14 | -------------------------------------------------------------------------------- /spec/acceptance/hieradata/environments/production/data/osfamily/Debian/16.04.yaml: -------------------------------------------------------------------------------- 1 | --- 2 | cassandra::hints_directory_mode: '0770' 3 | 4 | cassandra::java::aptkey: 5 | OpenJDK: 6 | id: 'DA1A4A13543B466853BAF164EB9B1D8886F44E2A' 7 | server: 'keyserver.ubuntu.com' 8 | 9 | cassandra::java::aptsource: 10 | OpenJDK: 11 | comment: 'OpenJDK builds (all archs)' 12 | location: 'http://ppa.launchpad.net/openjdk-r/ppa/ubuntu' 13 | release: 'xenial' 14 | 15 | cassandra::java::package_name: 'openjdk-8-jdk' 16 | -------------------------------------------------------------------------------- /spec/acceptance/hieradata/environments/production/data/osfamily/Debian/7.yaml: -------------------------------------------------------------------------------- 1 | --- 2 | cassandra::java::aptkey: 3 | ZuluJDK: 4 | id: '27BC0C8CB3D81623F59BDADCB1998361219BD9C9' 5 | server: 'keyserver.ubuntu.com' 6 | 7 | cassandra::java::aptsource: 8 | ZuluJDK: 9 | location: 'http://repos.azulsystems.com/debian' 10 | comment: 'Zulu OpenJDK 8 for Debian' 11 | release: 'stable' 12 | repos: 'main' 13 | 14 | cassandra::java::package_name: 'zulu-8' 15 | 16 | cassandra::system::swapoff::device: '/dev/mapper/localhost--vg-swap_1' 17 | cassandra::system::swapoff::mount: 'none' 18 | -------------------------------------------------------------------------------- /spec/acceptance/hieradata/environments/production/data/osfamily/Debian/8.yaml: -------------------------------------------------------------------------------- 1 | --- 2 | cassandra::java::aptkey: 3 | ZuluJDK: 4 | id: '27BC0C8CB3D81623F59BDADCB1998361219BD9C9' 5 | server: 'keyserver.ubuntu.com' 6 | 7 | cassandra::java::aptsource: 8 | ZuluJDK: 9 | location: 'http://repos.azulsystems.com/debian' 10 | comment: 'Zulu OpenJDK 8 for Debian' 11 | release: 'stable' 12 | repos: 'main' 13 | 14 | cassandra::java::package_name: 'zulu-8' 15 | -------------------------------------------------------------------------------- /spec/classes/apache_repo_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | describe 'cassandra::apache_repo' do 3 | context 'On a RedHat OS with defaults for all parameters' do 4 | let :facts do 5 | { 6 | osfamily: 'RedHat', 7 | os: { 8 | 'family' => 'RedHat', 9 | 'release' => { 10 | 'full' => '7.6.1810', 11 | 'major' => '7', 12 | 'minor' => '6' 13 | } 14 | } 15 | } 16 | end 17 | 18 | let :params do 19 | { 20 | release: '311x' 21 | } 22 | end 23 | 24 | it do 25 | is_expected.to have_resource_count(1) 26 | 27 | is_expected.to contain_class('cassandra::apache_repo').only_with( 28 | 'descr' => 'Repo for Apache Cassandra', 29 | 'key_id' => 'A26E528B271F19B9E5D8E19EA278B781FE4B2BDA', 30 | 'key_url' => 'https://www.apache.org/dist/cassandra/KEYS', 31 | 'release' => '311x' 32 | ) 33 | 34 | is_expected.to contain_yumrepo('cassandra_apache').with( 35 | ensure: 'present', 36 | descr: 'Repo for Apache Cassandra', 37 | baseurl: 'http://www.apache.org/dist/cassandra/redhat/311x', 38 | enabled: 1, 39 | gpgcheck: 1, 40 | gpgkey: 'https://www.apache.org/dist/cassandra/KEYS' 41 | ) 42 | end 43 | end 44 | 45 | context 'On a Debian OS with defaults for all parameters' do 46 | let :facts do 47 | { 48 | osfamily: 'Debian', 49 | lsbdistid: 'Debian', 50 | lsbdistrelease: '9', 51 | os: { 52 | 'family' => 'Debian', 53 | 'name' => 'Debian', 54 | 'release' => { 55 | 'full' => '9.9', 56 | 'major' => '9', 57 | 'minor' => '9' 58 | } 59 | } 60 | } 61 | end 62 | 63 | it do 64 | is_expected.to contain_class('apt') 65 | is_expected.to contain_class('apt::update') 66 | 67 | is_expected.to contain_apt__key('apache.cassandra').with( 68 | id: 'A26E528B271F19B9E5D8E19EA278B781FE4B2BDA', 69 | source: 'https://www.apache.org/dist/cassandra/KEYS' 70 | ) 71 | 72 | is_expected.to contain_apt__source('cassandra.sources').with( 73 | location: 'http://www.apache.org/dist/cassandra/debian', 74 | comment: 'Repo for Apache Cassandra', 75 | release: 'main', 76 | include: { 'src' => false } 77 | ).that_notifies('Exec[update-apache-cassandra-repo]') 78 | 79 | is_expected.to contain_exec('update-apache-cassandra-repo').with( 80 | refreshonly: true, 81 | command: '/bin/true' 82 | ) 83 | end 84 | end 85 | end 86 | -------------------------------------------------------------------------------- /spec/classes/datastax_agent_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandra::datastax_agent' do 4 | context 'Test for cassandra::datastax_agent with defaults (RedHat).' do 5 | let :facts do 6 | { 7 | osfamily: 'RedHat', 8 | operatingsystemmajrelease: '6', 9 | os: { 10 | 'name' => 'RedHat', 11 | 'family' => 'RedHat', 12 | 'release' => { 13 | 'full' => '6.10', 14 | 'major' => '6', 15 | 'minor' => '10' 16 | } 17 | } 18 | } 19 | end 20 | 21 | it do 22 | is_expected.to compile.with_all_deps 23 | 24 | is_expected.to have_resource_count(10) 25 | 26 | is_expected.to contain_class('cassandra::datastax_agent').with( 27 | 'address_config_file' => '/var/lib/datastax-agent/conf/address.yaml', 28 | 'defaults_file' => '/etc/default/datastax-agent', 29 | 'package_ensure' => 'present', 30 | 'package_name' => 'datastax-agent', 31 | 'service_ensure' => 'running', 32 | 'service_enable' => true, 33 | 'service_name' => 'datastax-agent', 34 | 'settings' => {} 35 | ) 36 | 37 | is_expected.to contain_package('datastax-agent').with( 38 | ensure: 'present', 39 | notify: 'Exec[datastax_agent_reload_systemctl]' 40 | ).that_notifies('Exec[datastax_agent_reload_systemctl]') 41 | 42 | is_expected.to contain_exec('datastax_agent_reload_systemctl').only_with( 43 | command: '/usr/bin/systemctl daemon-reload', 44 | onlyif: 'test -x /usr/bin/systemctl', 45 | path: ['/usr/bin', '/bin'], 46 | refreshonly: true, 47 | notify: 'Service[datastax-agent]' 48 | ).that_notifies('Service[datastax-agent]') 49 | 50 | is_expected.to contain_file('/var/lib/datastax-agent/conf/address.yaml'). 51 | with( 52 | owner: 'cassandra', 53 | group: 'cassandra', 54 | mode: '0644' 55 | ).that_requires('Package[datastax-agent]') 56 | 57 | is_expected.to contain_service('datastax-agent').only_with( 58 | ensure: 'running', 59 | enable: true, 60 | name: 'datastax-agent' 61 | ) 62 | end 63 | end 64 | 65 | context 'Test for cassandra::datastax_agent with defaults (Debian).' do 66 | let :facts do 67 | { 68 | osfamily: 'Debian', 69 | operatingsystemmajrelease: '7', 70 | os: { 71 | 'family' => 'Debian', 72 | 'release' => { 73 | 'full' => '7.8', 74 | 'major' => '7', 75 | 'minor' => '8' 76 | } 77 | } 78 | } 79 | end 80 | 81 | it do 82 | is_expected.to contain_exec('datastax_agent_reload_systemctl').with( 83 | command: '/bin/systemctl daemon-reload', 84 | onlyif: 'test -x /bin/systemctl', 85 | path: ['/usr/bin', '/bin'], 86 | refreshonly: true 87 | ).that_notifies('Service[datastax-agent]') 88 | end 89 | end 90 | 91 | context 'Test that the JAVA_HOME can be set.' do 92 | let :facts do 93 | { 94 | osfamily: 'Debian', 95 | operatingsystemmajrelease: '7', 96 | os: { 97 | 'family' => 'Debian', 98 | 'release' => { 99 | 'full' => '7.8', 100 | 'major' => '7', 101 | 'minor' => '8' 102 | } 103 | } 104 | } 105 | end 106 | 107 | let :params do 108 | { 109 | java_home: '/usr/lib/jvm/java-8-oracle' 110 | } 111 | end 112 | 113 | it do 114 | is_expected.to contain_ini_setting('java_home').with( 115 | ensure: 'present', 116 | path: '/etc/default/datastax-agent', 117 | section: '', 118 | key_val_separator: '=', 119 | setting: 'JAVA_HOME', 120 | value: '/usr/lib/jvm/java-8-oracle' 121 | ).that_notifies('Service[datastax-agent]') 122 | end 123 | end 124 | 125 | context 'Test settings.' do 126 | let :facts do 127 | { 128 | osfamily: 'Debian', 129 | operatingsystemmajrelease: '7', 130 | os: { 131 | 'family' => 'Debian', 132 | 'release' => { 133 | 'full' => '7.8', 134 | 'major' => '7', 135 | 'minor' => '8' 136 | } 137 | } 138 | } 139 | end 140 | 141 | let :params do 142 | { 143 | settings: { 144 | 'agent_alias' => { 145 | 'setting' => 'agent_alias', 146 | 'value' => 'foobar' 147 | }, 148 | 'stomp_interface' => { 149 | 'setting' => 'stomp_interface', 150 | 'value' => 'localhost' 151 | }, 152 | 'async_pool_size' => { 153 | 'ensure' => 'absent' 154 | } 155 | } 156 | } 157 | end 158 | 159 | it do 160 | is_expected.to have_resource_count(16) 161 | end 162 | end 163 | end 164 | -------------------------------------------------------------------------------- /spec/classes/datastax_repo_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | describe 'cassandra::datastax_repo' do 3 | context 'On a RedHat OS with defaults for all parameters' do 4 | let :facts do 5 | { 6 | osfamily: 'RedHat', 7 | os: { 8 | 'family' => 'RedHat', 9 | 'release' => { 10 | 'full' => '7.6.1810', 11 | 'major' => '7', 12 | 'minor' => '6' 13 | } 14 | } 15 | } 16 | end 17 | 18 | it do 19 | is_expected.to have_resource_count(1) 20 | 21 | is_expected.to contain_class('cassandra::datastax_repo').only_with( 22 | 'descr' => 'DataStax Repo for Apache Cassandra', 23 | 'key_id' => '7E41C00F85BFC1706C4FFFB3350200F2B999A372', 24 | 'key_url' => 'http://debian.datastax.com/debian/repo_key', 25 | 'release' => 'stable' 26 | ) 27 | 28 | is_expected.to contain_yumrepo('datastax').with( 29 | ensure: 'present', 30 | descr: 'DataStax Repo for Apache Cassandra', 31 | baseurl: 'http://rpm.datastax.com/community', 32 | enabled: 1, 33 | gpgcheck: 0 34 | ) 35 | end 36 | end 37 | 38 | context 'On a Debian OS with defaults for all parameters' do 39 | let :facts do 40 | { 41 | osfamily: 'Debian', 42 | lsbdistid: 'Debian', 43 | lsbdistrelease: '9', 44 | os: { 45 | 'name' => 'Debian', 46 | 'family' => 'Debian', 47 | 'release' => { 48 | 'major' => '9', 49 | 'minor' => '9', 50 | 'full' => '9.9' 51 | } 52 | } 53 | } 54 | end 55 | 56 | it do 57 | is_expected.to contain_class('apt') 58 | is_expected.to contain_class('apt::update') 59 | 60 | is_expected.to contain_apt__key('datastaxkey').with( 61 | id: '7E41C00F85BFC1706C4FFFB3350200F2B999A372', 62 | source: 'http://debian.datastax.com/debian/repo_key' 63 | ) 64 | 65 | is_expected.to contain_apt__source('datastax').with( 66 | location: 'http://debian.datastax.com/community', 67 | comment: 'DataStax Repo for Apache Cassandra', 68 | release: 'stable', 69 | include: { 'src' => false } 70 | ).that_notifies('Exec[update-cassandra-repos]') 71 | 72 | is_expected.to contain_exec('update-cassandra-repos').with( 73 | refreshonly: true, 74 | command: '/bin/true' 75 | ) 76 | end 77 | end 78 | end 79 | -------------------------------------------------------------------------------- /spec/classes/dse_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | describe 'cassandra::dse' do 3 | context 'with defaults for all parameters' do 4 | let :facts do 5 | { 6 | osfamily: 'RedHat', 7 | operatingsystemmajrelease: 7, 8 | os: { 9 | 'family' => 'RedHat', 10 | 'name' => 'Redhat', 11 | 'release' => { 12 | 'full' => '7.6.1810', 13 | 'major' => '7', 14 | 'minor' => '6' 15 | } 16 | } 17 | } 18 | end 19 | 20 | it do 21 | is_expected.to have_resource_count(13) 22 | is_expected.to contain_class('cassandra') 23 | 24 | is_expected.to contain_class('cassandra::dse').with( 25 | config_file_mode: '0644', 26 | config_file: '/etc/dse/dse.yaml' 27 | ) 28 | end 29 | end 30 | end 31 | -------------------------------------------------------------------------------- /spec/classes/firewall_ports_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | describe 'cassandra::firewall_ports' do 3 | context 'Run with defaults.' do 4 | it do 5 | is_expected.to have_resource_count(2) 6 | is_expected.to contain_firewall('200 - Cassandra (Public) - 0.0.0.0/0') 7 | 8 | is_expected.to contain_class('cassandra::firewall_ports').with( 9 | client_ports: [9042, 9160], 10 | client_subnets: ['0.0.0.0/0'], 11 | inter_node_ports: [7000, 7001, 7199], 12 | inter_node_subnets: ['0.0.0.0/0'], 13 | public_ports: [8888], 14 | public_subnets: ['0.0.0.0/0'], 15 | ssh_port: 22, 16 | opscenter_ports: [9042, 9160, 61_620, 61_621], 17 | opscenter_subnets: ['0.0.0.0/0'] 18 | ) 19 | 20 | is_expected.to contain_cassandra__private__firewall_ports__rule('200_Public_0.0.0.0/0').with(ports: [8888, 22]) 21 | end 22 | end 23 | end 24 | -------------------------------------------------------------------------------- /spec/classes/java_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | describe 'cassandra::java' do 3 | context 'On a RedHat OS with defaults for all parameters' do 4 | let :facts do 5 | { 6 | operatingsystemmajrelease: '7', 7 | osfamily: 'RedHat', 8 | os: { 9 | 'family' => 'RedHat', 10 | 'release' => { 11 | 'full' => '7.6.1810', 12 | 'major' => '7', 13 | 'minor' => '6' 14 | } 15 | } 16 | } 17 | end 18 | 19 | it do 20 | is_expected.to contain_class('cassandra::java') 21 | is_expected.to contain_package('java-1.8.0-openjdk-headless') 22 | is_expected.to contain_package('jna') 23 | end 24 | end 25 | 26 | context 'On a Debian OS with defaults for all parameters' do 27 | let :facts do 28 | { 29 | operatingsystemmajrelease: '7', 30 | osfamily: 'Debian', 31 | lsbdistid: 'Debian', 32 | os: { 33 | 'name' => 'Debian', 34 | 'family' => 'Debian', 35 | 'release' => { 36 | 'full' => '7.8', 37 | 'major' => '7', 38 | 'minor' => '8' 39 | } 40 | } 41 | } 42 | end 43 | 44 | it do 45 | is_expected.to contain_class('cassandra::java') 46 | is_expected.to contain_package('openjdk-7-jre-headless') 47 | is_expected.to contain_package('libjna-java') 48 | is_expected.to have_resource_count(2) 49 | end 50 | end 51 | 52 | context 'On a Debian OS with package_ensure set' do 53 | let :facts do 54 | { 55 | operatingsystemmajrelease: '7', 56 | osfamily: 'Debian', 57 | lsbdistid: 'Debian', 58 | os: { 59 | 'name' => 'Debian', 60 | 'family' => 'Debian', 61 | 'release' => { 62 | 'full' => '7.8', 63 | 'major' => '7', 64 | 'minor' => '8' 65 | } 66 | } 67 | } 68 | end 69 | 70 | let :params do 71 | { 72 | package_ensure: '2.1.13' 73 | } 74 | end 75 | 76 | it do 77 | is_expected.to contain_package('openjdk-7-jre-headless').with_ensure('2.1.13') 78 | end 79 | end 80 | 81 | context 'With package names set to foobar' do 82 | let :facts do 83 | { 84 | operatingsystemmajrelease: '7', 85 | osfamily: 'RedHat', 86 | os: { 87 | 'family' => 'RedHat', 88 | 'release' => { 89 | 'full' => '7.6.1810', 90 | 'major' => '7', 91 | 'minor' => '6' 92 | } 93 | } 94 | } 95 | end 96 | 97 | let :params do 98 | { 99 | package_name: 'foobar-java', 100 | package_ensure: '42', 101 | jna_package_name: 'foobar-jna', 102 | jna_ensure: 'latest' 103 | } 104 | end 105 | 106 | it do 107 | is_expected.to contain_package('foobar-java').with(ensure: 42) 108 | is_expected.to contain_package('foobar-jna').with(ensure: 'latest') 109 | end 110 | end 111 | 112 | context 'Ensure that a YUM repo can be specified.' do 113 | let :facts do 114 | { 115 | operatingsystemmajrelease: '7', 116 | osfamily: 'RedHat', 117 | os: { 118 | 'family' => 'RedHat', 119 | 'release' => { 120 | 'full' => '7.6.1810', 121 | 'major' => '7', 122 | 'minor' => '6' 123 | } 124 | } 125 | } 126 | end 127 | 128 | let :params do 129 | { 130 | yumrepo: { 131 | 'ACME' => { 132 | 'baseurl' => 'http://yum.acme.org/repos', 133 | 'descr' => 'YUM Repository for ACME Products' 134 | } 135 | } 136 | } 137 | end 138 | 139 | it do 140 | is_expected.to contain_yumrepo('ACME').with( 141 | baseurl: 'http://yum.acme.org/repos', 142 | descr: 'YUM Repository for ACME Products' 143 | ).that_comes_before('Package[java-1.8.0-openjdk-headless]') 144 | end 145 | end 146 | 147 | context 'Ensure that Apt key and source can be specified.' do 148 | let :facts do 149 | { 150 | operatingsystemmajrelease: '7', 151 | osfamily: 'Debian', 152 | lsbdistid: 'Debian', 153 | os: { 154 | 'name' => 'Debian', 155 | 'family' => 'Debian', 156 | 'release' => { 157 | 'full' => '7.8', 158 | 'major' => '7', 159 | 'minor' => '8' 160 | } 161 | } 162 | } 163 | end 164 | 165 | let :params do 166 | { 167 | aptkey: { 168 | 'openjdk-r' => { 169 | 'id' => 'DA1A4A13543B466853BAF164EB9B1D8886F44E2A', 170 | 'server' => 'keyserver.ubuntu.com' 171 | } 172 | }, 173 | aptsource: { 174 | 'openjdk-r' => { 175 | 'comment' => 'OpenJDK builds (all archs)', 176 | 'location' => 'http://ppa.launchpad.net/openjdk-r/ppa/ubuntu', 177 | 'repos' => 'main', 178 | 'release' => 'trusty' 179 | } 180 | } 181 | } 182 | end 183 | 184 | it do 185 | is_expected.to contain_apt__key('openjdk-r'). 186 | with( 187 | id: 'DA1A4A13543B466853BAF164EB9B1D8886F44E2A', 188 | server: 'keyserver.ubuntu.com' 189 | ). 190 | that_comes_before('Package[openjdk-7-jre-headless]') 191 | is_expected.to contain_apt__source('openjdk-r'). 192 | with( 193 | comment: 'OpenJDK builds (all archs)', 194 | location: 'http://ppa.launchpad.net/openjdk-r/ppa/ubuntu', 195 | repos: 'main', 196 | release: 'trusty' 197 | ) 198 | is_expected.to contain_exec('cassandra::java::apt_update'). 199 | with( 200 | refreshonly: true, 201 | command: '/bin/true' 202 | ). 203 | that_comes_before('Package[openjdk-7-jre-headless]') 204 | end 205 | end 206 | end 207 | -------------------------------------------------------------------------------- /spec/classes/optutils_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | describe 'cassandra::optutils' do 3 | context 'On a RedHat OS with defaults for all parameters' do 4 | let :facts do 5 | { 6 | operatingsystemmajrelease: '7', 7 | osfamily: 'RedHat', 8 | os: { 9 | 'family' => 'RedHat', 10 | 'name' => 'RedHat', 11 | 'release' => { 12 | 'full' => '7.6.1810', 13 | 'major' => '7', 14 | 'minor' => '6' 15 | } 16 | } 17 | } 18 | end 19 | 20 | it do 21 | is_expected.to have_resource_count(7) 22 | is_expected.to contain_package('cassandra22-tools').with(ensure: 'present') 23 | 24 | is_expected.to contain_class('cassandra::optutils').with( 25 | package_ensure: 'present', 26 | package_name: 'cassandra22-tools' 27 | ) 28 | end 29 | end 30 | 31 | context 'On a Debian OS with defaults for all parameters' do 32 | let :facts do 33 | { 34 | operatingsystemmajrelease: '7', 35 | osfamily: 'Debian', 36 | os: { 37 | 'family' => 'Debian', 38 | 'name' => 'Debian', 39 | 'release' => { 40 | 'full' => '7.8', 41 | 'major' => '7', 42 | 'minor' => '8' 43 | } 44 | } 45 | } 46 | end 47 | 48 | it do 49 | is_expected.to contain_package('cassandra-tools').with(ensure: 'present') 50 | 51 | is_expected.to contain_class('cassandra::optutils').with( 52 | package_ensure: 'present', 53 | package_name: 'cassandra-tools' 54 | ) 55 | end 56 | end 57 | 58 | context 'With package_name set to foobar' do 59 | let :facts do 60 | { 61 | operatingsystemmajrelease: '7', 62 | osfamily: 'Debian', 63 | os: { 64 | 'family' => 'Debian', 65 | 'release' => { 66 | 'full' => '7.8', 67 | 'major' => '7', 68 | 'minor' => '8' 69 | } 70 | } 71 | } 72 | end 73 | 74 | let :params do 75 | { 76 | package_name: 'foobar-java', 77 | package_ensure: '42' 78 | } 79 | end 80 | 81 | it do 82 | is_expected.to contain_package('foobar-java').with(ensure: 42) 83 | end 84 | end 85 | 86 | context 'On a Debian OS with package_ensure set' do 87 | let :facts do 88 | { 89 | operatingsystemmajrelease: '7', 90 | osfamily: 'Debian', 91 | os: { 92 | 'family' => 'Debian', 93 | 'release' => { 94 | 'full' => '7.8', 95 | 'major' => '7', 96 | 'minor' => '8' 97 | } 98 | } 99 | } 100 | end 101 | let :params do 102 | { 103 | package_ensure: '2.1.13' 104 | } 105 | end 106 | 107 | it { is_expected.to contain_package('cassandra-tools').with_ensure('2.1.13') } 108 | end 109 | end 110 | -------------------------------------------------------------------------------- /spec/classes/params_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandra::params' do 4 | let :facts do 5 | { 6 | osfamily: 'RedHat', 7 | operatingsystemmajrelease: '7', 8 | os: { 9 | 'family' => 'RedHat', 10 | 'release' => { 11 | 'full' => '7.6.1810', 12 | 'major' => '7', 13 | 'minor' => '6' 14 | } 15 | } 16 | } 17 | end 18 | 19 | it do 20 | is_expected.to compile 21 | is_expected.to contain_class('cassandra::params') 22 | is_expected.to have_resource_count(0) 23 | end 24 | end 25 | -------------------------------------------------------------------------------- /spec/classes/schema_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | describe 'cassandra::schema' do 3 | context 'Ensure that a connection test is made.' do 4 | let :facts do 5 | { 6 | operatingsystemmajrelease: 7, 7 | osfamily: 'RedHat', 8 | os: { 9 | 'family' => 'RedHat', 10 | 'name' => 'RedHat', 11 | 'release' => { 12 | 'full' => '7.6.1810', 13 | 'major' => '7', 14 | 'minor' => '6' 15 | } 16 | } 17 | } 18 | end 19 | 20 | it do 21 | is_expected.to contain_class('cassandra::schema'). 22 | with(connection_tries: 6, 23 | connection_try_sleep: 30, 24 | cqlsh_additional_options: '', 25 | cqlsh_command: '/usr/bin/cqlsh', 26 | cqlsh_host: 'localhost', 27 | cqlsh_password: nil, 28 | cqlsh_port: 9042, 29 | cqlsh_user: 'cassandra') 30 | 31 | read_command = '/usr/bin/cqlsh -e \'DESC KEYSPACES\' localhost 9042' 32 | 33 | is_expected.to contain_exec('cassandra::schema connection test'). 34 | only_with(command: read_command, 35 | returns: 0, 36 | tries: 6, 37 | try_sleep: 30, 38 | unless: read_command) 39 | end 40 | end 41 | 42 | context 'Ensure that a connection test is made with SCL.' do 43 | let :facts do 44 | { 45 | operatingsystemmajrelease: 7, 46 | osfamily: 'RedHat', 47 | os: { 48 | 'family' => 'RedHat', 49 | 'name' => 'RedHat', 50 | 'release' => { 51 | 'full' => '7.6.1810', 52 | 'major' => '7', 53 | 'minor' => '6' 54 | } 55 | } 56 | } 57 | end 58 | 59 | let :params do 60 | { 61 | use_scl: true, 62 | scl_name: 'testscl' 63 | } 64 | end 65 | 66 | it do 67 | is_expected.to contain_class('cassandra::schema'). 68 | with(connection_tries: 6, 69 | connection_try_sleep: 30, 70 | cqlsh_additional_options: '', 71 | cqlsh_command: '/usr/bin/cqlsh', 72 | cqlsh_host: 'localhost', 73 | cqlsh_password: nil, 74 | cqlsh_port: 9042, 75 | cqlsh_user: 'cassandra') 76 | 77 | read_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \'DESC KEYSPACES\' localhost 9042"' 78 | 79 | is_expected.to contain_exec('cassandra::schema connection test'). 80 | only_with(command: read_command, 81 | returns: 0, 82 | tries: 6, 83 | try_sleep: 30, 84 | unless: read_command) 85 | end 86 | end 87 | 88 | context 'Test that users can specify a credentials file.' do 89 | let :facts do 90 | { 91 | id: 0, 92 | gid: 0, 93 | operatingsystemmajrelease: 7, 94 | osfamily: 'Debian', 95 | os: { 96 | 'family' => 'Debian', 97 | 'name' => 'Debian', 98 | 'release' => { 99 | 'full' => '7.8', 100 | 'major' => '7', 101 | 'minor' => '8' 102 | } 103 | }, 104 | identity: { 105 | uid: 0, 106 | gid: 0 107 | } 108 | } 109 | end 110 | 111 | let :params do 112 | { 113 | cqlsh_client_config: '/root/.puppetcqlshrc', 114 | use_scl: false, 115 | scl_name: 'nodefault' 116 | } 117 | end 118 | 119 | it do 120 | is_expected.to contain_file('/root/.puppetcqlshrc').with( 121 | ensure: 'file', 122 | group: 0, 123 | mode: '0600', 124 | owner: 0, 125 | content: %r{username = cassandra} 126 | ).that_comes_before('Exec[::cassandra::schema connection test]') 127 | 128 | read_command = "/usr/bin/cqlsh --cqlshrc=/root/.puppetcqlshrc -e 'DESC KEYSPACES' localhost 9042" 129 | 130 | is_expected.to contain_exec('cassandra::schema connection test'). 131 | only_with(command: read_command, 132 | returns: 0, 133 | tries: 6, 134 | try_sleep: 30, 135 | unless: read_command) 136 | end 137 | end 138 | 139 | context 'Test that users can specify a credentials file and password.' do 140 | let :facts do 141 | { 142 | id: 0, 143 | gid: 0, 144 | operatingsystemmajrelease: 7, 145 | osfamily: 'Debian', 146 | os: { 147 | 'family' => 'Debian', 148 | 'name' => 'Debian', 149 | 'release' => { 150 | 'full' => '7.8', 151 | 'major' => '7', 152 | 'minor' => '8' 153 | } 154 | }, 155 | identity: { 156 | uid: 0, 157 | gid: 0 158 | } 159 | } 160 | end 161 | 162 | let :params do 163 | { 164 | cqlsh_client_config: '/root/.puppetcqlshrc', 165 | cqlsh_password: 'topsecret', 166 | use_scl: false, 167 | scl_name: 'nodefault' 168 | } 169 | end 170 | 171 | it do 172 | is_expected.to contain_file('/root/.puppetcqlshrc').with( 173 | ensure: 'file', 174 | group: 0, 175 | mode: '0600', 176 | owner: 0, 177 | content: %r{password = topsecret} 178 | ) 179 | 180 | read_command = "/usr/bin/cqlsh --cqlshrc=/root/.puppetcqlshrc -e 'DESC KEYSPACES' localhost 9042" 181 | 182 | is_expected.to contain_exec('cassandra::schema connection test'). 183 | only_with(command: read_command, 184 | returns: 0, 185 | tries: 6, 186 | try_sleep: 30, 187 | unless: read_command) 188 | end 189 | end 190 | 191 | context 'Test that users can specify a password.' do 192 | let :facts do 193 | { 194 | operatingsystemmajrelease: 7, 195 | osfamily: 'Redhat', 196 | os: { 197 | 'family' => 'RedHat', 198 | 'name' => 'RedHat', 199 | 'release' => { 200 | 'full' => '7.6.1810', 201 | 'major' => '7', 202 | 'minor' => '6' 203 | } 204 | } 205 | } 206 | end 207 | 208 | let :params do 209 | { 210 | cqlsh_password: 'topsecret' 211 | } 212 | end 213 | 214 | it do 215 | read_command = "/usr/bin/cqlsh -u cassandra -p topsecret -e 'DESC KEYSPACES' localhost 9042" 216 | 217 | is_expected.to contain_exec('cassandra::schema connection test'). 218 | only_with(command: read_command, 219 | returns: 0, 220 | tries: 6, 221 | try_sleep: 30, 222 | unless: read_command) 223 | end 224 | end 225 | end 226 | -------------------------------------------------------------------------------- /spec/classes/system/swapoff_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandra::system::swapoff' do 4 | context 'Test the default parameters' do 5 | it do 6 | is_expected.to have_resource_count(1) 7 | is_expected.to contain_class('cassandra::system::swapoff') 8 | is_expected.to contain_exec('Disable Swap') 9 | end 10 | end 11 | 12 | context 'Test we can remove a swap device from /etc/fstab' do 13 | let :params do 14 | { 15 | device: '/dev/mapper/centos-swap' 16 | } 17 | end 18 | 19 | it do 20 | is_expected.to have_resource_count(2) 21 | is_expected.to contain_class('cassandra::system::swapoff') 22 | is_expected.to contain_exec('Disable Swap') 23 | is_expected.to contain_mount('swap').with( 24 | ensure: 'absent', 25 | device: '/dev/mapper/centos-swap', 26 | fstype: 'swap' 27 | ) 28 | end 29 | end 30 | end 31 | -------------------------------------------------------------------------------- /spec/classes/system/sysctl_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandra::system::sysctl' do 4 | context 'Test the default parameters (RedHat)' do 5 | let :facts do 6 | { 7 | osfamily: 'RedHat', 8 | operatingsystemmajrelease: '7', 9 | os: { 10 | 'family' => 'RedHat', 11 | 'release' => { 12 | 'full' => '7.6.1810', 13 | 'major' => '7', 14 | 'minor' => '6' 15 | } 16 | } 17 | } 18 | end 19 | 20 | it do 21 | is_expected.to have_resource_count(9) 22 | is_expected.to contain_class('Cassandra::System::Sysctl') 23 | is_expected.to contain_ini_setting('net.core.optmem_max = 40960') 24 | is_expected.to contain_ini_setting('net.core.rmem_default = 16777216') 25 | is_expected.to contain_ini_setting('net.core.rmem_max = 16777216') 26 | is_expected.to contain_ini_setting('net.core.wmem_default = 16777216') 27 | is_expected.to contain_ini_setting('net.core.wmem_max = 16777216') 28 | is_expected.to contain_ini_setting('net.ipv4.tcp_rmem = 4096, 87380, 16777216') 29 | is_expected.to contain_ini_setting('net.ipv4.tcp_wmem = 4096, 65536, 16777216') 30 | is_expected.to contain_ini_setting('vm.max_map_count = 1048575') 31 | is_expected.to contain_exec('Apply sysctl changes').with( 32 | command: '/sbin/sysctl -p /etc/sysctl.d/10-cassandra.conf' 33 | ) 34 | end 35 | end 36 | end 37 | -------------------------------------------------------------------------------- /spec/classes/system/transparent_hugepage_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandra::system::transparent_hugepage' do 4 | context 'Test the default parameters (RedHat)' do 5 | let :facts do 6 | { 7 | osfamily: 'RedHat', 8 | operatingsystemmajrelease: 7, 9 | os: { 10 | 'family' => 'RedHat', 11 | 'release' => { 12 | 'full' => '7.6.1810', 13 | 'major' => '7', 14 | 'minor' => '6' 15 | } 16 | } 17 | } 18 | end 19 | 20 | it do 21 | is_expected.to have_resource_count(1) 22 | is_expected.to contain_class('cassandra::system::transparent_hugepage') 23 | is_expected.to contain_exec('Disable Java Hugepages') 24 | end 25 | end 26 | 27 | context 'Test the default parameters (Debian)' do 28 | let :facts do 29 | { 30 | osfamily: 'Debian', 31 | operatingsystemmajrelease: 7, 32 | os: { 33 | 'family' => 'Debian', 34 | 'release' => { 35 | 'full' => '7.8', 36 | 'major' => '7', 37 | 'minor' => '8' 38 | } 39 | } 40 | } 41 | end 42 | 43 | it do 44 | is_expected.to have_resource_count(1) 45 | is_expected.to contain_class('cassandra::system::transparent_hugepage') 46 | is_expected.to contain_exec('Disable Java Hugepages') 47 | end 48 | end 49 | end 50 | -------------------------------------------------------------------------------- /spec/defines/file_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandra::file' do 4 | context 'On a Debian OS set the max and new heap size' do 5 | let :facts do 6 | { 7 | osfamily: 'Debian', 8 | operatingsystemmajrelease: 8, 9 | os: { 10 | 'family' => 'Debian', 11 | 'name' => 'Debian', 12 | 'release' => { 13 | 'full' => '8.11', 14 | 'major' => '8', 15 | 'minor' => '11' 16 | } 17 | } 18 | } 19 | end 20 | 21 | let(:title) { 'cassandra-env.sh' } 22 | 23 | let :params do 24 | { 25 | config_path: '/etc/cassandra', 26 | 'file_lines' => { 27 | 'MAX_HEAP_SIZE 4GB' => { 28 | 'line' => 'MAX_HEAP_SIZE="4G"', 29 | 'match' => '^#MAX_HEAP_SIZE="4G"$' 30 | } 31 | } 32 | } 33 | end 34 | 35 | it do 36 | is_expected.to contain_class('cassandra') 37 | is_expected.to contain_class('cassandra::params') 38 | is_expected.to contain_class('stdlib') 39 | is_expected.to contain_cassandra__file('cassandra-env.sh') 40 | 41 | is_expected.to contain_file_line('MAX_HEAP_SIZE 4GB').with( 42 | path: '/etc/cassandra/cassandra-env.sh', 43 | line: 'MAX_HEAP_SIZE="4G"', 44 | match: '^#MAX_HEAP_SIZE="4G"$' 45 | ) 46 | end 47 | end 48 | end 49 | -------------------------------------------------------------------------------- /spec/defines/private/firewall_ports/rule_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | describe 'cassandra::private::firewall_ports::rule' do 3 | context 'Test that rules can be set.' do 4 | let(:title) { '200_Public_0.0.0.0/0' } 5 | let :params do 6 | { 7 | ports: [8888, 22] 8 | } 9 | end 10 | 11 | it do 12 | is_expected.to contain_firewall('200 - Cassandra (Public) - 0.0.0.0/0').with( 13 | action: 'accept', 14 | dport: [8888, 22], 15 | proto: 'tcp', 16 | source: '0.0.0.0/0' 17 | ) 18 | is_expected.to have_resource_count(2) 19 | end 20 | end 21 | end 22 | -------------------------------------------------------------------------------- /spec/defines/schema/cql_type_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandra::schema::cql_type' do 4 | context 'CQL TYPE (fullname)' do 5 | let :facts do 6 | { 7 | operatingsystemmajrelease: 7, 8 | osfamily: 'RedHat', 9 | os: { 10 | 'family' => 'RedHat', 11 | 'name' => 'RedHat', 12 | 'release' => { 13 | 'full' => '7.6.1810', 14 | 'major' => '7', 15 | 'minor' => '6' 16 | } 17 | } 18 | } 19 | end 20 | 21 | let(:title) { 'fullname' } 22 | 23 | let(:params) do 24 | { 25 | 'keyspace' => 'Excelsior', 26 | fields: 27 | { 28 | 'firstname' => 'text', 29 | 'lastname' => 'text' 30 | }, 31 | 'use_scl' => false, 32 | 'scl_name' => 'nodefault' 33 | } 34 | end 35 | 36 | it do 37 | is_expected.to compile 38 | is_expected.to contain_class('cassandra::schema') 39 | is_expected.to contain_cassandra__schema__cql_type('fullname') 40 | read_command = '/usr/bin/cqlsh -e "DESC TYPE Excelsior.fullname" localhost 9042' 41 | exec_command = '/usr/bin/cqlsh -e "CREATE TYPE IF NOT EXISTS Excelsior.fullname ' 42 | exec_command += '(firstname text, lastname text)" localhost 9042' 43 | is_expected.to contain_exec(exec_command). 44 | only_with(unless: read_command, 45 | require: 'Exec[::cassandra::schema connection test]') 46 | end 47 | end 48 | 49 | context 'CQL TYPE (fullname) with SCL' do 50 | let :facts do 51 | { 52 | operatingsystemmajrelease: 7, 53 | osfamily: 'RedHat', 54 | os: { 55 | 'family' => 'RedHat', 56 | 'name' => 'RedHat', 57 | 'release' => { 58 | 'full' => '7.6.1810', 59 | 'major' => '7', 60 | 'minor' => '6' 61 | } 62 | } 63 | } 64 | end 65 | 66 | let(:title) { 'fullname' } 67 | 68 | let(:params) do 69 | { 70 | 'keyspace' => 'Excelsior', 71 | fields: 72 | { 73 | 'firstname' => 'text', 74 | 'lastname' => 'text' 75 | }, 76 | 'use_scl' => true, 77 | 'scl_name' => 'testscl' 78 | } 79 | end 80 | 81 | it do 82 | is_expected.to compile 83 | is_expected.to contain_class('cassandra::schema') 84 | is_expected.to contain_cassandra__schema__cql_type('fullname') 85 | read_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DESC TYPE Excelsior.fullname\" localhost 9042"' 86 | exec_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"CREATE TYPE IF NOT EXISTS Excelsior.fullname ' 87 | exec_command += '(firstname text, lastname text)\" localhost 9042"' 88 | is_expected.to contain_exec(exec_command). 89 | only_with(unless: read_command, 90 | require: 'Exec[::cassandra::schema connection test]') 91 | end 92 | end 93 | 94 | context 'Set ensure to absent' do 95 | let :facts do 96 | { 97 | operatingsystemmajrelease: 7, 98 | osfamily: 'RedHat', 99 | os: { 100 | 'family' => 'RedHat', 101 | 'name' => 'RedHat', 102 | 'release' => { 103 | 'full' => '7.6.1810', 104 | 'major' => '7', 105 | 'minor' => '6' 106 | } 107 | } 108 | } 109 | end 110 | 111 | let(:title) { 'address' } 112 | let(:params) do 113 | { 114 | 'ensure' => 'absent', 115 | 'keyspace' => 'Excalibur', 116 | 'use_scl' => false, 117 | 'scl_name' => 'nodefault' 118 | } 119 | end 120 | 121 | it do 122 | is_expected.to compile 123 | is_expected.to contain_cassandra__schema__cql_type('address') 124 | read_command = '/usr/bin/cqlsh -e "DESC TYPE Excalibur.address" localhost 9042' 125 | exec_command = '/usr/bin/cqlsh -e "DROP type Excalibur.address" localhost 9042' 126 | is_expected.to contain_exec(exec_command). 127 | only_with(onlyif: read_command, 128 | require: 'Exec[::cassandra::schema connection test]') 129 | end 130 | end 131 | 132 | context 'Set ensure to absent with SCL' do 133 | let :facts do 134 | { 135 | operatingsystemmajrelease: 7, 136 | osfamily: 'RedHat', 137 | os: { 138 | 'family' => 'RedHat', 139 | 'name' => 'RedHat', 140 | 'release' => { 141 | 'full' => '7.6.1810', 142 | 'major' => '7', 143 | 'minor' => '6' 144 | } 145 | } 146 | } 147 | end 148 | 149 | let(:title) { 'address' } 150 | let(:params) do 151 | { 152 | 'ensure' => 'absent', 153 | 'keyspace' => 'Excalibur', 154 | 'use_scl' => true, 155 | 'scl_name' => 'testscl' 156 | } 157 | end 158 | 159 | it do 160 | is_expected.to compile 161 | is_expected.to contain_cassandra__schema__cql_type('address') 162 | read_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DESC TYPE Excalibur.address\" localhost 9042"' 163 | exec_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DROP type Excalibur.address\" localhost 9042"' 164 | is_expected.to contain_exec(exec_command). 165 | only_with(onlyif: read_command, 166 | require: 'Exec[::cassandra::schema connection test]') 167 | end 168 | end 169 | 170 | context 'Set ensure to latest' do 171 | let :facts do 172 | { 173 | operatingsystemmajrelease: 7, 174 | osfamily: 'RedHat', 175 | os: { 176 | 'family' => 'RedHat', 177 | 'name' => 'RedHat', 178 | 'release' => { 179 | 'full' => '7.6.1810', 180 | 'major' => '7', 181 | 'minor' => '6' 182 | } 183 | } 184 | } 185 | end 186 | 187 | let(:title) { 'foobar' } 188 | let(:params) do 189 | { 190 | ensure: 'latest' 191 | } 192 | end 193 | 194 | it { is_expected.to raise_error(Puppet::Error) } 195 | end 196 | end 197 | -------------------------------------------------------------------------------- /spec/defines/schema/index_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandra::schema::index' do 4 | context 'Create a basic index' do 5 | let :facts do 6 | { 7 | operatingsystemmajrelease: 7, 8 | osfamily: 'RedHat', 9 | os: { 10 | 'family' => 'RedHat', 11 | 'name' => 'RedHat', 12 | 'release' => { 13 | 'full' => '7.6.1810', 14 | 'major' => '7', 15 | 'minor' => '6' 16 | } 17 | } 18 | } 19 | end 20 | 21 | let(:title) { 'user_index' } 22 | 23 | let(:params) do 24 | { 25 | keys: 'lname', 26 | keyspace: 'mykeyspace', 27 | table: 'users', 28 | use_scl: false, 29 | scl_name: 'nodefault' 30 | } 31 | end 32 | 33 | it do 34 | is_expected.to compile 35 | is_expected.to contain_cassandra__schema__index('user_index') 36 | read_command = '/usr/bin/cqlsh -e "DESC INDEX mykeyspace.user_index" localhost 9042' 37 | exec_command = '/usr/bin/cqlsh -e "CREATE INDEX IF NOT EXISTS user_index ON mykeyspace.users (lname)" localhost 9042' 38 | is_expected.to contain_exec(exec_command). 39 | only_with(unless: read_command, 40 | require: 'Exec[::cassandra::schema connection test]') 41 | end 42 | end 43 | 44 | context 'Create a basic index with SCL' do 45 | let :facts do 46 | { 47 | operatingsystemmajrelease: 7, 48 | osfamily: 'RedHat', 49 | os: { 50 | 'family' => 'RedHat', 51 | 'name' => 'RedHat', 52 | 'release' => { 53 | 'full' => '7.6.1810', 54 | 'major' => '7', 55 | 'minor' => '6' 56 | } 57 | } 58 | } 59 | end 60 | 61 | let(:title) { 'user_index' } 62 | 63 | let(:params) do 64 | { 65 | keys: 'lname', 66 | keyspace: 'mykeyspace', 67 | table: 'users', 68 | use_scl: true, 69 | scl_name: 'testscl' 70 | } 71 | end 72 | 73 | it do 74 | is_expected.to compile 75 | is_expected.to contain_cassandra__schema__index('user_index') 76 | read_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DESC INDEX mykeyspace.user_index\" localhost 9042"' 77 | exec_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"CREATE INDEX IF NOT EXISTS user_index ON mykeyspace.users (lname)\" localhost 9042"' 78 | is_expected.to contain_exec(exec_command). 79 | only_with(unless: read_command, 80 | require: 'Exec[::cassandra::schema connection test]') 81 | end 82 | end 83 | 84 | context 'Create a custom index.' do 85 | let :facts do 86 | { 87 | operatingsystemmajrelease: 7, 88 | osfamily: 'RedHat', 89 | os: { 90 | 'family' => 'RedHat', 91 | 'name' => 'RedHat', 92 | 'release' => { 93 | 'full' => '7.6.1810', 94 | 'major' => '7', 95 | 'minor' => '6' 96 | } 97 | } 98 | } 99 | end 100 | 101 | let(:title) { 'user_index' } 102 | 103 | let(:params) do 104 | { 105 | class_name: 'path.to.the.IndexClass', 106 | keys: 'email', 107 | keyspace: 'Excelsior', 108 | table: 'users', 109 | use_scl: false, 110 | scl_name: 'nodefault' 111 | } 112 | end 113 | 114 | it do 115 | is_expected.to compile 116 | read_command = '/usr/bin/cqlsh -e "DESC INDEX Excelsior.user_index" localhost 9042' 117 | exec_command = '/usr/bin/cqlsh -e "CREATE CUSTOM INDEX IF NOT EXISTS user_index ON Excelsior.users (email) USING \'path.to.the.IndexClass\'" localhost 9042' 118 | is_expected.to contain_exec(exec_command). 119 | only_with(unless: read_command, 120 | require: 'Exec[::cassandra::schema connection test]') 121 | end 122 | end 123 | 124 | context 'Create a custom index with SCL.' do 125 | let :facts do 126 | { 127 | operatingsystemmajrelease: 7, 128 | osfamily: 'RedHat', 129 | os: { 130 | 'family' => 'RedHat', 131 | 'name' => 'RedHat', 132 | 'release' => { 133 | 'full' => '7.6.1810', 134 | 'major' => '7', 135 | 'minor' => '6' 136 | } 137 | } 138 | } 139 | end 140 | 141 | let(:title) { 'user_index' } 142 | 143 | let(:params) do 144 | { 145 | class_name: 'path.to.the.IndexClass', 146 | keys: 'email', 147 | keyspace: 'Excelsior', 148 | table: 'users', 149 | use_scl: true, 150 | scl_name: 'testscl' 151 | } 152 | end 153 | 154 | it do 155 | is_expected.to compile 156 | read_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DESC INDEX Excelsior.user_index\" localhost 9042"' 157 | exec_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"CREATE CUSTOM INDEX IF NOT EXISTS user_index ON Excelsior.users (email) USING \'path.to.the.IndexClass\'\" localhost 9042"' 158 | is_expected.to contain_exec(exec_command). 159 | only_with(unless: read_command, 160 | require: 'Exec[::cassandra::schema connection test]') 161 | end 162 | end 163 | 164 | context 'Create a custom index with options.' do 165 | let :facts do 166 | { 167 | operatingsystemmajrelease: 7, 168 | osfamily: 'RedHat', 169 | os: { 170 | 'family' => 'RedHat', 171 | 'name' => 'RedHat', 172 | 'release' => { 173 | 'full' => '7.6.1810', 174 | 'major' => '7', 175 | 'minor' => '6' 176 | } 177 | } 178 | } 179 | end 180 | 181 | let(:title) { 'user_index' } 182 | 183 | let(:params) do 184 | { 185 | class_name: 'path.to.the.IndexClass', 186 | keys: 'email', 187 | keyspace: 'Excelsior', 188 | options: "{'storage': '/mnt/ssd/indexes/'}", 189 | table: 'users', 190 | use_scl: false, 191 | scl_name: 'nodefault' 192 | } 193 | end 194 | 195 | it do 196 | is_expected.to compile 197 | read_command = '/usr/bin/cqlsh -e "DESC INDEX Excelsior.user_index" localhost 9042' 198 | exec_command = '/usr/bin/cqlsh -e "CREATE CUSTOM INDEX IF NOT EXISTS user_index ON ' 199 | exec_command += 'Excelsior.users (email) USING \'path.to.the.IndexClass\' WITH OPTIONS = {' 200 | exec_command += '\'storage\': \'/mnt/ssd/indexes/\'}" localhost 9042' 201 | is_expected.to contain_exec(exec_command). 202 | only_with(unless: read_command, 203 | require: 'Exec[::cassandra::schema connection test]') 204 | end 205 | end 206 | 207 | context 'Create a custom index with options with SCL.' do 208 | let :facts do 209 | { 210 | operatingsystemmajrelease: 7, 211 | osfamily: 'RedHat', 212 | os: { 213 | 'family' => 'RedHat', 214 | 'name' => 'RedHat', 215 | 'release' => { 216 | 'full' => '7.6.1810', 217 | 'major' => '7', 218 | 'minor' => '6' 219 | } 220 | } 221 | } 222 | end 223 | 224 | let(:title) { 'user_index' } 225 | 226 | let(:params) do 227 | { 228 | class_name: 'path.to.the.IndexClass', 229 | keys: 'email', 230 | keyspace: 'Excelsior', 231 | options: "{'storage': '/mnt/ssd/indexes/'}", 232 | table: 'users', 233 | use_scl: true, 234 | scl_name: 'testscl' 235 | } 236 | end 237 | 238 | it do 239 | is_expected.to compile 240 | read_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DESC INDEX Excelsior.user_index\" localhost 9042"' 241 | exec_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"CREATE CUSTOM INDEX IF NOT EXISTS user_index ON ' 242 | exec_command += 'Excelsior.users (email) USING \'path.to.the.IndexClass\' WITH OPTIONS = {' 243 | exec_command += '\'storage\': \'/mnt/ssd/indexes/\'}\" localhost 9042"' 244 | is_expected.to contain_exec(exec_command). 245 | only_with(unless: read_command, 246 | require: 'Exec[::cassandra::schema connection test]') 247 | end 248 | end 249 | 250 | context 'Drop Index' do 251 | let :facts do 252 | { 253 | operatingsystemmajrelease: 7, 254 | osfamily: 'RedHat', 255 | os: { 256 | 'family' => 'RedHat', 257 | 'name' => 'RedHat', 258 | 'release' => { 259 | 'full' => '7.6.1810', 260 | 'major' => '7', 261 | 'minor' => '6' 262 | } 263 | } 264 | } 265 | end 266 | 267 | let(:title) { 'user_index' } 268 | 269 | let(:params) do 270 | { 271 | ensure: 'absent', 272 | keys: 'lname', 273 | keyspace: 'Excelsior', 274 | table: 'users', 275 | use_scl: false, 276 | scl_name: 'nodefault' 277 | } 278 | end 279 | 280 | it do 281 | is_expected.to compile 282 | read_command = '/usr/bin/cqlsh -e "DESC INDEX Excelsior.user_index" localhost 9042' 283 | exec_command = '/usr/bin/cqlsh -e "DROP INDEX Excelsior.user_index" localhost 9042' 284 | is_expected.to contain_exec(exec_command). 285 | only_with(onlyif: read_command, 286 | require: 'Exec[::cassandra::schema connection test]') 287 | end 288 | end 289 | 290 | context 'Drop Index with SCL' do 291 | let :facts do 292 | { 293 | operatingsystemmajrelease: 7, 294 | osfamily: 'RedHat', 295 | os: { 296 | 'family' => 'RedHat', 297 | 'name' => 'RedHat', 298 | 'release' => { 299 | 'full' => '7.6.1810', 300 | 'major' => '7', 301 | 'minor' => '6' 302 | } 303 | } 304 | } 305 | end 306 | 307 | let(:title) { 'user_index' } 308 | 309 | let(:params) do 310 | { 311 | ensure: 'absent', 312 | keys: 'lname', 313 | keyspace: 'Excelsior', 314 | table: 'users', 315 | use_scl: true, 316 | scl_name: 'testscl' 317 | } 318 | end 319 | 320 | it do 321 | is_expected.to compile 322 | read_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DESC INDEX Excelsior.user_index\" localhost 9042"' 323 | exec_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DROP INDEX Excelsior.user_index\" localhost 9042"' 324 | is_expected.to contain_exec(exec_command). 325 | only_with(onlyif: read_command, 326 | require: 'Exec[::cassandra::schema connection test]') 327 | end 328 | end 329 | 330 | context 'Set ensure to latest' do 331 | let :facts do 332 | { 333 | operatingsystemmajrelease: 7, 334 | osfamily: 'RedHat', 335 | os: { 336 | 'family' => 'RedHat', 337 | 'name' => 'RedHat', 338 | 'release' => { 339 | 'full' => '7.6.1810', 340 | 'major' => '7', 341 | 'minor' => '6' 342 | } 343 | } 344 | } 345 | end 346 | 347 | let(:title) { 'foobar' } 348 | let(:params) do 349 | { 350 | ensure: 'latest' 351 | } 352 | end 353 | 354 | it { is_expected.to raise_error(Puppet::Error) } 355 | end 356 | end 357 | -------------------------------------------------------------------------------- /spec/defines/schema/keyspace_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandra::schema::keyspace' do 4 | context 'Set ensure to present (SimpleStrategy)' do 5 | let :facts do 6 | { 7 | operatingsystemmajrelease: 7, 8 | osfamily: 'RedHat', 9 | os: { 10 | 'family' => 'RedHat', 11 | 'name' => 'RedHat', 12 | 'release' => { 13 | 'full' => '7.6.1810', 14 | 'major' => '7', 15 | 'minor' => '6' 16 | } 17 | } 18 | } 19 | end 20 | 21 | let(:title) { 'foobar' } 22 | 23 | let(:params) do 24 | { 25 | ensure: 'present', 26 | replication_map: 27 | { 28 | 'keyspace_class' => 'SimpleStrategy', 29 | 'replication_factor' => 3 30 | }, 31 | use_scl: false, 32 | scl_name: 'nodefault' 33 | } 34 | end 35 | 36 | it do 37 | is_expected.to compile 38 | is_expected.to contain_class('cassandra::schema') 39 | read_command = '/usr/bin/cqlsh -e "DESC KEYSPACE foobar" localhost 9042' 40 | exec_command = '/usr/bin/cqlsh -e "CREATE KEYSPACE IF NOT EXISTS foobar WITH REPLICATION = ' 41 | exec_command += '{ \'class\' : \'SimpleStrategy\', \'replication_factor\' : 3 } ' 42 | exec_command += 'AND DURABLE_WRITES = true" localhost 9042' 43 | is_expected.to contain_exec(exec_command). 44 | only_with(unless: read_command, 45 | require: 'Exec[::cassandra::schema connection test]') 46 | end 47 | end 48 | 49 | context 'Set ensure to present (SimpleStrategy) with SCL' do 50 | let :facts do 51 | { 52 | operatingsystemmajrelease: 7, 53 | osfamily: 'RedHat', 54 | os: { 55 | 'family' => 'RedHat', 56 | 'name' => 'RedHat', 57 | 'release' => { 58 | 'full' => '7.6.1810', 59 | 'major' => '7', 60 | 'minor' => '6' 61 | } 62 | } 63 | } 64 | end 65 | 66 | let(:title) { 'foobar' } 67 | 68 | let(:params) do 69 | { 70 | ensure: 'present', 71 | replication_map: 72 | { 73 | 'keyspace_class' => 'SimpleStrategy', 74 | 'replication_factor' => 3 75 | }, 76 | use_scl: true, 77 | scl_name: 'testscl' 78 | } 79 | end 80 | 81 | it do 82 | is_expected.to compile 83 | read_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DESC KEYSPACE foobar\" localhost 9042"' 84 | exec_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"CREATE KEYSPACE IF NOT EXISTS foobar WITH REPLICATION = ' 85 | exec_command += '{ \'class\' : \'SimpleStrategy\', \'replication_factor\' : 3 } ' 86 | exec_command += 'AND DURABLE_WRITES = true\" localhost 9042"' 87 | is_expected.to contain_exec(exec_command). 88 | only_with(unless: read_command, 89 | require: 'Exec[::cassandra::schema connection test]') 90 | end 91 | end 92 | 93 | context 'Set ensure to present (NetworkTopologyStrategy)' do 94 | let :facts do 95 | { 96 | operatingsystemmajrelease: 7, 97 | osfamily: 'RedHat', 98 | os: { 99 | 'family' => 'RedHat', 100 | 'name' => 'RedHat', 101 | 'release' => { 102 | 'full' => '7.6.1810', 103 | 'major' => '7', 104 | 'minor' => '6' 105 | } 106 | } 107 | } 108 | end 109 | 110 | let(:title) { 'foobar' } 111 | 112 | let(:params) do 113 | { 114 | ensure: 'present', 115 | replication_map: 116 | { 117 | 'keyspace_class' => 'NetworkTopologyStrategy', 118 | 'dc1' => '3', 119 | 'dc2' => '2' 120 | }, 121 | use_scl: false, 122 | scl_name: 'nodefault' 123 | } 124 | end 125 | 126 | it do 127 | is_expected.to contain_cassandra__schema__keyspace('foobar') 128 | read_command = '/usr/bin/cqlsh -e "DESC KEYSPACE foobar" localhost 9042' 129 | exec_command = '/usr/bin/cqlsh -e "CREATE KEYSPACE IF NOT EXISTS foobar WITH REPLICATION = ' 130 | exec_command += '{ \'class\' : \'NetworkTopologyStrategy\', \'dc1\': 3, \'dc2\': 2 } ' 131 | exec_command += 'AND DURABLE_WRITES = true" localhost 9042' 132 | is_expected.to contain_exec(exec_command). 133 | only_with(unless: read_command, 134 | require: 'Exec[::cassandra::schema connection test]') 135 | end 136 | end 137 | 138 | context 'Set ensure to present (NetworkTopologyStrategy) with SCL' do 139 | let :facts do 140 | { 141 | operatingsystemmajrelease: 7, 142 | osfamily: 'RedHat', 143 | os: { 144 | 'family' => 'RedHat', 145 | 'name' => 'RedHat', 146 | 'release' => { 147 | 'full' => '7.6.1810', 148 | 'major' => '7', 149 | 'minor' => '6' 150 | } 151 | } 152 | } 153 | end 154 | 155 | let(:title) { 'foobar' } 156 | 157 | let(:params) do 158 | { 159 | ensure: 'present', 160 | replication_map: 161 | { 162 | 'keyspace_class' => 'NetworkTopologyStrategy', 163 | 'dc1' => '3', 164 | 'dc2' => '2' 165 | }, 166 | use_scl: true, 167 | scl_name: 'testscl' 168 | } 169 | end 170 | 171 | it do 172 | is_expected.to contain_cassandra__schema__keyspace('foobar') 173 | read_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DESC KEYSPACE foobar\" localhost 9042"' 174 | exec_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"CREATE KEYSPACE IF NOT EXISTS foobar WITH REPLICATION = ' 175 | exec_command += '{ \'class\' : \'NetworkTopologyStrategy\', \'dc1\': 3, \'dc2\': 2 } ' 176 | exec_command += 'AND DURABLE_WRITES = true\" localhost 9042"' 177 | is_expected.to contain_exec(exec_command). 178 | only_with(unless: read_command, 179 | require: 'Exec[::cassandra::schema connection test]') 180 | end 181 | end 182 | 183 | context 'Set ensure to absent' do 184 | let :facts do 185 | { 186 | operatingsystemmajrelease: 7, 187 | osfamily: 'RedHat', 188 | os: { 189 | 'family' => 'RedHat', 190 | 'name' => 'RedHat', 191 | 'release' => { 192 | 'full' => '7.6.1810', 193 | 'major' => '7', 194 | 'minor' => '6' 195 | } 196 | } 197 | } 198 | end 199 | 200 | let(:title) { 'foobar' } 201 | let(:params) do 202 | { 203 | ensure: 'absent', 204 | use_scl: false, 205 | scl_name: 'nodefault' 206 | } 207 | end 208 | 209 | it do 210 | is_expected.to compile 211 | read_command = '/usr/bin/cqlsh -e "DESC KEYSPACE foobar" localhost 9042' 212 | exec_command = '/usr/bin/cqlsh -e "DROP KEYSPACE foobar" localhost 9042' 213 | is_expected.to contain_exec(exec_command). 214 | only_with(onlyif: read_command, 215 | require: 'Exec[::cassandra::schema connection test]') 216 | end 217 | end 218 | 219 | context 'Set ensure to absent with SCL' do 220 | let :facts do 221 | { 222 | operatingsystemmajrelease: 7, 223 | osfamily: 'RedHat', 224 | os: { 225 | 'family' => 'RedHat', 226 | 'name' => 'RedHat', 227 | 'release' => { 228 | 'full' => '7.6.1810', 229 | 'major' => '7', 230 | 'minor' => '6' 231 | } 232 | } 233 | } 234 | end 235 | 236 | let(:title) { 'foobar' } 237 | let(:params) do 238 | { 239 | ensure: 'absent', 240 | use_scl: true, 241 | scl_name: 'testscl' 242 | } 243 | end 244 | 245 | it do 246 | is_expected.to compile 247 | read_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DESC KEYSPACE foobar\" localhost 9042"' 248 | exec_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DROP KEYSPACE foobar\" localhost 9042"' 249 | is_expected.to contain_exec(exec_command). 250 | only_with(onlyif: read_command, 251 | require: 'Exec[::cassandra::schema connection test]') 252 | end 253 | end 254 | 255 | context 'Set ensure to latest' do 256 | let :facts do 257 | { 258 | operatingsystemmajrelease: 7, 259 | osfamily: 'RedHat', 260 | os: { 261 | 'family' => 'RedHat', 262 | 'name' => 'RedHat', 263 | 'release' => { 264 | 'full' => '7.6.1810', 265 | 'major' => '7', 266 | 'minor' => '6' 267 | } 268 | } 269 | } 270 | end 271 | 272 | let(:title) { 'foobar' } 273 | 274 | let(:params) do 275 | { 276 | ensure: 'latest' 277 | } 278 | end 279 | 280 | it { is_expected.to raise_error(Puppet::Error) } 281 | end 282 | end 283 | -------------------------------------------------------------------------------- /spec/defines/schema/table_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandra::schema::table' do 4 | context 'Create Table' do 5 | let :facts do 6 | { 7 | operatingsystemmajrelease: 7, 8 | osfamily: 'RedHat', 9 | os: { 10 | 'family' => 'RedHat', 11 | 'name' => 'RedHat', 12 | 'release' => { 13 | 'full' => '7.6.1810', 14 | 'major' => '7', 15 | 'minor' => '6' 16 | } 17 | } 18 | } 19 | end 20 | 21 | let(:title) { 'users' } 22 | 23 | let(:params) do 24 | { 25 | use_scl: false, 26 | scl_name: 'nodefault', 27 | keyspace: 'Excelsior', 28 | columns: 29 | { 30 | 'userid' => 'text', 31 | 'username' => 'FROZEN', 32 | 'emails' => 'set', 33 | 'top_scores' => 'list', 34 | 'todo' => 'map', 35 | 'COLLECTION-TYPE' => 'tuple', 36 | 'PRIMARY KEY' => '(userid)' 37 | }, 38 | options: 39 | [ 40 | 'COMPACT STORAGE', 41 | 'ID=\'5a1c395e-b41f-11e5-9f22-ba0be0483c18\'' 42 | ] 43 | } 44 | end 45 | 46 | it do 47 | is_expected.to compile 48 | is_expected.to contain_cassandra__schema__table('users') 49 | read_command = '/usr/bin/cqlsh -e "DESC TABLE Excelsior.users" localhost 9042' 50 | exec_command = '/usr/bin/cqlsh -e "CREATE TABLE IF NOT EXISTS Excelsior.users ' 51 | exec_command += '(userid text, username FROZEN, emails set, top_scores list, ' 52 | exec_command += 'todo map, tuple, PRIMARY KEY (userid)) ' 53 | exec_command += 'WITH COMPACT STORAGE AND ID=\'5a1c395e-b41f-11e5-9f22-ba0be0483c18\'" localhost 9042' 54 | is_expected.to contain_exec(exec_command). 55 | only_with(unless: read_command, 56 | require: 'Exec[::cassandra::schema connection test]') 57 | end 58 | end 59 | 60 | context 'Create Table with SCL' do 61 | let :facts do 62 | { 63 | operatingsystemmajrelease: 7, 64 | osfamily: 'RedHat', 65 | os: { 66 | 'family' => 'RedHat', 67 | 'name' => 'RedHat', 68 | 'release' => { 69 | 'full' => '7.6.1810', 70 | 'major' => '7', 71 | 'minor' => '6' 72 | } 73 | } 74 | } 75 | end 76 | 77 | let(:title) { 'users' } 78 | 79 | let(:params) do 80 | { 81 | use_scl: true, 82 | scl_name: 'testscl', 83 | keyspace: 'Excelsior', 84 | columns: 85 | { 86 | 'userid' => 'text', 87 | 'username' => 'FROZEN', 88 | 'emails' => 'set', 89 | 'top_scores' => 'list', 90 | 'todo' => 'map', 91 | 'COLLECTION-TYPE' => 'tuple', 92 | 'PRIMARY KEY' => '(userid)' 93 | }, 94 | options: 95 | [ 96 | 'COMPACT STORAGE', 97 | 'ID=\'5a1c395e-b41f-11e5-9f22-ba0be0483c18\'' 98 | ] 99 | } 100 | end 101 | 102 | it do 103 | is_expected.to compile 104 | is_expected.to contain_cassandra__schema__table('users') 105 | read_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DESC TABLE Excelsior.users\" localhost 9042"' 106 | exec_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"CREATE TABLE IF NOT EXISTS Excelsior.users ' 107 | exec_command += '(userid text, username FROZEN, emails set, top_scores list, ' 108 | exec_command += 'todo map, tuple, PRIMARY KEY (userid)) ' 109 | exec_command += 'WITH COMPACT STORAGE AND ID=\'5a1c395e-b41f-11e5-9f22-ba0be0483c18\'\" localhost 9042"' 110 | is_expected.to contain_exec(exec_command). 111 | only_with(unless: read_command, 112 | require: 'Exec[::cassandra::schema connection test]') 113 | end 114 | end 115 | 116 | context 'Drop Table' do 117 | let :facts do 118 | { 119 | operatingsystemmajrelease: 7, 120 | osfamily: 'RedHat', 121 | os: { 122 | 'family' => 'RedHat', 123 | 'name' => 'RedHat', 124 | 'release' => { 125 | 'full' => '7.6.1810', 126 | 'major' => '7', 127 | 'minor' => '6' 128 | } 129 | } 130 | } 131 | end 132 | 133 | let(:title) { 'users' } 134 | 135 | let(:params) do 136 | { 137 | use_scl: false, 138 | scl_name: 'nodefault', 139 | keyspace: 'Excelsior', 140 | ensure: 'absent' 141 | } 142 | end 143 | 144 | it do 145 | is_expected.to compile 146 | read_command = '/usr/bin/cqlsh -e "DESC TABLE Excelsior.users" localhost 9042' 147 | exec_command = '/usr/bin/cqlsh -e "DROP TABLE IF EXISTS Excelsior.users" localhost 9042' 148 | is_expected.to contain_exec(exec_command). 149 | only_with(onlyif: read_command, 150 | require: 'Exec[::cassandra::schema connection test]') 151 | end 152 | end 153 | 154 | context 'Drop Table with SCL' do 155 | let :facts do 156 | { 157 | operatingsystemmajrelease: 7, 158 | osfamily: 'RedHat', 159 | os: { 160 | 'family' => 'RedHat', 161 | 'release' => { 162 | 'full' => '7.6.1810', 163 | 'major' => '7', 164 | 'minor' => '6' 165 | } 166 | } 167 | } 168 | end 169 | 170 | let(:title) { 'users' } 171 | 172 | let(:params) do 173 | { 174 | use_scl: true, 175 | scl_name: 'testscl', 176 | keyspace: 'Excelsior', 177 | ensure: 'absent' 178 | } 179 | end 180 | 181 | it do 182 | is_expected.to compile 183 | read_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DESC TABLE Excelsior.users\" localhost 9042"' 184 | exec_command = '/usr/bin/scl enable testscl "/usr/bin/cqlsh -e \"DROP TABLE IF EXISTS Excelsior.users\" localhost 9042"' 185 | is_expected.to contain_exec(exec_command). 186 | only_with(onlyif: read_command, 187 | require: 'Exec[::cassandra::schema connection test]') 188 | end 189 | end 190 | 191 | context 'Set ensure to latest' do 192 | let :facts do 193 | { 194 | operatingsystemmajrelease: 7, 195 | osfamily: 'RedHat', 196 | os: { 197 | 'family' => 'RedHat', 198 | 'name' => 'RedHat', 199 | 'release' => { 200 | 'full' => '7.6.1810', 201 | 'major' => '7', 202 | 'minor' => '6' 203 | } 204 | } 205 | } 206 | end 207 | 208 | let(:title) { 'foobar' } 209 | let(:params) do 210 | { 211 | ensure: 'latest' 212 | } 213 | end 214 | 215 | it { is_expected.to raise_error(Puppet::Error) } 216 | end 217 | end 218 | -------------------------------------------------------------------------------- /spec/spec_helper.rb: -------------------------------------------------------------------------------- 1 | # This file is managed via modulesync 2 | # https://github.com/voxpupuli/modulesync 3 | # https://github.com/voxpupuli/modulesync_config 4 | 5 | RSpec.configure do |c| 6 | c.mock_with :mocha 7 | end 8 | 9 | # puppetlabs_spec_helper will set up coverage if the env variable is set. 10 | # We want to do this if lib exists and it hasn't been explicitly set. 11 | ENV['COVERAGE'] ||= 'yes' if Dir.exist?(File.expand_path('../../lib', __FILE__)) 12 | 13 | require 'voxpupuli/test/spec_helper' 14 | 15 | if File.exist?(File.join(__dir__, 'default_module_facts.yml')) 16 | facts = YAML.safe_load(File.read(File.join(__dir__, 'default_module_facts.yml'))) 17 | if facts 18 | facts.each do |name, value| 19 | add_custom_fact name.to_sym, value 20 | end 21 | end 22 | end 23 | -------------------------------------------------------------------------------- /spec/unit/facter/cassandracmsheapnewsize_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandracmsheapnewsize' do 4 | before { Facter.clear } 5 | after { Facter.clear } 6 | 7 | describe 'Heap settings' do 8 | describe 'Rasberry Pi 3' do 9 | it do 10 | Facter.fact(:memorysize_mb).stubs(:value).returns('1024') 11 | Facter.fact(:processorcount).stubs(:value).returns('4') 12 | expect(Facter.fact(:cassandracmsheapnewsize).value).to be(128) 13 | end 14 | end 15 | 16 | describe 'm4.large' do 17 | it do 18 | Facter.fact(:memorysize_mb).stubs(:value).returns('8191.9') 19 | Facter.fact(:processorcount).stubs(:value).returns('2') 20 | expect(Facter.fact(:cassandracmsheapnewsize).value).to be(200) 21 | end 22 | end 23 | 24 | describe 'm4.xlarge' do 25 | it do 26 | Facter.fact(:memorysize_mb).stubs(:value).returns('16384') 27 | Facter.fact(:processorcount).stubs(:value).returns('2') 28 | expect(Facter.fact(:cassandracmsheapnewsize).value).to be(200) 29 | end 30 | end 31 | 32 | describe 'c4.2xlarge' do 33 | it do 34 | Facter.fact(:memorysize_mb).stubs(:value).returns('15360') 35 | Facter.fact(:processorcount).stubs(:value).returns('8') 36 | expect(Facter.fact(:cassandracmsheapnewsize).value).to be(800) 37 | end 38 | end 39 | 40 | describe 'i2.2xlarge' do 41 | it do 42 | Facter.fact(:memorysize_mb).stubs(:value).returns('62464') 43 | Facter.fact(:processorcount).stubs(:value).returns('8') 44 | expect(Facter.fact(:cassandracmsheapnewsize).value).to be(800) 45 | end 46 | end 47 | end 48 | end 49 | -------------------------------------------------------------------------------- /spec/unit/facter/cassandracmsmaxheapsize_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandracmsmaxheapsize' do 4 | before { Facter.clear } 5 | after { Facter.clear } 6 | 7 | describe 'Heap settings' do 8 | describe 'Rasberry Pi 3' do 9 | it do 10 | Facter.fact(:memorysize_mb).stubs(:value).returns('1024') 11 | Facter.fact(:processorcount).stubs(:value).returns('4') 12 | expect(Facter.fact(:cassandracmsmaxheapsize).value).to be(512) 13 | end 14 | end 15 | 16 | describe 'm4.large' do 17 | it do 18 | Facter.fact(:memorysize_mb).stubs(:value).returns('8191.9') 19 | Facter.fact(:processorcount).stubs(:value).returns('2') 20 | expect(Facter.fact(:cassandracmsmaxheapsize).value).to be(2048) 21 | end 22 | end 23 | 24 | describe 'm4.xlarge' do 25 | it do 26 | Facter.fact(:memorysize_mb).stubs(:value).returns('16384') 27 | Facter.fact(:processorcount).stubs(:value).returns('2') 28 | expect(Facter.fact(:cassandracmsmaxheapsize).value).to be(4096) 29 | end 30 | end 31 | 32 | describe 'c4.2xlarge' do 33 | it do 34 | Facter.fact(:memorysize_mb).stubs(:value).returns('15360') 35 | Facter.fact(:processorcount).stubs(:value).returns('8') 36 | expect(Facter.fact(:cassandracmsmaxheapsize).value).to be(3840) 37 | end 38 | end 39 | 40 | describe 'i2.2xlarge' do 41 | it do 42 | Facter.fact(:memorysize_mb).stubs(:value).returns('62464') 43 | Facter.fact(:processorcount).stubs(:value).returns('8') 44 | expect(Facter.fact(:cassandracmsmaxheapsize).value).to be(14_336) 45 | end 46 | end 47 | end 48 | end 49 | -------------------------------------------------------------------------------- /spec/unit/facter/cassandraheapnewsize_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandraheapnewsize' do 4 | before { Facter.clear } 5 | after { Facter.clear } 6 | 7 | describe 'Heap settings' do 8 | describe 'Rasberry Pi 3' do 9 | it do 10 | Facter.fact(:memorysize_mb).stubs(:value).returns('1024') 11 | Facter.fact(:processorcount).stubs(:value).returns('4') 12 | expect(Facter.fact(:cassandraheapnewsize).value).to be(128) 13 | end 14 | end 15 | 16 | describe 'm4.large' do 17 | it do 18 | Facter.fact(:memorysize_mb).stubs(:value).returns('8191.9') 19 | Facter.fact(:processorcount).stubs(:value).returns('2') 20 | expect(Facter.fact(:cassandraheapnewsize).value).to be(200) 21 | end 22 | end 23 | 24 | describe 'm4.xlarge' do 25 | it do 26 | Facter.fact(:memorysize_mb).stubs(:value).returns('16384') 27 | Facter.fact(:processorcount).stubs(:value).returns('2') 28 | expect(Facter.fact(:cassandraheapnewsize).value).to be(200) 29 | end 30 | end 31 | 32 | describe 'c4.2xlarge' do 33 | it do 34 | Facter.fact(:memorysize_mb).stubs(:value).returns('15360') 35 | Facter.fact(:processorcount).stubs(:value).returns('8') 36 | expect(Facter.fact(:cassandraheapnewsize).value).to be(800) 37 | end 38 | end 39 | 40 | describe 'i2.2xlarge' do 41 | it do 42 | Facter.fact(:memorysize_mb).stubs(:value).returns('62464') 43 | Facter.fact(:processorcount).stubs(:value).returns('8') 44 | expect(Facter.fact(:cassandraheapnewsize).value).to be(800) 45 | end 46 | end 47 | end 48 | end 49 | -------------------------------------------------------------------------------- /spec/unit/facter/cassandramajorversion_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandramajorversion' do 4 | before { Facter.clear } 5 | after { Facter.clear } 6 | 7 | describe 'cassandrarelease DSE' do 8 | it do 9 | Facter::Util::Resolution.stubs(:exec).with('nodetool version').returns('2.1.11.969') 10 | expect(Facter.fact(:cassandramajorversion).value).to be(2) 11 | end 12 | end 13 | 14 | describe 'cassandrarelease DDC' do 15 | it do 16 | Facter::Util::Resolution.stubs(:exec).with('nodetool version').returns('3.0.1') 17 | expect(Facter.fact(:cassandramajorversion).value).to be(3) 18 | end 19 | end 20 | 21 | describe 'Cassandra not installed or not running' do 22 | it do 23 | Facter::Util::Resolution.stubs(:exec).with('nodetool version').returns('') 24 | expect(Facter.fact(:cassandramajorversion).value).to be(nil) 25 | end 26 | end 27 | end 28 | -------------------------------------------------------------------------------- /spec/unit/facter/cassandramaxheapsize_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe ':cassandramaxheapsize' do 4 | before { Facter.clear } 5 | after { Facter.clear } 6 | 7 | describe 'Heap settings' do 8 | describe 'Rasberry Pi 3' do 9 | it do 10 | Facter.fact(:memorysize_mb).stubs(:value).returns('1024') 11 | Facter.fact(:processorcount).stubs(:value).returns('4') 12 | expect(Facter.fact(:cassandramaxheapsize).value).to eq(512) 13 | end 14 | end 15 | 16 | describe 'm4.large' do 17 | it do 18 | Facter.fact(:memorysize_mb).stubs(:value).returns('8191.9') 19 | Facter.fact(:processorcount).stubs(:value).returns('2') 20 | expect(Facter.fact(:cassandramaxheapsize).value).to be(2048) 21 | end 22 | end 23 | 24 | describe 'm4.xlarge' do 25 | it do 26 | Facter.fact(:memorysize_mb).stubs(:value).returns('16384') 27 | Facter.fact(:processorcount).stubs(:value).returns('2') 28 | expect(Facter.fact(:cassandramaxheapsize).value).to be(4096) 29 | end 30 | end 31 | 32 | describe 'c4.2xlarge' do 33 | it do 34 | Facter.fact(:memorysize_mb).stubs(:value).returns('15360') 35 | Facter.fact(:processorcount).stubs(:value).returns('8') 36 | expect(Facter.fact(:cassandramaxheapsize).value).to be(3840) 37 | end 38 | end 39 | 40 | describe 'i2.2xlarge' do 41 | it do 42 | Facter.fact(:memorysize_mb).stubs(:value).returns('62464') 43 | Facter.fact(:processorcount).stubs(:value).returns('8') 44 | expect(Facter.fact(:cassandramaxheapsize).value).to be(8192) 45 | end 46 | end 47 | end 48 | end 49 | -------------------------------------------------------------------------------- /spec/unit/facter/cassandraminorversion_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandraminorversion' do 4 | before { Facter.clear } 5 | after { Facter.clear } 6 | 7 | describe 'cassandrarelease DSE' do 8 | it do 9 | Facter::Util::Resolution.stubs(:exec).with('nodetool version').returns('2.1.11.969') 10 | expect(Facter.fact(:cassandraminorversion).value).to be(1) 11 | end 12 | end 13 | 14 | describe 'cassandrarelease DDC' do 15 | it do 16 | Facter::Util::Resolution.stubs(:exec).with('nodetool version').returns('3.0.1') 17 | expect(Facter.fact(:cassandraminorversion).value).to be(0) 18 | end 19 | end 20 | 21 | describe 'Cassandra not installed or not running' do 22 | it do 23 | Facter::Util::Resolution.stubs(:exec).with('nodetool version').returns('') 24 | expect(Facter.fact(:cassandraminorversion).value).to be(nil) 25 | end 26 | end 27 | end 28 | -------------------------------------------------------------------------------- /spec/unit/facter/cassandrapatchversion_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandrapatchversion' do 4 | before { Facter.clear } 5 | after { Facter.clear } 6 | 7 | describe 'cassandrarelease DSE' do 8 | it do 9 | Facter::Util::Resolution.stubs(:exec).with('nodetool version').returns('2.1.11.969') 10 | expect(Facter.fact(:cassandrapatchversion).value).to be(11) 11 | end 12 | end 13 | 14 | describe 'cassandrarelease DDC' do 15 | it do 16 | Facter::Util::Resolution.stubs(:exec).with('nodetool version').returns('3.0.1') 17 | expect(Facter.fact(:cassandrapatchversion).value).to be(1) 18 | end 19 | end 20 | 21 | describe 'Cassandra not installed or not running' do 22 | it do 23 | Facter::Util::Resolution.stubs(:exec).with('nodetool version').returns('') 24 | expect(Facter.fact(:cassandrapatchversion).value).to be(nil) 25 | end 26 | end 27 | end 28 | -------------------------------------------------------------------------------- /spec/unit/facter/cassandrarelease_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe 'cassandrarelease' do 4 | before { Facter.clear } 5 | after { Facter.clear } 6 | 7 | describe 'cassandrarelease DSE' do 8 | it do 9 | Facter::Util::Resolution.stubs(:exec).with('nodetool version').returns('2.1.11.969') 10 | expect(Facter.fact(:cassandrarelease).value).to eql('2.1.11') 11 | end 12 | end 13 | 14 | describe 'cassandrarelease DDC' do 15 | it do 16 | Facter::Util::Resolution.stubs(:exec).with('nodetool version').returns('3.0.1') 17 | expect(Facter.fact(:cassandrarelease).value).to eql('3.0.1') 18 | end 19 | end 20 | 21 | describe 'Cassandra not installed or not running' do 22 | it do 23 | Facter::Util::Resolution.stubs(:exec).with('nodetool version').returns('') 24 | expect(Facter.fact(:cassandrarelease).value).to be(nil) 25 | end 26 | end 27 | end 28 | -------------------------------------------------------------------------------- /templates/cassandra-rackdc.properties.erb: -------------------------------------------------------------------------------- 1 | # Licensed to the Apache Software Foundation (ASF) under one 2 | # or more contributor license agreements. See the NOTICE file 3 | # distributed with this work for additional information 4 | # regarding copyright ownership. The ASF licenses this file 5 | # to you under the Apache License, Version 2.0 (the 6 | # "License"); you may not use this file except in compliance 7 | # with the License. You may obtain a copy of the License at 8 | # 9 | # http://www.apache.org/licenses/LICENSE-2.0 10 | # 11 | # Unless required by applicable law or agreed to in writing, software 12 | # distributed under the License is distributed on an "AS IS" BASIS, 13 | # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 | # See the License for the specific language governing permissions and 15 | # limitations under the License. 16 | 17 | # These properties are used with GossipingPropertyFileSnitch and will 18 | # indicate the rack and dc for this node 19 | dc=<%= @dc %> 20 | rack=<%= @rack %> 21 | 22 | # Add a suffix to a datacenter name. Used by the Ec2Snitch and Ec2MultiRegionSnitch 23 | # to append a string to the EC2 region name. 24 | <% if @dc_suffix != nil %>dc_suffix=<%= @dc_suffix %><% else %>#dc_suffix=<% end %> 25 | 26 | # Uncomment the following line to make this snitch prefer the internal ip when possible, as the Ec2MultiRegionSnitch does. 27 | <% if @prefer_local != nil %>prefer_local=<%= @prefer_local %><% else %># prefer_local=true<% end %> 28 | -------------------------------------------------------------------------------- /templates/cassandra.yaml.erb: -------------------------------------------------------------------------------- 1 | # This file is managed by Puppet. Manual changes are likely to be 2 | # overwritten. If you see that the YAML indentation looks somewhat strange, 3 | # don't worry, please see the following ticket for more details. 4 | # https://tickets.puppetlabs.com/browse/PUP-3120 5 | <%= @merged_settings.to_yaml() %> 6 | -------------------------------------------------------------------------------- /templates/cqlshrc.erb: -------------------------------------------------------------------------------- 1 | ; Managed by Puppet 2 | ; --cqlshrc=CQLSHRC became available in 2.1 - does NOT work in 2.0 3 | 4 | [authentication] 5 | ;; If Cassandra has auth enabled, fill out these options 6 | <% if @cqlsh_user != nil %>username = <%= @cqlsh_user %><% else %>; username = fred<% end %> 7 | <% if @cqlsh_password != nil %>password = <%= @cqlsh_password %><% else %>; password = !!bang!!$<% end %> 8 | -------------------------------------------------------------------------------- /templates/dse.yaml.erb: -------------------------------------------------------------------------------- 1 | # This file is managed by Puppet. Manual changes are likely to be 2 | # overwritten. If you see that the YAML indentation looks somewhat strange, 3 | # don't worry, please see the following ticket for more details. 4 | # https://tickets.puppetlabs.com/browse/PUP-3120 5 | <%= @settings.to_yaml() %> 6 | -------------------------------------------------------------------------------- /vagrant/environment.conf: -------------------------------------------------------------------------------- 1 | # hardcoded module path is "fine" because we're in the "vagrant" directory in our source tree... 2 | modulepath = $codedir/environments/vagrant/modules 3 | -------------------------------------------------------------------------------- /vagrant/hiera.yaml: -------------------------------------------------------------------------------- 1 | --- 2 | :backends: 3 | - yaml 4 | :yaml: 5 | :datadir: /etc/puppetlabs/code/environments/vagrant/hieradata 6 | :hierarchy: 7 | - operatingsystem/%{operatingsystem}-%{operatingsystemmajrelease} 8 | - operatingsystem/%{operatingsystem} 9 | - common 10 | -------------------------------------------------------------------------------- /vagrant/manifests/site.pp: -------------------------------------------------------------------------------- 1 | require cassandra::java 2 | include cassandra::optutils 3 | 4 | class { 'cassandra::apache_repo': 5 | release => '310x', 6 | before => Class['cassandra', 'cassandra::optutils'], 7 | } 8 | 9 | class { 'cassandra': 10 | commitlog_directory => '/var/lib/cassandra/commitlog', 11 | data_file_directories => ['/var/lib/cassandra/data'], 12 | hints_directory => '/var/lib/cassandra/hints', 13 | saved_caches_directory => '/var/lib/cassandra/saved_caches', 14 | settings => { 15 | 'authenticator' => 'PasswordAuthenticator', 16 | 'authorizer' => 'CassandraAuthorizer', 17 | 'cluster_name' => 'MyCassandraCluster', 18 | 'commitlog_sync' => 'periodic', 19 | 'commitlog_sync_period_in_ms' => 10000, 20 | 'endpoint_snitch' => 'GossipingPropertyFileSnitch', 21 | 'listen_address' => $facts['networking']['ip'], 22 | 'partitioner' => 'org.apache.cassandra.dht.Murmur3Partitioner', 23 | 'seed_provider' => [ 24 | { 25 | 'class_name' => 'org.apache.cassandra.locator.SimpleSeedProvider', 26 | 'parameters' => [ 27 | { 28 | 'seeds' => $facts['networking']['ip'], 29 | }, 30 | ], 31 | }, 32 | ], 33 | 'start_native_transport' => true, 34 | }, 35 | service_ensure => running, 36 | } 37 | --------------------------------------------------------------------------------