cloud-mu 1.9.0.pre.beta
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/Berksfile +56 -0
- data/Berksfile.lock +250 -0
- data/Jenkinsfile +184 -0
- data/LICENSE.md +37 -0
- data/README.md +26 -0
- data/bin/mu-aws-setup +376 -0
- data/bin/mu-cleanup +68 -0
- data/bin/mu-configure +1133 -0
- data/bin/mu-deploy +166 -0
- data/bin/mu-firewall-allow-clients +30 -0
- data/bin/mu-gcp-setup +200 -0
- data/bin/mu-gen-docs +34 -0
- data/bin/mu-gen-env +42 -0
- data/bin/mu-load-config.rb +158 -0
- data/bin/mu-node-manage +683 -0
- data/bin/mu-self-update +228 -0
- data/bin/mu-ssh +23 -0
- data/bin/mu-tunnel-nagios +144 -0
- data/bin/mu-upload-chef-artifacts +757 -0
- data/bin/mu-user-manage +275 -0
- data/cookbooks/awscli/LICENSE +37 -0
- data/cookbooks/awscli/README.md +58 -0
- data/cookbooks/awscli/attributes/default.rb +1 -0
- data/cookbooks/awscli/libraries/instance_metadata.rb +21 -0
- data/cookbooks/awscli/metadata.rb +20 -0
- data/cookbooks/awscli/recipes/default.rb +56 -0
- data/cookbooks/awscli/templates/default/config.erb +18 -0
- data/cookbooks/mu-activedirectory/CHANGELOG.md +13 -0
- data/cookbooks/mu-activedirectory/LICENSE +37 -0
- data/cookbooks/mu-activedirectory/README.md +6 -0
- data/cookbooks/mu-activedirectory/attributes/default.rb +98 -0
- data/cookbooks/mu-activedirectory/files/default/password-auth +32 -0
- data/cookbooks/mu-activedirectory/files/default/sshd_pol.pp +0 -0
- data/cookbooks/mu-activedirectory/files/default/sshd_pol.te +32 -0
- data/cookbooks/mu-activedirectory/files/default/syslogd_oddjobd.pp +0 -0
- data/cookbooks/mu-activedirectory/files/default/syslogd_oddjobd.te +10 -0
- data/cookbooks/mu-activedirectory/files/default/system-auth +34 -0
- data/cookbooks/mu-activedirectory/files/default/winbindpol.pp +0 -0
- data/cookbooks/mu-activedirectory/files/default/winbindpol.te +37 -0
- data/cookbooks/mu-activedirectory/libraries/config.rb +106 -0
- data/cookbooks/mu-activedirectory/libraries/helper.rb +86 -0
- data/cookbooks/mu-activedirectory/metadata.rb +17 -0
- data/cookbooks/mu-activedirectory/providers/domain.rb +152 -0
- data/cookbooks/mu-activedirectory/providers/domain_controller.rb +89 -0
- data/cookbooks/mu-activedirectory/providers/domain_node.rb +275 -0
- data/cookbooks/mu-activedirectory/recipes/default.rb +8 -0
- data/cookbooks/mu-activedirectory/recipes/domain-controller.rb +44 -0
- data/cookbooks/mu-activedirectory/recipes/domain-node.rb +50 -0
- data/cookbooks/mu-activedirectory/recipes/domain.rb +43 -0
- data/cookbooks/mu-activedirectory/recipes/sssd.rb +185 -0
- data/cookbooks/mu-activedirectory/resources/domain.rb +25 -0
- data/cookbooks/mu-activedirectory/resources/domain_controller.rb +25 -0
- data/cookbooks/mu-activedirectory/resources/domain_node.rb +20 -0
- data/cookbooks/mu-activedirectory/templates/default/dhclient-eth0.conf.erb +4 -0
- data/cookbooks/mu-activedirectory/templates/default/interface +0 -0
- data/cookbooks/mu-activedirectory/templates/default/krb5.conf.erb +23 -0
- data/cookbooks/mu-activedirectory/templates/default/ntp.conf.erb +56 -0
- data/cookbooks/mu-activedirectory/templates/default/smb.conf.erb +33 -0
- data/cookbooks/mu-activedirectory/templates/default/sssd.conf.erb +60 -0
- data/cookbooks/mu-activedirectory/templates/windows/Backup.xml.erb +20 -0
- data/cookbooks/mu-activedirectory/templates/windows/bkupInfo.xml.erb +1 -0
- data/cookbooks/mu-activedirectory/templates/windows/gpreprt.xml.erb +198 -0
- data/cookbooks/mu-activedirectory/templates/windows/gptmpl.inf.erb +12 -0
- data/cookbooks/mu-activedirectory/templates/windows/manifest.xml.erb +1 -0
- data/cookbooks/mu-firewall/CHANGELOG.md +11 -0
- data/cookbooks/mu-firewall/LICENSE +37 -0
- data/cookbooks/mu-firewall/README.md +5 -0
- data/cookbooks/mu-firewall/attributes/default.rb +3 -0
- data/cookbooks/mu-firewall/metadata.rb +16 -0
- data/cookbooks/mu-firewall/recipes/default.rb +10 -0
- data/cookbooks/mu-glusterfs/CHANGELOG.md +13 -0
- data/cookbooks/mu-glusterfs/LICENSE +37 -0
- data/cookbooks/mu-glusterfs/README.md +5 -0
- data/cookbooks/mu-glusterfs/attributes/default.rb +34 -0
- data/cookbooks/mu-glusterfs/metadata.rb +17 -0
- data/cookbooks/mu-glusterfs/recipes/client.rb +62 -0
- data/cookbooks/mu-glusterfs/recipes/default.rb +16 -0
- data/cookbooks/mu-glusterfs/recipes/samba.rb +57 -0
- data/cookbooks/mu-glusterfs/recipes/server.rb +200 -0
- data/cookbooks/mu-glusterfs/templates/default/mu-gluster-client.erb +71 -0
- data/cookbooks/mu-glusterfs/templates/default/smb.conf.erb +14 -0
- data/cookbooks/mu-jenkins/CHANGELOG.md +13 -0
- data/cookbooks/mu-jenkins/LICENSE +37 -0
- data/cookbooks/mu-jenkins/README.md +105 -0
- data/cookbooks/mu-jenkins/attributes/default.rb +42 -0
- data/cookbooks/mu-jenkins/files/default/cleanup_deploy_config.xml +73 -0
- data/cookbooks/mu-jenkins/files/default/deploy_config.xml +44 -0
- data/cookbooks/mu-jenkins/metadata.rb +21 -0
- data/cookbooks/mu-jenkins/recipes/default.rb +195 -0
- data/cookbooks/mu-jenkins/recipes/node-ssh-config.rb +54 -0
- data/cookbooks/mu-jenkins/recipes/public_key.rb +24 -0
- data/cookbooks/mu-jenkins/templates/default/example_job.config.xml.erb +24 -0
- data/cookbooks/mu-jenkins/templates/default/org.jvnet.hudson.plugins.SSHBuildWrapper.xml.erb +14 -0
- data/cookbooks/mu-jenkins/templates/default/ssh_config.erb +6 -0
- data/cookbooks/mu-master/CHANGELOG.md +13 -0
- data/cookbooks/mu-master/LICENSE +37 -0
- data/cookbooks/mu-master/README.md +6 -0
- data/cookbooks/mu-master/attributes/default.rb +95 -0
- data/cookbooks/mu-master/files/default/0-mu-log-server.conf +19 -0
- data/cookbooks/mu-master/files/default/addRSA.ldif +8 -0
- data/cookbooks/mu-master/files/default/check_mem.pl +197 -0
- data/cookbooks/mu-master/files/default/cloudamatic.png +0 -0
- data/cookbooks/mu-master/files/default/dirsrv_admin.pp +0 -0
- data/cookbooks/mu-master/files/default/dirsrv_admin.te +13 -0
- data/cookbooks/mu-master/files/default/nagios_selinux.pp +0 -0
- data/cookbooks/mu-master/files/default/nagios_selinux.te +51 -0
- data/cookbooks/mu-master/files/default/nagios_selinux_7.pp +0 -0
- data/cookbooks/mu-master/files/default/nagios_selinux_7.te +17 -0
- data/cookbooks/mu-master/files/default/pam_sshd +18 -0
- data/cookbooks/mu-master/files/default/ssl_enable.ldif +18 -0
- data/cookbooks/mu-master/files/default/syslogd_oddjobd.pp +0 -0
- data/cookbooks/mu-master/files/default/syslogd_oddjobd.te +10 -0
- data/cookbooks/mu-master/files/default/vimrc +19 -0
- data/cookbooks/mu-master/libraries/mu.rb +29 -0
- data/cookbooks/mu-master/metadata.rb +30 -0
- data/cookbooks/mu-master/providers/user.rb +41 -0
- data/cookbooks/mu-master/recipes/389ds.rb +164 -0
- data/cookbooks/mu-master/recipes/basepackages.rb +58 -0
- data/cookbooks/mu-master/recipes/caching_nameserver.rb +37 -0
- data/cookbooks/mu-master/recipes/default.rb +451 -0
- data/cookbooks/mu-master/recipes/eks-kubectl.rb +41 -0
- data/cookbooks/mu-master/recipes/firewall-holes.rb +70 -0
- data/cookbooks/mu-master/recipes/init.rb +542 -0
- data/cookbooks/mu-master/recipes/ssl-certs.rb +109 -0
- data/cookbooks/mu-master/recipes/sssd.rb +89 -0
- data/cookbooks/mu-master/recipes/update_nagios_only.rb +242 -0
- data/cookbooks/mu-master/recipes/vault.rb +111 -0
- data/cookbooks/mu-master/resources/user.rb +19 -0
- data/cookbooks/mu-master/templates/default/389-directory-setup.inf.erb +28 -0
- data/cookbooks/mu-master/templates/default/chef-server.rb.erb +18 -0
- data/cookbooks/mu-master/templates/default/dhclient-eth0.conf.erb +9 -0
- data/cookbooks/mu-master/templates/default/mu-momma-cat.erb +149 -0
- data/cookbooks/mu-master/templates/default/mu.rc.erb +9 -0
- data/cookbooks/mu-master/templates/default/openssl.cnf.erb +354 -0
- data/cookbooks/mu-master/templates/default/sssd.conf.erb +44 -0
- data/cookbooks/mu-master/templates/default/web_app.conf.erb +90 -0
- data/cookbooks/mu-mongo/CHANGELOG.md +13 -0
- data/cookbooks/mu-mongo/LICENSE +37 -0
- data/cookbooks/mu-mongo/README.md +5 -0
- data/cookbooks/mu-mongo/attributes/default.rb +22 -0
- data/cookbooks/mu-mongo/files/default/keyfile +16 -0
- data/cookbooks/mu-mongo/files/default/remove_nodes.js +5 -0
- data/cookbooks/mu-mongo/metadata.rb +17 -0
- data/cookbooks/mu-mongo/recipes/default.rb +149 -0
- data/cookbooks/mu-mongo/recipes/yum-update-rule.rb +18 -0
- data/cookbooks/mu-mongo/templates/default/mongo_create_openfema_db.js.erb +2 -0
- data/cookbooks/mu-mongo/templates/default/mongo_init.js.erb +1 -0
- data/cookbooks/mu-mongo/templates/default/mongo_logrotate.erb +14 -0
- data/cookbooks/mu-mongo/templates/default/mongo_replset_addnodes.js.erb +6 -0
- data/cookbooks/mu-mongo/templates/default/replset_init.js.erb +2 -0
- data/cookbooks/mu-openvpn/CHANGELOG.md +13 -0
- data/cookbooks/mu-openvpn/LICENSE +37 -0
- data/cookbooks/mu-openvpn/README.md +6 -0
- data/cookbooks/mu-openvpn/attributes/default.rb +119 -0
- data/cookbooks/mu-openvpn/metadata.rb +18 -0
- data/cookbooks/mu-openvpn/recipes/default.rb +108 -0
- data/cookbooks/mu-openvpn/templates/default/users.json.erb +42 -0
- data/cookbooks/mu-php54/CHANGELOG.md +12 -0
- data/cookbooks/mu-php54/LICENSE +37 -0
- data/cookbooks/mu-php54/README.md +0 -0
- data/cookbooks/mu-php54/files/centos/php.ini +1802 -0
- data/cookbooks/mu-php54/files/ubuntu/php.ini +1870 -0
- data/cookbooks/mu-php54/metadata.rb +21 -0
- data/cookbooks/mu-php54/recipes/default.rb +97 -0
- data/cookbooks/mu-splunk/CHANGELOG.md +37 -0
- data/cookbooks/mu-splunk/LICENSE +37 -0
- data/cookbooks/mu-splunk/README.md +451 -0
- data/cookbooks/mu-splunk/attributes/default.rb +95 -0
- data/cookbooks/mu-splunk/attributes/upgrade.rb +49 -0
- data/cookbooks/mu-splunk/definitions/splunk_installer.rb +103 -0
- data/cookbooks/mu-splunk/files/default/splunk-nocheck +10 -0
- data/cookbooks/mu-splunk/libraries/helpers.rb +72 -0
- data/cookbooks/mu-splunk/libraries/splunk_app_provider.rb +156 -0
- data/cookbooks/mu-splunk/libraries/splunk_app_resource.rb +43 -0
- data/cookbooks/mu-splunk/metadata.json +30 -0
- data/cookbooks/mu-splunk/metadata.rb +17 -0
- data/cookbooks/mu-splunk/recipes/client.rb +143 -0
- data/cookbooks/mu-splunk/recipes/default.rb +31 -0
- data/cookbooks/mu-splunk/recipes/disabled.rb +41 -0
- data/cookbooks/mu-splunk/recipes/install_forwarder.rb +23 -0
- data/cookbooks/mu-splunk/recipes/install_server.rb +23 -0
- data/cookbooks/mu-splunk/recipes/server.rb +53 -0
- data/cookbooks/mu-splunk/recipes/service.rb +95 -0
- data/cookbooks/mu-splunk/recipes/setup_auth.rb +49 -0
- data/cookbooks/mu-splunk/recipes/setup_ssl.rb +63 -0
- data/cookbooks/mu-splunk/recipes/upgrade.rb +94 -0
- data/cookbooks/mu-splunk/recipes/user.rb +34 -0
- data/cookbooks/mu-splunk/templates/default/base_logs_unix_inputs.conf.erb +26 -0
- data/cookbooks/mu-splunk/templates/default/inputs.conf.erb +13 -0
- data/cookbooks/mu-splunk/templates/default/outputs.conf.erb +9 -0
- data/cookbooks/mu-splunk/templates/default/splunk-init.erb +74 -0
- data/cookbooks/mu-splunk/templates/default/system-web.conf.erb +7 -0
- data/cookbooks/mu-tools/CHANGELOG.md +12 -0
- data/cookbooks/mu-tools/LICENSE +37 -0
- data/cookbooks/mu-tools/README.md +188 -0
- data/cookbooks/mu-tools/attributes/default.rb +142 -0
- data/cookbooks/mu-tools/attributes/ebs_rolling_snapshots.rb +3 -0
- data/cookbooks/mu-tools/files/amazon/etc/freshclam.conf +235 -0
- data/cookbooks/mu-tools/files/centos/CentOS-Base.repo +52 -0
- data/cookbooks/mu-tools/files/centos/etc/bashrc +93 -0
- data/cookbooks/mu-tools/files/centos/etc/freshclam.conf +235 -0
- data/cookbooks/mu-tools/files/centos/etc/login.defs +72 -0
- data/cookbooks/mu-tools/files/centos/etc/profile +77 -0
- data/cookbooks/mu-tools/files/centos/etc/security/limits.conf +57 -0
- data/cookbooks/mu-tools/files/centos/etc/sysconfig/init +19 -0
- data/cookbooks/mu-tools/files/centos/etc/sysctl.conf +82 -0
- data/cookbooks/mu-tools/files/centos-6/README_MU +0 -0
- data/cookbooks/mu-tools/files/centos-6/etc/audit/stig.rules +173 -0
- data/cookbooks/mu-tools/files/centos-6/etc/bashrc +90 -0
- data/cookbooks/mu-tools/files/centos-6/etc/login.defs +70 -0
- data/cookbooks/mu-tools/files/centos-6/etc/pam.d/su +12 -0
- data/cookbooks/mu-tools/files/centos-6/etc/profile +83 -0
- data/cookbooks/mu-tools/files/centos-6/etc/securetty +12 -0
- data/cookbooks/mu-tools/files/centos-6/etc/sysconfig/init +30 -0
- data/cookbooks/mu-tools/files/centos-6/etc/sysctl.conf +40 -0
- data/cookbooks/mu-tools/files/default/Mu_CA.pem +34 -0
- data/cookbooks/mu-tools/files/default/PSWindowsUpdate.zip +0 -0
- data/cookbooks/mu-tools/files/default/ebs_snapshots.py +123 -0
- data/cookbooks/mu-tools/files/default/etc/BANNER +0 -0
- data/cookbooks/mu-tools/files/default/etc/BANNER-FEDERAL +19 -0
- data/cookbooks/mu-tools/files/default/gpo_no_uac.zip +0 -0
- data/cookbooks/mu-tools/files/default/mypol.pp +0 -0
- data/cookbooks/mu-tools/files/default/mypol.te +37 -0
- data/cookbooks/mu-tools/files/default/nrpe_c7.pp +0 -0
- data/cookbooks/mu-tools/files/default/nrpe_c7.te +31 -0
- data/cookbooks/mu-tools/files/default/nrpe_check_disk.pp +0 -0
- data/cookbooks/mu-tools/files/default/nrpe_check_disk.te +11 -0
- data/cookbooks/mu-tools/files/default/nrpe_disk.pp +0 -0
- data/cookbooks/mu-tools/files/default/nrpe_disk.te +10 -0
- data/cookbooks/mu-tools/files/default/nrpe_file.pp +0 -0
- data/cookbooks/mu-tools/files/default/nrpe_file.te +31 -0
- data/cookbooks/mu-tools/files/default/ntrights +0 -0
- data/cookbooks/mu-tools/files/default/serverclass.conf +18 -0
- data/cookbooks/mu-tools/files/default/splunk-apps/base_logs_unix/local/app.conf +1 -0
- data/cookbooks/mu-tools/files/default/splunk-apps/base_logs_unix/local/inputs.conf +13 -0
- data/cookbooks/mu-tools/files/default/splunk-apps/base_logs_windows/local/app.conf +1 -0
- data/cookbooks/mu-tools/files/default/splunk-apps/base_logs_windows/local/inputs.conf +8 -0
- data/cookbooks/mu-tools/files/default/sshd_pol.pp +0 -0
- data/cookbooks/mu-tools/files/default/sshd_pol.te +32 -0
- data/cookbooks/mu-tools/files/redhat/etc/bashrc +93 -0
- data/cookbooks/mu-tools/files/redhat/etc/freshclam.conf +235 -0
- data/cookbooks/mu-tools/files/redhat/etc/login.defs +72 -0
- data/cookbooks/mu-tools/files/redhat/etc/profile +77 -0
- data/cookbooks/mu-tools/files/redhat/etc/security/limits.conf +57 -0
- data/cookbooks/mu-tools/files/redhat/etc/sysconfig/init +19 -0
- data/cookbooks/mu-tools/files/redhat/etc/sysctl.conf +82 -0
- data/cookbooks/mu-tools/files/redhat-6/README_MU +0 -0
- data/cookbooks/mu-tools/files/redhat-6/etc/audit/stig.rules +173 -0
- data/cookbooks/mu-tools/files/redhat-6/etc/bashrc +90 -0
- data/cookbooks/mu-tools/files/redhat-6/etc/login.defs +70 -0
- data/cookbooks/mu-tools/files/redhat-6/etc/pam.d/su +12 -0
- data/cookbooks/mu-tools/files/redhat-6/etc/profile +83 -0
- data/cookbooks/mu-tools/files/redhat-6/etc/securetty +12 -0
- data/cookbooks/mu-tools/files/redhat-6/etc/sysconfig/init +30 -0
- data/cookbooks/mu-tools/files/redhat-6/etc/sysctl.conf +40 -0
- data/cookbooks/mu-tools/files/redhat-7.1/etc/freshclam.conf +235 -0
- data/cookbooks/mu-tools/files/ubuntu-12.04/etc/bash.bashrc +64 -0
- data/cookbooks/mu-tools/files/ubuntu-12.04/etc/common-session +30 -0
- data/cookbooks/mu-tools/files/ubuntu-12.04/etc/login.defs +338 -0
- data/cookbooks/mu-tools/files/ubuntu-12.04/etc/profile +30 -0
- data/cookbooks/mu-tools/files/ubuntu-12.04/etc/security/limits.conf +56 -0
- data/cookbooks/mu-tools/files/ubuntu-12.04/etc/sysctl.conf +60 -0
- data/cookbooks/mu-tools/libraries/helper.rb +292 -0
- data/cookbooks/mu-tools/metadata.rb +28 -0
- data/cookbooks/mu-tools/recipes/add_admin_ssh_keys.rb +35 -0
- data/cookbooks/mu-tools/recipes/apply_security.rb +440 -0
- data/cookbooks/mu-tools/recipes/aws_api.rb +23 -0
- data/cookbooks/mu-tools/recipes/base_repositories.rb +31 -0
- data/cookbooks/mu-tools/recipes/cisbenchmark.rb +59 -0
- data/cookbooks/mu-tools/recipes/clamav.rb +53 -0
- data/cookbooks/mu-tools/recipes/cloudinit.rb +58 -0
- data/cookbooks/mu-tools/recipes/configure_oracle_tools.rb +81 -0
- data/cookbooks/mu-tools/recipes/disable-requiretty.rb +22 -0
- data/cookbooks/mu-tools/recipes/ebs_rolling_snapshots.rb +75 -0
- data/cookbooks/mu-tools/recipes/efs.rb +70 -0
- data/cookbooks/mu-tools/recipes/eks.rb +160 -0
- data/cookbooks/mu-tools/recipes/gcloud.rb +98 -0
- data/cookbooks/mu-tools/recipes/google_api.rb +25 -0
- data/cookbooks/mu-tools/recipes/maldet.rb +67 -0
- data/cookbooks/mu-tools/recipes/nagios.rb +19 -0
- data/cookbooks/mu-tools/recipes/newclient.rb +23 -0
- data/cookbooks/mu-tools/recipes/nrpe.rb +115 -0
- data/cookbooks/mu-tools/recipes/python_pip.rb +35 -0
- data/cookbooks/mu-tools/recipes/retrieve_application.rb +51 -0
- data/cookbooks/mu-tools/recipes/rsyslog.rb +65 -0
- data/cookbooks/mu-tools/recipes/set_local_fw.rb +57 -0
- data/cookbooks/mu-tools/recipes/set_mu_hostname.rb +81 -0
- data/cookbooks/mu-tools/recipes/split_var_partitions.rb +86 -0
- data/cookbooks/mu-tools/recipes/splunk-client.rb +69 -0
- data/cookbooks/mu-tools/recipes/splunk-server.rb +104 -0
- data/cookbooks/mu-tools/recipes/store_inspec_attr.rb +8 -0
- data/cookbooks/mu-tools/recipes/updates.rb +96 -0
- data/cookbooks/mu-tools/recipes/windows-client.rb +202 -0
- data/cookbooks/mu-tools/resources/aws_windows.rb +33 -0
- data/cookbooks/mu-tools/resources/disk.rb +88 -0
- data/cookbooks/mu-tools/resources/mommacat_request.rb +11 -0
- data/cookbooks/mu-tools/resources/scheduled_tasks.rb +29 -0
- data/cookbooks/mu-tools/resources/sshd_service.rb +45 -0
- data/cookbooks/mu-tools/resources/windows_users.rb +242 -0
- data/cookbooks/mu-tools/templates/amazon/sshd_config.erb +168 -0
- data/cookbooks/mu-tools/templates/centos-6/sshd_config.erb +212 -0
- data/cookbooks/mu-tools/templates/centos-7/sshd_config.erb +215 -0
- data/cookbooks/mu-tools/templates/default/0-mu-log-client.conf.erb +13 -0
- data/cookbooks/mu-tools/templates/default/conf.maldet.erb +137 -0
- data/cookbooks/mu-tools/templates/default/etc_hosts.erb +30 -0
- data/cookbooks/mu-tools/templates/default/etc_pamd_password-auth.erb +14 -0
- data/cookbooks/mu-tools/templates/default/etc_pamd_system-auth.erb +14 -0
- data/cookbooks/mu-tools/templates/default/etc_sysconfig_network.erb +12 -0
- data/cookbooks/mu-tools/templates/default/kubeconfig.erb +29 -0
- data/cookbooks/mu-tools/templates/default/kubelet.service.erb +35 -0
- data/cookbooks/mu-tools/templates/default/maldet_scanall.sh.erb +15 -0
- data/cookbooks/mu-tools/templates/default/nrpe.cfg.erb +233 -0
- data/cookbooks/mu-tools/templates/redhat-6/sshd_config.erb +213 -0
- data/cookbooks/mu-tools/templates/redhat-7/sshd_config.erb +215 -0
- data/cookbooks/mu-tools/templates/ubuntu-12.04/sshd_config.erb +146 -0
- data/cookbooks/mu-tools/templates/ubuntu-14.04/sshd_config.erb +145 -0
- data/cookbooks/mu-tools/templates/windows/Backup.xml.erb +20 -0
- data/cookbooks/mu-tools/templates/windows/bkupInfo.xml.erb +1 -0
- data/cookbooks/mu-tools/templates/windows/gpreprt.xml.erb +214 -0
- data/cookbooks/mu-tools/templates/windows/gptmpl.inf.erb +12 -0
- data/cookbooks/mu-tools/templates/windows/manifest.xml.erb +1 -0
- data/cookbooks/mu-tools/templates/windows/set_ad_dns_scheduled_task.ps1.erb +6 -0
- data/cookbooks/mu-tools/templates/windows/sshd_config.erb +136 -0
- data/cookbooks/mu-utility/CHANGELOG.md +12 -0
- data/cookbooks/mu-utility/LICENSE +37 -0
- data/cookbooks/mu-utility/README.md +6 -0
- data/cookbooks/mu-utility/attributes/default.rb +1 -0
- data/cookbooks/mu-utility/libraries/matchers.rb +21 -0
- data/cookbooks/mu-utility/metadata.rb +16 -0
- data/cookbooks/mu-utility/recipes/apt.rb +23 -0
- data/cookbooks/mu-utility/recipes/cleanup_image_helper.rb +118 -0
- data/cookbooks/mu-utility/recipes/iptables.rb +26 -0
- data/cookbooks/mu-utility/recipes/luks.rb +18 -0
- data/cookbooks/mu-utility/recipes/nat.rb +104 -0
- data/cookbooks/mu-utility/recipes/php.rb +33 -0
- data/cookbooks/mu-utility/recipes/rdp_gateway.rb +83 -0
- data/cookbooks/mu-utility/recipes/remi.rb +44 -0
- data/cookbooks/mu-utility/recipes/vim.rb +26 -0
- data/cookbooks/mu-utility/recipes/windows_basics.rb +37 -0
- data/cookbooks/mu-utility/recipes/zip.rb +26 -0
- data/cookbooks/mu-utility/templates/default/BundleConfig.xml.erb +34 -0
- data/cookbooks/mu-utility/templates/default/config.xml.erb +60 -0
- data/cookbooks/nagios/Berksfile +8 -0
- data/cookbooks/nagios/CHANGELOG.md +589 -0
- data/cookbooks/nagios/CONTRIBUTING.md +11 -0
- data/cookbooks/nagios/LICENSE +37 -0
- data/cookbooks/nagios/README.md +328 -0
- data/cookbooks/nagios/TESTING.md +2 -0
- data/cookbooks/nagios/attributes/config.rb +171 -0
- data/cookbooks/nagios/attributes/default.rb +228 -0
- data/cookbooks/nagios/chefignore +102 -0
- data/cookbooks/nagios/definitions/command.rb +33 -0
- data/cookbooks/nagios/definitions/contact.rb +33 -0
- data/cookbooks/nagios/definitions/contactgroup.rb +33 -0
- data/cookbooks/nagios/definitions/host.rb +33 -0
- data/cookbooks/nagios/definitions/hostdependency.rb +33 -0
- data/cookbooks/nagios/definitions/hostescalation.rb +34 -0
- data/cookbooks/nagios/definitions/hostgroup.rb +33 -0
- data/cookbooks/nagios/definitions/nagios_conf.rb +38 -0
- data/cookbooks/nagios/definitions/resource.rb +33 -0
- data/cookbooks/nagios/definitions/service.rb +33 -0
- data/cookbooks/nagios/definitions/servicedependency.rb +33 -0
- data/cookbooks/nagios/definitions/serviceescalation.rb +34 -0
- data/cookbooks/nagios/definitions/servicegroup.rb +33 -0
- data/cookbooks/nagios/definitions/timeperiod.rb +33 -0
- data/cookbooks/nagios/libraries/base.rb +314 -0
- data/cookbooks/nagios/libraries/command.rb +91 -0
- data/cookbooks/nagios/libraries/contact.rb +230 -0
- data/cookbooks/nagios/libraries/contactgroup.rb +112 -0
- data/cookbooks/nagios/libraries/custom_option.rb +36 -0
- data/cookbooks/nagios/libraries/data_bag_helper.rb +23 -0
- data/cookbooks/nagios/libraries/default.rb +90 -0
- data/cookbooks/nagios/libraries/host.rb +412 -0
- data/cookbooks/nagios/libraries/hostdependency.rb +181 -0
- data/cookbooks/nagios/libraries/hostescalation.rb +173 -0
- data/cookbooks/nagios/libraries/hostgroup.rb +119 -0
- data/cookbooks/nagios/libraries/nagios.rb +282 -0
- data/cookbooks/nagios/libraries/resource.rb +59 -0
- data/cookbooks/nagios/libraries/service.rb +455 -0
- data/cookbooks/nagios/libraries/servicedependency.rb +215 -0
- data/cookbooks/nagios/libraries/serviceescalation.rb +195 -0
- data/cookbooks/nagios/libraries/servicegroup.rb +144 -0
- data/cookbooks/nagios/libraries/timeperiod.rb +160 -0
- data/cookbooks/nagios/libraries/users_helper.rb +54 -0
- data/cookbooks/nagios/metadata.rb +25 -0
- data/cookbooks/nagios/recipes/_load_databag_config.rb +153 -0
- data/cookbooks/nagios/recipes/_load_default_config.rb +241 -0
- data/cookbooks/nagios/recipes/apache.rb +48 -0
- data/cookbooks/nagios/recipes/default.rb +204 -0
- data/cookbooks/nagios/recipes/nginx.rb +82 -0
- data/cookbooks/nagios/recipes/pagerduty.rb +143 -0
- data/cookbooks/nagios/recipes/server_package.rb +40 -0
- data/cookbooks/nagios/recipes/server_source.rb +164 -0
- data/cookbooks/nagios/templates/default/apache2.conf.erb +96 -0
- data/cookbooks/nagios/templates/default/cgi.cfg.erb +266 -0
- data/cookbooks/nagios/templates/default/commands.cfg.erb +13 -0
- data/cookbooks/nagios/templates/default/contacts.cfg.erb +37 -0
- data/cookbooks/nagios/templates/default/hostgroups.cfg.erb +25 -0
- data/cookbooks/nagios/templates/default/hosts.cfg.erb +15 -0
- data/cookbooks/nagios/templates/default/htpasswd.users.erb +6 -0
- data/cookbooks/nagios/templates/default/nagios.cfg.erb +22 -0
- data/cookbooks/nagios/templates/default/nginx.conf.erb +62 -0
- data/cookbooks/nagios/templates/default/pagerduty.cgi.erb +185 -0
- data/cookbooks/nagios/templates/default/resource.cfg.erb +27 -0
- data/cookbooks/nagios/templates/default/servicedependencies.cfg.erb +15 -0
- data/cookbooks/nagios/templates/default/servicegroups.cfg.erb +14 -0
- data/cookbooks/nagios/templates/default/services.cfg.erb +14 -0
- data/cookbooks/nagios/templates/default/templates.cfg.erb +31 -0
- data/cookbooks/nagios/templates/default/timeperiods.cfg.erb +13 -0
- data/cookbooks/s3fs/CHANGELOG.md +13 -0
- data/cookbooks/s3fs/LICENSE +37 -0
- data/cookbooks/s3fs/README.md +6 -0
- data/cookbooks/s3fs/attributes/default.rb +15 -0
- data/cookbooks/s3fs/files/default/fuse-2.9.3.zip +0 -0
- data/cookbooks/s3fs/metadata.rb +16 -0
- data/cookbooks/s3fs/recipes/default.rb +91 -0
- data/data_bags/demo/app.json +7 -0
- data/data_bags/nagios_services/chef.json +6 -0
- data/data_bags/nagios_services/linux_diskspace.json +5 -0
- data/data_bags/nagios_services/momma_cat.json +6 -0
- data/data_bags/nagios_services/mu-master-memory.json +5 -0
- data/data_bags/nagios_services/nagios_ui.json +6 -0
- data/data_bags/nagios_services/node_ssh.json +6 -0
- data/data_bags/nagios_services/ssh.json +6 -0
- data/demo/lambda_test.yaml +29 -0
- data/environments/DEV.json +8 -0
- data/environments/PROD.json +8 -0
- data/environments/dev.json +8 -0
- data/environments/development.json +8 -0
- data/environments/prod.json +8 -0
- data/extras/README.md +1 -0
- data/extras/admin-role-binding.yaml +16 -0
- data/extras/admin-user.yaml +6 -0
- data/extras/aws-auth-cm.yaml.erb +12 -0
- data/extras/clean-stock-amis +48 -0
- data/extras/git-fix-permissions-hook +12 -0
- data/extras/gitlab-eks-helper.sh.erb +20 -0
- data/extras/image-generators/README.md +2 -0
- data/extras/image-generators/aws/centos6.yaml +18 -0
- data/extras/image-generators/aws/centos7-govcloud.yaml +24 -0
- data/extras/image-generators/aws/centos7.yaml +17 -0
- data/extras/image-generators/aws/rhel7.yaml +17 -0
- data/extras/image-generators/aws/win2k12.yaml +16 -0
- data/extras/image-generators/aws/win2k16.yaml +16 -0
- data/extras/image-generators/aws/windows.yaml +18 -0
- data/extras/image-generators/gcp/centos6.yaml +17 -0
- data/extras/lambda_waf_domain_blacklist.py +103 -0
- data/extras/platform_berksfile_base +50 -0
- data/extras/ruby_rpm/build.sh +17 -0
- data/extras/ruby_rpm/muby.spec +44 -0
- data/extras/vault_tools/README.md +6 -0
- data/extras/vault_tools/export_vaults.sh +3 -0
- data/extras/vault_tools/recreate_vaults.sh +5 -0
- data/extras/vault_tools/test_vaults.sh +5 -0
- data/install/README.md +8 -0
- data/install/cfn_create_mu_master.json +1034 -0
- data/install/chef-server.rb.erb +19 -0
- data/install/deprecated-bash-library.sh +1891 -0
- data/install/images/Usage.png +0 -0
- data/install/installer +71 -0
- data/install/jenkinskeys.rb +8 -0
- data/install/user-dot-murc.erb +14 -0
- data/modules/html.erb +19 -0
- data/modules/mommacat.ru +426 -0
- data/modules/mu/cleanup.rb +339 -0
- data/modules/mu/cloud.rb +1446 -0
- data/modules/mu/clouds/README.md +201 -0
- data/modules/mu/clouds/aws/alarm.rb +319 -0
- data/modules/mu/clouds/aws/cache_cluster.rb +1010 -0
- data/modules/mu/clouds/aws/collection.rb +373 -0
- data/modules/mu/clouds/aws/container_cluster.rb +667 -0
- data/modules/mu/clouds/aws/database.rb +1836 -0
- data/modules/mu/clouds/aws/dnszone.rb +911 -0
- data/modules/mu/clouds/aws/firewall_rule.rb +641 -0
- data/modules/mu/clouds/aws/folder.rb +92 -0
- data/modules/mu/clouds/aws/function.rb +349 -0
- data/modules/mu/clouds/aws/group.rb +251 -0
- data/modules/mu/clouds/aws/loadbalancer.rb +888 -0
- data/modules/mu/clouds/aws/log.rb +363 -0
- data/modules/mu/clouds/aws/msg_queue.rb +480 -0
- data/modules/mu/clouds/aws/notification.rb +139 -0
- data/modules/mu/clouds/aws/role.rb +656 -0
- data/modules/mu/clouds/aws/search_domain.rb +646 -0
- data/modules/mu/clouds/aws/server.rb +2294 -0
- data/modules/mu/clouds/aws/server_pool.rb +1388 -0
- data/modules/mu/clouds/aws/storage_pool.rb +495 -0
- data/modules/mu/clouds/aws/user.rb +382 -0
- data/modules/mu/clouds/aws/userdata/README.md +4 -0
- data/modules/mu/clouds/aws/userdata/linux.erb +179 -0
- data/modules/mu/clouds/aws/userdata/windows.erb +278 -0
- data/modules/mu/clouds/aws/vpc.rb +1943 -0
- data/modules/mu/clouds/aws.rb +1009 -0
- data/modules/mu/clouds/cloudformation/alarm.rb +146 -0
- data/modules/mu/clouds/cloudformation/cache_cluster.rb +167 -0
- data/modules/mu/clouds/cloudformation/collection.rb +117 -0
- data/modules/mu/clouds/cloudformation/database.rb +278 -0
- data/modules/mu/clouds/cloudformation/dnszone.rb +274 -0
- data/modules/mu/clouds/cloudformation/firewall_rule.rb +308 -0
- data/modules/mu/clouds/cloudformation/loadbalancer.rb +193 -0
- data/modules/mu/clouds/cloudformation/log.rb +170 -0
- data/modules/mu/clouds/cloudformation/server.rb +370 -0
- data/modules/mu/clouds/cloudformation/server_pool.rb +279 -0
- data/modules/mu/clouds/cloudformation/vpc.rb +322 -0
- data/modules/mu/clouds/cloudformation.rb +733 -0
- data/modules/mu/clouds/docker.rb +30 -0
- data/modules/mu/clouds/google/container_cluster.rb +290 -0
- data/modules/mu/clouds/google/database.rb +152 -0
- data/modules/mu/clouds/google/firewall_rule.rb +267 -0
- data/modules/mu/clouds/google/group.rb +164 -0
- data/modules/mu/clouds/google/loadbalancer.rb +479 -0
- data/modules/mu/clouds/google/server.rb +1510 -0
- data/modules/mu/clouds/google/server_pool.rb +274 -0
- data/modules/mu/clouds/google/user.rb +266 -0
- data/modules/mu/clouds/google/userdata/README.md +4 -0
- data/modules/mu/clouds/google/userdata/linux.erb +137 -0
- data/modules/mu/clouds/google/userdata/windows.erb +275 -0
- data/modules/mu/clouds/google/vpc.rb +890 -0
- data/modules/mu/clouds/google.rb +811 -0
- data/modules/mu/config/README.md +11 -0
- data/modules/mu/config/alarm.rb +271 -0
- data/modules/mu/config/cache_cluster.rb +172 -0
- data/modules/mu/config/collection.rb +87 -0
- data/modules/mu/config/container_cluster.rb +103 -0
- data/modules/mu/config/container_cluster.yml +36 -0
- data/modules/mu/config/database.rb +458 -0
- data/modules/mu/config/database.yml +26 -0
- data/modules/mu/config/dnszone.rb +327 -0
- data/modules/mu/config/firewall_rule.rb +118 -0
- data/modules/mu/config/folder.rb +70 -0
- data/modules/mu/config/function.rb +140 -0
- data/modules/mu/config/group.rb +64 -0
- data/modules/mu/config/loadbalancer.rb +482 -0
- data/modules/mu/config/log.rb +47 -0
- data/modules/mu/config/log.yml +6 -0
- data/modules/mu/config/msg_queue.rb +47 -0
- data/modules/mu/config/msg_queue.yml +9 -0
- data/modules/mu/config/notification.rb +44 -0
- data/modules/mu/config/project.rb +71 -0
- data/modules/mu/config/role.rb +102 -0
- data/modules/mu/config/search_domain.rb +61 -0
- data/modules/mu/config/search_domain.yml +25 -0
- data/modules/mu/config/server.rb +587 -0
- data/modules/mu/config/server.yml +8 -0
- data/modules/mu/config/server_pool.rb +216 -0
- data/modules/mu/config/server_pool.yml +71 -0
- data/modules/mu/config/storage_pool.rb +145 -0
- data/modules/mu/config/user.rb +78 -0
- data/modules/mu/config/vpc.rb +743 -0
- data/modules/mu/config/vpc.yml +6 -0
- data/modules/mu/config.rb +2000 -0
- data/modules/mu/defaults/README.md +2 -0
- data/modules/mu/defaults/amazon_images.yaml +121 -0
- data/modules/mu/defaults/google_images.yaml +16 -0
- data/modules/mu/deploy.rb +686 -0
- data/modules/mu/groomer.rb +123 -0
- data/modules/mu/groomers/README.md +58 -0
- data/modules/mu/groomers/chef.rb +1024 -0
- data/modules/mu/kittens.rb +11319 -0
- data/modules/mu/logger.rb +208 -0
- data/modules/mu/master/README.md +27 -0
- data/modules/mu/master/chef.rb +471 -0
- data/modules/mu/master/ldap.rb +1005 -0
- data/modules/mu/master.rb +415 -0
- data/modules/mu/mommacat.rb +2703 -0
- data/modules/mu-load-config.rb +1 -0
- data/modules/mu.rb +724 -0
- data/modules/scratchpad.erb +1 -0
- data/modules/tests/super_complex_bok.yml +41 -0
- data/modules/tests/super_simple_bok.yml +40 -0
- data/mu.gemspec +62 -0
- data/roles/demo-dbservice-configure.json +19 -0
- data/roles/demo-portal-configure.json +19 -0
- data/roles/mu-master-jenkins.json +24 -0
- data/roles/mu-master-nagios-only.json +13 -0
- data/roles/mu-master.json +12 -0
- data/roles/mu-node.json +19 -0
- data/roles/mu-splunk-server.json +13 -0
- data/roles/mu-splunk.json +13 -0
- data/test/clean_up.py +25 -0
- data/test/demo-test-profile/README.md +3 -0
- data/test/demo-test-profile/controls/flask.rb +84 -0
- data/test/demo-test-profile/inspec.lock +7 -0
- data/test/demo-test-profile/inspec.yml +11 -0
- data/test/etco-test-profile/README.md +3 -0
- data/test/etco-test-profile/controls/all-in-one.rb +182 -0
- data/test/etco-test-profile/inspec.lock +7 -0
- data/test/etco-test-profile/inspec.yml +11 -0
- data/test/exec_inspec.py +246 -0
- data/test/exec_mu_install.py +241 -0
- data/test/exec_retry.py +44 -0
- data/test/mu-master-test/README.md +3 -0
- data/test/mu-master-test/controls/all_in_one.rb +557 -0
- data/test/mu-master-test/inspec.lock +3 -0
- data/test/mu-master-test/inspec.yml +11 -0
- data/test/mu-tools-test/README.md +3 -0
- data/test/mu-tools-test/controls/base.rb +265 -0
- data/test/mu-tools-test/inspec.lock +3 -0
- data/test/mu-tools-test/inspec.yml +8 -0
- data/test/simple-server-php-test/README.md +3 -0
- data/test/simple-server-php-test/controls/apachephp.rb +25 -0
- data/test/simple-server-php-test/controls/example.rb +19 -0
- data/test/simple-server-php-test/inspec.lock +7 -0
- data/test/simple-server-php-test/inspec.yml +12 -0
- data/test/simple-server-rails-test/README.md +3 -0
- data/test/simple-server-rails-test/controls/rails.rb +188 -0
- data/test/simple-server-rails-test/inspec.lock +7 -0
- data/test/simple-server-rails-test/inspec.yml +11 -0
- data/test/simple-windows-test/README.md +3 -0
- data/test/simple-windows-test/controls/windows.rb +20 -0
- data/test/simple-windows-test/inspec.lock +7 -0
- data/test/simple-windows-test/inspec.yml +11 -0
- data/test/smoke_test.rb +75 -0
- data/test/wordpress-test/README.md +3 -0
- data/test/wordpress-test/controls/wordpress.rb +97 -0
- data/test/wordpress-test/inspec.lock +7 -0
- data/test/wordpress-test/inspec.yml +11 -0
- metadata +979 -0
|
@@ -0,0 +1,1010 @@
|
|
|
1
|
+
# Copyright:: Copyright (c) 2014 eGlobalTech, Inc., all rights reserved
|
|
2
|
+
#
|
|
3
|
+
# Licensed under the BSD-3 license (the "License");
|
|
4
|
+
# you may not use this file except in compliance with the License.
|
|
5
|
+
# You may obtain a copy of the License in the root of the project or at
|
|
6
|
+
#
|
|
7
|
+
# http://egt-labs.com/mu/LICENSE.html
|
|
8
|
+
#
|
|
9
|
+
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
+
# See the License for the specific language governing permissions and
|
|
13
|
+
# limitations under the License.
|
|
14
|
+
|
|
15
|
+
module MU
|
|
16
|
+
class Cloud
|
|
17
|
+
class AWS
|
|
18
|
+
# A cache cluster as configured in {MU::Config::BasketofKittens::cache_clusters}
|
|
19
|
+
class CacheCluster < MU::Cloud::CacheCluster
|
|
20
|
+
@deploy = nil
|
|
21
|
+
@config = nil
|
|
22
|
+
attr_reader :mu_name
|
|
23
|
+
attr_reader :cloud_id
|
|
24
|
+
attr_reader :config
|
|
25
|
+
|
|
26
|
+
@cloudformation_data = {}
|
|
27
|
+
attr_reader :cloudformation_data
|
|
28
|
+
|
|
29
|
+
# @param mommacat [MU::MommaCat]: A {MU::Mommacat} object containing the deploy of which this resource is/will be a member.
|
|
30
|
+
# @param kitten_cfg [Hash]: The fully parsed and resolved {MU::Config} resource descriptor as defined in {MU::Config::BasketofKittens::cache_clusters}
|
|
31
|
+
def initialize(mommacat: nil, kitten_cfg: nil, mu_name: nil, cloud_id: nil)
|
|
32
|
+
@deploy = mommacat
|
|
33
|
+
@config = MU::Config.manxify(kitten_cfg)
|
|
34
|
+
@cloud_id ||= cloud_id
|
|
35
|
+
# @mu_name = mu_name ? mu_name : @deploy.getResourceName(@config["name"])
|
|
36
|
+
|
|
37
|
+
@mu_name ||=
|
|
38
|
+
if @config["create_replication_group"]
|
|
39
|
+
@deploy.getResourceName(@config["name"], max_length: 16, need_unique_string: true)
|
|
40
|
+
else
|
|
41
|
+
@deploy.getResourceName(@config["name"], max_length: 20, need_unique_string: true)
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
@mu_name.gsub!(/(--|-$)/i, "")
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
# Canonical Amazon Resource Number for this resource
|
|
48
|
+
# @return [String]
|
|
49
|
+
def arn
|
|
50
|
+
"arn:"+(MU::Cloud::AWS.isGovCloud?(@config["region"]) ? "aws-us-gov" : "aws")+":elasticache:"+@config['region']+":"+MU.account_number+":cluster/"+@cloud_id
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
# Locate an existing Cache Cluster or Cache Clusters and return an array containing matching AWS resource descriptors for those that match.
|
|
54
|
+
# @param cloud_id [String]: The cloud provider's identifier for this resource.
|
|
55
|
+
# @param region [String]: The cloud provider region.
|
|
56
|
+
# @param tag_key [String]: A tag key to search.
|
|
57
|
+
# @param tag_value [String]: The value of the tag specified by tag_key to match when searching by tag.
|
|
58
|
+
# @param flags [Hash]: Optional flags
|
|
59
|
+
# @return [Array<Hash<String,OpenStruct>>]: The cloud provider's complete descriptions of matching Cache Clusters.
|
|
60
|
+
def self.find(cloud_id: nil, region: MU.curRegion, tag_key: "Name", tag_value: nil, flags: {})
|
|
61
|
+
map = {}
|
|
62
|
+
if cloud_id
|
|
63
|
+
cache_cluster = MU::Cloud::AWS::CacheCluster.getCacheClusterById(cloud_id, region: region)
|
|
64
|
+
map[cloud_id] = cache_cluster if cache_cluster
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
if tag_value
|
|
68
|
+
MU::Cloud::AWS.elasticache(region).describe_cache_clusters.cache_clusters.each { |cc|
|
|
69
|
+
resp = MU::Cloud::AWS.elasticache(region).list_tags_for_resource(
|
|
70
|
+
resource_name: MU::Cloud::AWS::CacheCluster.getARN(cc.cache_cluster_id, "cluster", "elasticache", region: region)
|
|
71
|
+
)
|
|
72
|
+
if resp && resp.tag_list && !resp.tag_list.empty?
|
|
73
|
+
resp.tag_list.each { |tag|
|
|
74
|
+
map[cc.cache_cluster_id] = cc if tag.key == tag_key and tag.value == tag_value
|
|
75
|
+
}
|
|
76
|
+
end
|
|
77
|
+
}
|
|
78
|
+
end
|
|
79
|
+
|
|
80
|
+
return map
|
|
81
|
+
end
|
|
82
|
+
|
|
83
|
+
# Construct an Amazon Resource Name for an AWS resource.
|
|
84
|
+
# Some APIs require this identifier in order to do things that other APIs can do with shorthand.
|
|
85
|
+
# @param resource [String]: The name of the resource
|
|
86
|
+
# @param client_type [String]: The name of the client (eg. elasticache, rds, ec2, s3)
|
|
87
|
+
# @param resource_type [String]: The type of the resource
|
|
88
|
+
# @param region [String]: The region in which the resource resides.
|
|
89
|
+
# @param account_number [String]: The account in which the resource resides.
|
|
90
|
+
# @return [String]
|
|
91
|
+
def self.getARN(resource, resource_type, client_type, region: MU.curRegion, account_number: MU.account_number)
|
|
92
|
+
aws_str = MU::Cloud::AWS.isGovCloud?(region) ? "aws-us-gov" : "aws"
|
|
93
|
+
"arn:#{aws_str}:#{client_type}:#{region}:#{account_number}:#{resource_type}:#{resource}"
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
# Construct all our tags.
|
|
97
|
+
# @return [Array]: All our standard tags and any custom tags.
|
|
98
|
+
def allTags
|
|
99
|
+
tags = []
|
|
100
|
+
MU::MommaCat.listStandardTags.each_pair { |name, value|
|
|
101
|
+
tags << {key: name, value: value}
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
if @config['optional_tags']
|
|
105
|
+
MU::MommaCat.listOptionalTags.each_pair { |name, value|
|
|
106
|
+
tags << {key: name, value: value}
|
|
107
|
+
}
|
|
108
|
+
end
|
|
109
|
+
|
|
110
|
+
if @config['tags']
|
|
111
|
+
@config['tags'].each { |tag|
|
|
112
|
+
tags << {key: tag['key'], value: tag['value']}
|
|
113
|
+
}
|
|
114
|
+
end
|
|
115
|
+
|
|
116
|
+
return tags
|
|
117
|
+
end
|
|
118
|
+
|
|
119
|
+
# Add our standard tag set to an Amazon ElasticCache resource.
|
|
120
|
+
# @param resource [String]: The name of the resource
|
|
121
|
+
# @param resource_type [String]: The type of the resource
|
|
122
|
+
# @param region [String]: The cloud provider region
|
|
123
|
+
def addStandardTags(resource, resource_type, region: MU.curRegion)
|
|
124
|
+
MU.log "Adding tags to ElasticCache resource #{resource}"
|
|
125
|
+
MU::Cloud::AWS.elasticache(region).add_tags_to_resource(
|
|
126
|
+
resource_name: MU::Cloud::AWS::CacheCluster.getARN(resource, resource_type, "elasticache", region: region),
|
|
127
|
+
tags: allTags
|
|
128
|
+
)
|
|
129
|
+
end
|
|
130
|
+
|
|
131
|
+
# Called automatically by {MU::Deploy#createResources}
|
|
132
|
+
# @return [String]: The cloud provider's identifier for this cache cluster instance.
|
|
133
|
+
def create
|
|
134
|
+
@config["snapshot_id"] =
|
|
135
|
+
if @config["creation_style"] == "existing_snapshot"
|
|
136
|
+
getExistingSnapshot ? getExistingSnapshot : createNewSnapshot
|
|
137
|
+
elsif @config["creation_style"] == "new_snapshot"
|
|
138
|
+
createNewSnapshot
|
|
139
|
+
end
|
|
140
|
+
|
|
141
|
+
# Should we base all our resource names on @mu_name even though only the cache cluster / cache replication group identifiers are the isssue?
|
|
142
|
+
@config['identifier'] = @mu_name
|
|
143
|
+
@config["subnet_group_name"] = @mu_name
|
|
144
|
+
createSubnetGroup
|
|
145
|
+
|
|
146
|
+
# Shared configuration elements between cache clusters and cache replication groups
|
|
147
|
+
config_struct = {
|
|
148
|
+
cache_node_type: @config["size"],
|
|
149
|
+
engine: @config["engine"],
|
|
150
|
+
engine_version: @config["engine_version"],
|
|
151
|
+
cache_subnet_group_name: @config["subnet_group_name"],
|
|
152
|
+
preferred_maintenance_window: @config["preferred_maintenance_window"],
|
|
153
|
+
port: @config["port"],
|
|
154
|
+
auto_minor_version_upgrade: @config["auto_minor_version_upgrade"],
|
|
155
|
+
security_group_ids: @config["security_group_ids"],
|
|
156
|
+
tags: allTags
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
if @config["engine"] == "redis"
|
|
160
|
+
config_struct[:snapshot_name] = @config["snapshot_id"] if @config["snapshot_id"]
|
|
161
|
+
config_struct[:snapshot_arns] = @config["snapshot_arn"] if @config["snapshot_arn"]
|
|
162
|
+
config_struct[:snapshot_retention_limit] = @config["snapshot_retention_limit"] if @config["snapshot_retention_limit"]
|
|
163
|
+
config_struct[:snapshot_window] = @config["snapshot_window"] if @config["snapshot_window"]
|
|
164
|
+
end
|
|
165
|
+
|
|
166
|
+
if @config.has_key?("parameter_group_family")
|
|
167
|
+
# downcasing parameter_group_name because AWS downcases the name for us and we won't be able to find it.
|
|
168
|
+
# AWS downcases all resource names in ElastiCache for some reason,
|
|
169
|
+
# but other resources don't seem to be case sensitive when we try to retrieve them.
|
|
170
|
+
@config["parameter_group_name"] = @mu_name.downcase
|
|
171
|
+
createParameterGroup
|
|
172
|
+
config_struct[:cache_parameter_group_name] = @config["parameter_group_name"]
|
|
173
|
+
end
|
|
174
|
+
|
|
175
|
+
config_struct[:notification_topic_arn] = @config["notification_topic_arn"] if @config["notification_topic_arn"]
|
|
176
|
+
|
|
177
|
+
# Mu already cleans up our resources for us when we fail mid creation, so not doing begin/ensure to cleanup in case we fail.
|
|
178
|
+
if @config["create_replication_group"]
|
|
179
|
+
config_struct[:automatic_failover_enabled] = @config['automatic_failover']
|
|
180
|
+
config_struct[:replication_group_id] = @config['identifier']
|
|
181
|
+
config_struct[:replication_group_description] = @mu_name
|
|
182
|
+
config_struct[:num_cache_clusters] = @config["node_count"]
|
|
183
|
+
# config_struct[:primary_cluster_id] = @config["primary_cluster_id"]
|
|
184
|
+
# config_struct[:preferred_cache_cluster_a_zs] = @config["preferred_cache_cluster_azs"]
|
|
185
|
+
|
|
186
|
+
MU.log "Creating cache replication group #{@config['identifier']}"
|
|
187
|
+
resp = MU::Cloud::AWS.elasticache(@config['region']).create_replication_group(config_struct).replication_group
|
|
188
|
+
|
|
189
|
+
wait_start_time = Time.now
|
|
190
|
+
retries = 0
|
|
191
|
+
begin
|
|
192
|
+
MU::Cloud::AWS.elasticache(@config['region']).wait_until(:replication_group_available, replication_group_id: @config['identifier']) do |waiter|
|
|
193
|
+
waiter.max_attempts = nil
|
|
194
|
+
waiter.before_attempt do |attempts|
|
|
195
|
+
MU.log "Waiting for cache replication group #{@config['identifier']} to become available", MU::NOTICE if attempts % 5 == 0
|
|
196
|
+
end
|
|
197
|
+
waiter.before_wait do |attempts, resp|
|
|
198
|
+
throw :success if resp.replication_groups.first.status == "available"
|
|
199
|
+
throw :failure if Time.now - wait_start_time > 1800
|
|
200
|
+
end
|
|
201
|
+
end
|
|
202
|
+
rescue Aws::Waiters::Errors::TooManyAttemptsError => e
|
|
203
|
+
raise MuError, "Waited #{(Time.now - wait_start_time).round/60*(retries+1)} minutes for #{@config['identifier']} become available, giving up. #{e}" if retries > 2
|
|
204
|
+
wait_start_time = Time.now
|
|
205
|
+
retries += 1
|
|
206
|
+
retry
|
|
207
|
+
end
|
|
208
|
+
|
|
209
|
+
resp = MU::Cloud::AWS::CacheCluster.getCacheReplicationGroupById(@config['identifier'], region: @config['region'])
|
|
210
|
+
|
|
211
|
+
# We want to make sure the clusters in the cache replication group get our tags
|
|
212
|
+
resp.member_clusters.each { |member|
|
|
213
|
+
addStandardTags(member, "cluster", region: @config['region'])
|
|
214
|
+
}
|
|
215
|
+
|
|
216
|
+
MU::Cloud::AWS::DNSZone.genericMuDNSEntry(
|
|
217
|
+
name: resp.replication_group_id,
|
|
218
|
+
target: "#{resp.node_groups.first.primary_endpoint.address}.",
|
|
219
|
+
cloudclass: MU::Cloud::CacheCluster,
|
|
220
|
+
sync_wait: @config['dns_sync_wait']
|
|
221
|
+
)
|
|
222
|
+
|
|
223
|
+
resp.node_groups.first.node_group_members.each { |member|
|
|
224
|
+
MU::Cloud::AWS::DNSZone.genericMuDNSEntry(
|
|
225
|
+
name: member.cache_cluster_id,
|
|
226
|
+
target: "#{member.read_endpoint.address}.",
|
|
227
|
+
cloudclass: MU::Cloud::CacheCluster,
|
|
228
|
+
sync_wait: @config['dns_sync_wait']
|
|
229
|
+
)
|
|
230
|
+
|
|
231
|
+
}
|
|
232
|
+
|
|
233
|
+
MU.log "Cache replication group #{@config['identifier']} is ready to use"
|
|
234
|
+
@cloud_id = resp.replication_group_id
|
|
235
|
+
else
|
|
236
|
+
config_struct[:cache_cluster_id] = @config['identifier']
|
|
237
|
+
config_struct[:az_mode] = @config["az_mode"]
|
|
238
|
+
config_struct[:num_cache_nodes] = @config["node_count"]
|
|
239
|
+
# config_struct[:replication_group_id] = @config["replication_group_id"] if @config["replication_group_id"]
|
|
240
|
+
# config_struct[:preferred_availability_zone] = @config["preferred_availability_zone"] if @config["preferred_availability_zone"] && @config["az_mode"] == "single-az"
|
|
241
|
+
# config_struct[:preferred_availability_zones] = @config["preferred_availability_zones"] if @config["preferred_availability_zones"] && @config["az_mode"] == "cross-az"
|
|
242
|
+
|
|
243
|
+
MU.log "Creating cache cluster #{@config['identifier']}"
|
|
244
|
+
resp = MU::Cloud::AWS.elasticache(@config['region']).create_cache_cluster(config_struct).cache_cluster
|
|
245
|
+
|
|
246
|
+
wait_start_time = Time.now
|
|
247
|
+
retries = 0
|
|
248
|
+
begin
|
|
249
|
+
MU::Cloud::AWS.elasticache(@config['region']).wait_until(:cache_cluster_available, cache_cluster_id: @config['identifier']) do |waiter|
|
|
250
|
+
waiter.max_attempts = nil
|
|
251
|
+
waiter.before_attempt do |attempts|
|
|
252
|
+
MU.log "Waiting for cache cluster #{@config['identifier']} to become available", MU::NOTICE if attempts % 5 == 0
|
|
253
|
+
end
|
|
254
|
+
waiter.before_wait do |attempts, resp|
|
|
255
|
+
throw :success if resp.cache_clusters.first.cache_cluster_status == "available"
|
|
256
|
+
throw :failure if Time.now - wait_start_time > 1800
|
|
257
|
+
end
|
|
258
|
+
end
|
|
259
|
+
rescue Aws::Waiters::Errors::TooManyAttemptsError => e
|
|
260
|
+
raise MuError, "Waited #{(Time.now - wait_start_time).round/60*(retries+1)} minutes for #{@config['identifier']} to become available, giving up. #{e}" if retries > 2
|
|
261
|
+
wait_start_time = Time.now
|
|
262
|
+
retries += 1
|
|
263
|
+
retry
|
|
264
|
+
end
|
|
265
|
+
|
|
266
|
+
resp = MU::Cloud::AWS::CacheCluster.getCacheClusterById(@config['identifier'], region: @config['region'])
|
|
267
|
+
MU.log "Cache Cluster #{@config['identifier']} is ready to use"
|
|
268
|
+
@cloud_id = resp.cache_cluster_id
|
|
269
|
+
end
|
|
270
|
+
end
|
|
271
|
+
|
|
272
|
+
# Create a subnet group for a Cache Cluster with the given config.
|
|
273
|
+
def createSubnetGroup
|
|
274
|
+
subnet_ids = []
|
|
275
|
+
|
|
276
|
+
if @config["vpc"] && !@config["vpc"].empty?
|
|
277
|
+
raise MuError, "Didn't find the VPC specified in #{@config["vpc"]}" unless @vpc
|
|
278
|
+
|
|
279
|
+
vpc_id = @vpc.cloud_id
|
|
280
|
+
|
|
281
|
+
# Getting subnet IDs
|
|
282
|
+
if @config["vpc"]["subnets"].empty?
|
|
283
|
+
@vpc.subnets.each { |subnet|
|
|
284
|
+
subnet_ids << subnet.cloud_id
|
|
285
|
+
}
|
|
286
|
+
MU.log "No subnets specified for #{@config['identifier']}, adding all subnets in #{@vpc}", MU::DEBUG
|
|
287
|
+
else
|
|
288
|
+
@config["vpc"]["subnets"].each { |subnet|
|
|
289
|
+
subnet_obj = @vpc.getSubnet(cloud_id: subnet["subnet_id"].to_s, name: subnet["subnet_name"].to_s)
|
|
290
|
+
raise MuError, "Couldn't find a live subnet matching #{subnet} in #{@vpc} (#{@vpc.subnets})" if subnet_obj.nil?
|
|
291
|
+
subnet_ids << subnet_obj.cloud_id
|
|
292
|
+
}
|
|
293
|
+
end
|
|
294
|
+
else
|
|
295
|
+
# If we didn't specify a VPC try to figure out if the account has a default VPC
|
|
296
|
+
vpc_id = nil
|
|
297
|
+
subnets = []
|
|
298
|
+
MU::Cloud::AWS.ec2(@config['region']).describe_vpcs.vpcs.each { |vpc|
|
|
299
|
+
if vpc.is_default
|
|
300
|
+
vpc_id = vpc.vpc_id
|
|
301
|
+
subnets = MU::Cloud::AWS.ec2(@config['region']).describe_subnets(
|
|
302
|
+
filters: [
|
|
303
|
+
{
|
|
304
|
+
name: "vpc-id",
|
|
305
|
+
values: [vpc_id]
|
|
306
|
+
}
|
|
307
|
+
]
|
|
308
|
+
).subnets
|
|
309
|
+
break
|
|
310
|
+
end
|
|
311
|
+
}
|
|
312
|
+
|
|
313
|
+
if !subnets.empty?
|
|
314
|
+
mu_subnets = []
|
|
315
|
+
subnets.each { |subnet|
|
|
316
|
+
subnet_ids << subnet.subnet_id
|
|
317
|
+
mu_subnets << {"subnet_id" => subnet.subnet_id}
|
|
318
|
+
}
|
|
319
|
+
|
|
320
|
+
@config['vpc'] = {
|
|
321
|
+
"vpc_id" => vpc_id,
|
|
322
|
+
"subnets" => mu_subnets
|
|
323
|
+
}
|
|
324
|
+
using_default_vpc = true
|
|
325
|
+
MU.log "Using default VPC for cache cluster #{@config['identifier']}"
|
|
326
|
+
end
|
|
327
|
+
end
|
|
328
|
+
|
|
329
|
+
if subnet_ids.empty?
|
|
330
|
+
raise MuError, "Can't create subnet group #{@config["subnet_group_name"]} because I couldn't find a VPC or subnets"
|
|
331
|
+
else
|
|
332
|
+
MU.log "Creating subnet group #{@config["subnet_group_name"]} for cache cluster #{@config['identifier']}"
|
|
333
|
+
|
|
334
|
+
resp = MU::Cloud::AWS.elasticache(@config['region']).create_cache_subnet_group(
|
|
335
|
+
cache_subnet_group_name: @config["subnet_group_name"],
|
|
336
|
+
cache_subnet_group_description: @config["subnet_group_name"],
|
|
337
|
+
subnet_ids: subnet_ids
|
|
338
|
+
)
|
|
339
|
+
|
|
340
|
+
# Find NAT and create holes in security groups.
|
|
341
|
+
# Adding just for consistency, but do we really need this for cache clusters? I guess Nagios and such..
|
|
342
|
+
if @config["vpc"]["nat_host_name"] || @config["vpc"]["nat_host_id"] || @config["vpc"]["nat_host_tag"] || @config["vpc"]["nat_host_ip"]
|
|
343
|
+
nat = @nat
|
|
344
|
+
if nat.is_a?(Struct) && nat.nat_gateway_id && nat.nat_gateway_id.start_with?("nat-")
|
|
345
|
+
MU.log "Using NAT Gateway, not modifying security groups"
|
|
346
|
+
else
|
|
347
|
+
nat_name, nat_conf, nat_deploydata = @nat.describe
|
|
348
|
+
@deploy.kittens['firewall_rules'].each_pair { |name, acl|
|
|
349
|
+
# XXX if a user doesn't set up dependencies correctly, this can die horribly on a NAT that's still in mid-creation. Fix this... possibly in the config parser.
|
|
350
|
+
if acl.config["admin"]
|
|
351
|
+
acl.addRule([nat_deploydata["private_ip_address"]], proto: "tcp")
|
|
352
|
+
acl.addRule([nat_deploydata["private_ip_address"]], proto: "udp")
|
|
353
|
+
break
|
|
354
|
+
end
|
|
355
|
+
}
|
|
356
|
+
end
|
|
357
|
+
end
|
|
358
|
+
|
|
359
|
+
if @dependencies.has_key?('firewall_rule')
|
|
360
|
+
@config["security_group_ids"] = []
|
|
361
|
+
@dependencies['firewall_rule'].values.each { |sg|
|
|
362
|
+
@config["security_group_ids"] << sg.cloud_id
|
|
363
|
+
}
|
|
364
|
+
end
|
|
365
|
+
end
|
|
366
|
+
end
|
|
367
|
+
|
|
368
|
+
# Create a Cache Cluster parameter group.
|
|
369
|
+
def createParameterGroup
|
|
370
|
+
MU.log "Creating a cache cluster parameter group #{@config["parameter_group_name"]}"
|
|
371
|
+
resp = MU::Cloud::AWS.elasticache(@config['region']).create_cache_parameter_group(
|
|
372
|
+
cache_parameter_group_name: @config["parameter_group_name"],
|
|
373
|
+
cache_parameter_group_family: @config["parameter_group_family"],
|
|
374
|
+
description: "Parameter group for #{@config["parameter_group_family"]}"
|
|
375
|
+
)
|
|
376
|
+
|
|
377
|
+
if @config.has_key?("parameter_group_parameters") && !@config["parameter_group_parameters"].empty?
|
|
378
|
+
params = []
|
|
379
|
+
@config["parameter_group_parameters"].each { |item|
|
|
380
|
+
params << {parameter_name: item['name'], parameter_value: item['value']}
|
|
381
|
+
}
|
|
382
|
+
|
|
383
|
+
MU.log "Modifiying cache cluster parameter group #{@config["parameter_group_name"]}"
|
|
384
|
+
MU::Cloud::AWS.elasticache(@config['region']).modify_cache_parameter_group(
|
|
385
|
+
cache_parameter_group_name: @config["parameter_group_name"],
|
|
386
|
+
parameter_name_values: params
|
|
387
|
+
)
|
|
388
|
+
end
|
|
389
|
+
end
|
|
390
|
+
|
|
391
|
+
# Retrieve a Cache Cluster parameter group name of on existing parameter group.
|
|
392
|
+
# @return [String]: Cache Cluster parameter group name.
|
|
393
|
+
def getParameterGroup
|
|
394
|
+
MU::Cloud::AWS.elasticache(@config['region']).describe_cache_parameter_groups(
|
|
395
|
+
cache_parameter_group_name: @config["parameter_group_name"]
|
|
396
|
+
).cache_parameter_groups.first.cache_parameter_group_name
|
|
397
|
+
end
|
|
398
|
+
|
|
399
|
+
# Called automatically by {MU::Deploy#createResources}
|
|
400
|
+
def groom
|
|
401
|
+
# Do we have anything to do here??
|
|
402
|
+
end
|
|
403
|
+
|
|
404
|
+
# Retrieve the complete cloud provider description of a cache cluster.
|
|
405
|
+
# @param cc_id [String]: The cloud provider's identifier for this cache cluster.
|
|
406
|
+
# @param region [String]: The cloud provider's region.
|
|
407
|
+
# @return [OpenStruct]
|
|
408
|
+
def self.getCacheClusterById(cc_id, region: MU.curRegion)
|
|
409
|
+
MU::Cloud::AWS.elasticache(region).describe_cache_clusters(cache_cluster_id: cc_id).cache_clusters.first
|
|
410
|
+
end
|
|
411
|
+
|
|
412
|
+
# Retrieve the complete cloud provider description of a cache replication group.
|
|
413
|
+
# @param repl_group_id [String]: The cloud provider's identifier for this cache replication group.
|
|
414
|
+
# @param region [String]: The cloud provider's region.
|
|
415
|
+
# @return [OpenStruct]
|
|
416
|
+
def self.getCacheReplicationGroupById(repl_group_id, region: MU.curRegion)
|
|
417
|
+
MU::Cloud::AWS.elasticache(region).describe_replication_groups(replication_group_id: repl_group_id).replication_groups.first
|
|
418
|
+
end
|
|
419
|
+
|
|
420
|
+
# Register a description of this cache cluster / cache replication group with this deployment's metadata.
|
|
421
|
+
def notify
|
|
422
|
+
### TO DO: Flatten the replication group deployment metadata structure. It is probably waaaaaaay too nested.
|
|
423
|
+
if @config["create_replication_group"]
|
|
424
|
+
repl_group = MU::Cloud::AWS::CacheCluster.getCacheReplicationGroupById(@config['identifier'], region: @config['region'])
|
|
425
|
+
# DNS records for the "real" zone should always be registered as late as possible so override_existing only overwrites the records after the resource is ready to use.
|
|
426
|
+
if @config['dns_records']
|
|
427
|
+
@config['dns_records'].each { |dnsrec|
|
|
428
|
+
dnsrec['name'] = repl_group.node_groups.first.primary_endpoint.address.downcase if !dnsrec.has_key?('name')
|
|
429
|
+
dnsrec['name'] = "#{dnsrec['name']}.#{MU.environment.downcase}" if dnsrec["append_environment_name"] && !dnsrec['name'].match(/\.#{MU.environment.downcase}$/)
|
|
430
|
+
}
|
|
431
|
+
end
|
|
432
|
+
# XXX this should be a call to @deploy.nameKitten
|
|
433
|
+
MU::Cloud::AWS::DNSZone.createRecordsFromConfig(@config['dns_records'], target: repl_group.node_groups.first.primary_endpoint.address)
|
|
434
|
+
|
|
435
|
+
deploy_struct = {
|
|
436
|
+
"identifier" => repl_group.replication_group_id,
|
|
437
|
+
"create_style" => @config["create_style"],
|
|
438
|
+
"region" => @config["region"],
|
|
439
|
+
"members" => repl_group.member_clusters,
|
|
440
|
+
"automatic_failover" => repl_group.automatic_failover,
|
|
441
|
+
"snapshotting_cluster_id" => repl_group.snapshotting_cluster_id,
|
|
442
|
+
"primary_endpoint" => repl_group.node_groups.first.primary_endpoint.address,
|
|
443
|
+
"primary_port" => repl_group.node_groups.first.primary_endpoint.port
|
|
444
|
+
}
|
|
445
|
+
|
|
446
|
+
repl_group.member_clusters.each { |id|
|
|
447
|
+
cluster = MU::Cloud::AWS::CacheCluster.getCacheClusterById(id, region: @config['region'])
|
|
448
|
+
|
|
449
|
+
vpc_sg_ids = []
|
|
450
|
+
cluster.security_groups.each { |vpc_sg|
|
|
451
|
+
vpc_sg_ids << vpc_sg.security_group_id
|
|
452
|
+
}
|
|
453
|
+
|
|
454
|
+
cache_sg_ids = []
|
|
455
|
+
unless cluster.cache_security_groups.empty?
|
|
456
|
+
cluster.cache_security_groups.each { |cache_sg|
|
|
457
|
+
cache_sg_ids << cache_sg.security_group_id
|
|
458
|
+
}
|
|
459
|
+
end
|
|
460
|
+
|
|
461
|
+
deploy_struct[id] = {
|
|
462
|
+
"configuration_endpoint" => cluster.configuration_endpoint,
|
|
463
|
+
"cache_node_type" => cluster.cache_node_type,
|
|
464
|
+
"engine" => cluster.engine,
|
|
465
|
+
"engine_version" => cluster.engine_version,
|
|
466
|
+
"num_cache_nodes" => cluster.num_cache_nodes,
|
|
467
|
+
"preferred_maintenance_window" => cluster.preferred_maintenance_window,
|
|
468
|
+
"notification_configuration" => cluster.notification_configuration,
|
|
469
|
+
"cache_security_groups" => cache_sg_ids,
|
|
470
|
+
"cache_parameter_group" => cluster.cache_parameter_group.cache_parameter_group_name,
|
|
471
|
+
"cache_subnet_group_name" => cluster.cache_subnet_group_name,
|
|
472
|
+
"cache_nodes" => cluster.cache_nodes,
|
|
473
|
+
"auto_minor_version_upgrade" => cluster.auto_minor_version_upgrade,
|
|
474
|
+
"vpc_security_groups" => vpc_sg_ids,
|
|
475
|
+
"replication_group_id" => cluster.replication_group_id,
|
|
476
|
+
"snapshot_retention_limit" => cluster.snapshot_retention_limit,
|
|
477
|
+
"snapshot_window" => cluster.snapshot_window
|
|
478
|
+
}
|
|
479
|
+
}
|
|
480
|
+
|
|
481
|
+
repl_group.node_groups.first.node_group_members.each{ |member|
|
|
482
|
+
deploy_struct[member.cache_cluster_id]["cache_node_id"] = member.cache_node_id
|
|
483
|
+
deploy_struct[member.cache_cluster_id]["read_endpoint_address"] = member.read_endpoint.address
|
|
484
|
+
deploy_struct[member.cache_cluster_id]["read_endpoint_port"] = member.read_endpoint.port
|
|
485
|
+
deploy_struct[member.cache_cluster_id]["current_role"] = member.current_role
|
|
486
|
+
}
|
|
487
|
+
else
|
|
488
|
+
cluster = MU::Cloud::AWS::CacheCluster.getCacheClusterById(@config['identifier'], region: @config['region'])
|
|
489
|
+
vpc_sg_ids = []
|
|
490
|
+
cluster.security_groups.each { |vpc_sg|
|
|
491
|
+
vpc_sg_ids << vpc_sg.security_group_id
|
|
492
|
+
}
|
|
493
|
+
|
|
494
|
+
cache_sg_ids = []
|
|
495
|
+
unless cluster.cache_security_groups.empty?
|
|
496
|
+
cluster.cache_security_groups.each { |cache_sg|
|
|
497
|
+
cache_sg_ids << cache_sg.security_group_id
|
|
498
|
+
}
|
|
499
|
+
end
|
|
500
|
+
|
|
501
|
+
deploy_struct = {
|
|
502
|
+
"cache_node_type" => cluster.cache_node_type,
|
|
503
|
+
"engine" => cluster.engine,
|
|
504
|
+
"engine_version" => cluster.engine_version,
|
|
505
|
+
"num_cache_nodes" => cluster.num_cache_nodes,
|
|
506
|
+
"preferred_maintenance_window" => cluster.preferred_maintenance_window,
|
|
507
|
+
"notification_configuration" => cluster.notification_configuration,
|
|
508
|
+
"cache_security_groups" => cache_sg_ids,
|
|
509
|
+
"cache_parameter_group" => cluster.cache_parameter_group.cache_parameter_group_name,
|
|
510
|
+
"cache_subnet_group_name" => cluster.cache_subnet_group_name,
|
|
511
|
+
"cache_nodes" => cluster.cache_nodes,
|
|
512
|
+
"auto_minor_version_upgrade" => cluster.auto_minor_version_upgrade,
|
|
513
|
+
"vpc_security_groups" => vpc_sg_ids,
|
|
514
|
+
"replication_group_id" => cluster.replication_group_id,
|
|
515
|
+
"snapshot_retention_limit" => cluster.snapshot_retention_limit,
|
|
516
|
+
"snapshot_window" => cluster.snapshot_window
|
|
517
|
+
}
|
|
518
|
+
if !cluster.configuration_endpoint.nil?
|
|
519
|
+
deploy_struct["configuration_endpoint_address"] = cluster.configuration_endpoint.address
|
|
520
|
+
deploy_struct["configuration_endpoint_port"] = cluster.configuration_endpoint.port
|
|
521
|
+
end
|
|
522
|
+
end
|
|
523
|
+
|
|
524
|
+
return deploy_struct
|
|
525
|
+
end
|
|
526
|
+
|
|
527
|
+
# Generate a snapshot from the Cache Cluster described in this instance.
|
|
528
|
+
# @return [String]: The cloud provider's identifier for the snapshot.
|
|
529
|
+
def createNewSnapshot
|
|
530
|
+
snap_id = @deploy.getResourceName(@config["name"]) + Time.new.strftime("%M%S").to_s
|
|
531
|
+
|
|
532
|
+
attempts = 0
|
|
533
|
+
begin
|
|
534
|
+
snapshot = MU::Cloud::AWS.elasticache(@config['region']).create_snapshot(
|
|
535
|
+
cache_cluster_id: @config["identifier"],
|
|
536
|
+
snapshot_name: snap_id
|
|
537
|
+
)
|
|
538
|
+
rescue Aws::ElastiCache::Errors::InvalidCacheClusterState => e
|
|
539
|
+
if attempts < 10
|
|
540
|
+
MU.log "Tried to create snapshot for #{@config["identifier"]} but cache cluster is busy, retrying a few times"
|
|
541
|
+
attempts += 1
|
|
542
|
+
sleep 30
|
|
543
|
+
retry
|
|
544
|
+
else
|
|
545
|
+
raise MuError, "Failed to create snpashot for cache cluster #{@config["identifier"]}: #{e.inspect}"
|
|
546
|
+
end
|
|
547
|
+
end
|
|
548
|
+
|
|
549
|
+
attempts = 0
|
|
550
|
+
loop do
|
|
551
|
+
MU.log "Waiting for snapshot of cache cluster #{@config["identifier"]} to be ready...", MU::NOTICE if attempts % 20 == 0
|
|
552
|
+
MU.log "Waiting for snapshot of cache cluster #{@config["identifier"]} to be ready...", MU::DEBUG
|
|
553
|
+
|
|
554
|
+
snapshot_resp = MU::Cloud::AWS.elasticache(@config['region']).describe_snapshots(snapshot_name: snap_id)
|
|
555
|
+
attempts += 1
|
|
556
|
+
break unless snapshot_resp.snapshots.first.snapshot_status != "available"
|
|
557
|
+
sleep 15
|
|
558
|
+
end
|
|
559
|
+
|
|
560
|
+
return snap_id
|
|
561
|
+
end
|
|
562
|
+
|
|
563
|
+
# @return [String]: The cloud provider's identifier for the snapshot.
|
|
564
|
+
def getExistingSnapshot
|
|
565
|
+
MU::Cloud::AWS.elasticache(@config['region']).describe_snapshots(snapshot_name: @config["identifier"]).snapshots.first.snapshot_name
|
|
566
|
+
rescue NoMethodError
|
|
567
|
+
raise MuError, "Snapshot #{@config["identifier"]} doesn't exist, make sure you provided a valid snapshot ID/Name"
|
|
568
|
+
end
|
|
569
|
+
|
|
570
|
+
# Called by {MU::Cleanup}. Locates resources that were created by the currently-loaded deployment and purges them.
|
|
571
|
+
# @param noop [Boolean]: If true, will only print what would be done.
|
|
572
|
+
# @param ignoremaster [Boolean]: If true, will remove resources not flagged as originating from this Mu server.
|
|
573
|
+
# @param region [String]: The cloud provider's region in which to operate.
|
|
574
|
+
# @return [void]
|
|
575
|
+
def self.cleanup(skipsnapshots: false, noop: false, ignoremaster: false, region: MU.curRegion, flags: {})
|
|
576
|
+
all_clusters = MU::Cloud::AWS.elasticache(region).describe_cache_clusters
|
|
577
|
+
our_clusters = []
|
|
578
|
+
our_replication_group_ids = []
|
|
579
|
+
|
|
580
|
+
# Because we can't run list_tags_for_resource on a cache cluster that isn't in "available" state we're loading the deploy to make sure we have a cache cluster to cleanup.
|
|
581
|
+
# To ensure we don't miss cache clusters that have been terminated mid creation we'll load the 'original_config'. We might want to find a better approach for this.
|
|
582
|
+
deploy = MU::MommaCat.getLitter(MU.deploy_id)
|
|
583
|
+
if deploy.original_config && deploy.original_config.has_key?("cache_clusters") && !deploy.original_config["cache_clusters"].empty?
|
|
584
|
+
|
|
585
|
+
# The ElastiCache API and documentation are a mess, the replication group ARN resource_type is not documented, and is not easily guessable.
|
|
586
|
+
# So instead of searching for replication groups directly we'll get their IDs from the cache clusters.
|
|
587
|
+
all_clusters.cache_clusters.each { |cluster|
|
|
588
|
+
cluster_id = cluster.cache_cluster_id
|
|
589
|
+
|
|
590
|
+
# ElastiCache API is buggy... It will throw a CacheClusterNotFound if we run list_tags_for_resource on a cahe cluster that isn't in an "available" state.
|
|
591
|
+
if cluster.cache_cluster_status != "available"
|
|
592
|
+
if %w{deleting deleted}.include?(cluster.cache_cluster_status)
|
|
593
|
+
# The cahe cluster might not be ours so don't notify us about it.
|
|
594
|
+
next
|
|
595
|
+
else
|
|
596
|
+
# We can replace this with an AWS waiter.
|
|
597
|
+
loop do
|
|
598
|
+
MU.log "Waiting for #{cluster_id} to be in a removable state", MU::NOTICE
|
|
599
|
+
cluster = MU::Cloud::AWS::CacheCluster.getCacheClusterById(cluster_id, region: region)
|
|
600
|
+
break unless %w{creating modifying backing-up}.include?(cluster.cache_cluster_status)
|
|
601
|
+
sleep 60
|
|
602
|
+
end
|
|
603
|
+
end
|
|
604
|
+
end
|
|
605
|
+
|
|
606
|
+
arn = MU::Cloud::AWS::CacheCluster.getARN(cluster_id, "cluster", "elasticache", region: region)
|
|
607
|
+
attempts = 0
|
|
608
|
+
|
|
609
|
+
begin
|
|
610
|
+
tags = MU::Cloud::AWS.elasticache(region).list_tags_for_resource(resource_name: arn).tag_list
|
|
611
|
+
rescue Aws::ElastiCache::Errors::CacheClusterNotFound => e
|
|
612
|
+
if attempts < 10
|
|
613
|
+
MU.log "Can't get tags for #{cluster_id}, retrying a few times in case of a lagging resource", MU::WARN
|
|
614
|
+
MU.log "arn #{arn}", MU::WARN
|
|
615
|
+
attempts += 1
|
|
616
|
+
sleep 30
|
|
617
|
+
retry
|
|
618
|
+
else
|
|
619
|
+
raise MuError, "Failed to get tags for cache cluster #{cluster_id}, MU-ID #{MU.deploy_id}: #{e.inspect}"
|
|
620
|
+
end
|
|
621
|
+
end
|
|
622
|
+
|
|
623
|
+
found_muid = false
|
|
624
|
+
found_master = false
|
|
625
|
+
tags.each { |tag|
|
|
626
|
+
found_muid = true if tag.key == "MU-ID" && tag.value == MU.deploy_id
|
|
627
|
+
found_master = true if tag.key == "MU-MASTER-IP" && tag.value == MU.mu_public_ip
|
|
628
|
+
}
|
|
629
|
+
next if !found_muid
|
|
630
|
+
|
|
631
|
+
delete =
|
|
632
|
+
if ignoremaster && found_muid
|
|
633
|
+
true
|
|
634
|
+
elsif !ignoremaster && found_muid && found_master
|
|
635
|
+
true
|
|
636
|
+
else
|
|
637
|
+
false
|
|
638
|
+
end
|
|
639
|
+
|
|
640
|
+
if delete
|
|
641
|
+
cluster.replication_group_id ? our_replication_group_ids << cluster.replication_group_id : our_clusters << cluster
|
|
642
|
+
end
|
|
643
|
+
}
|
|
644
|
+
|
|
645
|
+
threads = []
|
|
646
|
+
|
|
647
|
+
# Make sure we have only uniqe replication group IDs
|
|
648
|
+
our_replication_group_ids = our_replication_group_ids.uniq
|
|
649
|
+
if !our_replication_group_ids.empty?
|
|
650
|
+
our_replication_group_ids.each { |group_id|
|
|
651
|
+
replication_group = MU::Cloud::AWS::CacheCluster.getCacheReplicationGroupById(group_id, region: region)
|
|
652
|
+
parent_thread_id = Thread.current.object_id
|
|
653
|
+
threads << Thread.new(replication_group) { |myrepl_group|
|
|
654
|
+
MU.dupGlobals(parent_thread_id)
|
|
655
|
+
Thread.abort_on_exception = true
|
|
656
|
+
MU::Cloud::AWS::CacheCluster.terminate_replication_group(myrepl_group, noop: noop, skipsnapshots: skipsnapshots, region: region, deploy_id: MU.deploy_id, cloud_id: myrepl_group.replication_group_id)
|
|
657
|
+
}
|
|
658
|
+
}
|
|
659
|
+
end
|
|
660
|
+
|
|
661
|
+
# Hmmmm. Do we need to have seperate thread groups for clusters and replication groups?
|
|
662
|
+
if !our_clusters.empty?
|
|
663
|
+
our_clusters.each { |cluster|
|
|
664
|
+
parent_thread_id = Thread.current.object_id
|
|
665
|
+
threads << Thread.new(cluster) { |mycluster|
|
|
666
|
+
MU.dupGlobals(parent_thread_id)
|
|
667
|
+
Thread.abort_on_exception = true
|
|
668
|
+
MU::Cloud::AWS::CacheCluster.terminate_cache_cluster(mycluster, noop: noop, skipsnapshots: skipsnapshots, region: region, deploy_id: MU.deploy_id, cloud_id: mycluster.cache_cluster_id)
|
|
669
|
+
}
|
|
670
|
+
}
|
|
671
|
+
end
|
|
672
|
+
|
|
673
|
+
# Wait for all of the cache cluster and replication groups to finish cleanup before proceeding
|
|
674
|
+
threads.each { |t|
|
|
675
|
+
t.join
|
|
676
|
+
}
|
|
677
|
+
end
|
|
678
|
+
end
|
|
679
|
+
|
|
680
|
+
# Cloud-specific configuration properties.
|
|
681
|
+
# @param config [MU::Config]: The calling MU::Config object
|
|
682
|
+
# @return [Array<Array,Hash>]: List of required fields, and json-schema Hash of cloud-specific configuration parameters for this resource
|
|
683
|
+
def self.schema(config)
|
|
684
|
+
toplevel_required = []
|
|
685
|
+
schema = {
|
|
686
|
+
"ingress_rules" => {
|
|
687
|
+
"items" => {
|
|
688
|
+
"properties" => {
|
|
689
|
+
"sgs" => {
|
|
690
|
+
"type" => "array",
|
|
691
|
+
"items" => {
|
|
692
|
+
"description" => "Other AWS Security Groups; resources that are associated with this group will have this rule applied to their traffic",
|
|
693
|
+
"type" => "string"
|
|
694
|
+
}
|
|
695
|
+
},
|
|
696
|
+
"lbs" => {
|
|
697
|
+
"type" => "array",
|
|
698
|
+
"items" => {
|
|
699
|
+
"description" => "AWS Load Balancers which will have this rule applied to their traffic",
|
|
700
|
+
"type" => "string"
|
|
701
|
+
}
|
|
702
|
+
}
|
|
703
|
+
}
|
|
704
|
+
}
|
|
705
|
+
}
|
|
706
|
+
}
|
|
707
|
+
[toplevel_required, schema]
|
|
708
|
+
end
|
|
709
|
+
|
|
710
|
+
# Cloud-specific pre-processing of {MU::Config::BasketofKittens::cache_clusters}, bare and unvalidated.
|
|
711
|
+
# @param cache [Hash]: The resource to process and validate
|
|
712
|
+
# @param configurator [MU::Config]: The overall deployment configurator of which this resource is a member
|
|
713
|
+
# @return [Boolean]: True if validation succeeded, False otherwise
|
|
714
|
+
def self.validateConfig(cache, configurator)
|
|
715
|
+
ok = true
|
|
716
|
+
|
|
717
|
+
if cluster.has_key?("parameter_group_parameters") && cache["parameter_group_family"].nil?
|
|
718
|
+
MU.log "parameter_group_family must be set when setting parameter_group_parameters", MU::ERR
|
|
719
|
+
ok = false
|
|
720
|
+
end
|
|
721
|
+
if cache["engine"] == "redis"
|
|
722
|
+
# We aren't required to create a cache replication group for a single redis cache cluster,
|
|
723
|
+
# however AWS console does exactly that, ss such we will follow that behavior.
|
|
724
|
+
if cache["node_count"] > 1
|
|
725
|
+
cache["create_replication_group"] = true
|
|
726
|
+
cache["automatic_failover"] = cache["multi_az"]
|
|
727
|
+
end
|
|
728
|
+
|
|
729
|
+
# Some instance types don't support snapshotting
|
|
730
|
+
if %w{cache.t2.micro cache.t2.small cache.t2.medium}.include?(cache["size"])
|
|
731
|
+
if cluster.has_key?("snapshot_retention_limit") || cluster.has_key?("snapshot_window")
|
|
732
|
+
MU.log "Can't set snapshot_retention_limit or snapshot_window on #{cache["size"]}", MU::ERR
|
|
733
|
+
ok = false
|
|
734
|
+
end
|
|
735
|
+
end
|
|
736
|
+
elsif cache["engine"] == "memcached"
|
|
737
|
+
cache["create_replication_group"] = false
|
|
738
|
+
cache["az_mode"] = cache["multi_az"] ? "cross-az" : "single-az"
|
|
739
|
+
|
|
740
|
+
if cache["node_count"] > 20
|
|
741
|
+
MU.log "#{cache['engine']} supports up to 20 nodes per cache cluster", MU::ERR
|
|
742
|
+
ok = false
|
|
743
|
+
end
|
|
744
|
+
|
|
745
|
+
# memcached doesn't support snapshots
|
|
746
|
+
if cluster.has_key?("snapshot_retention_limit") || cluster.has_key?("snapshot_window")
|
|
747
|
+
MU.log "Can't set snapshot_retention_limit or snapshot_window on #{cache["engine"]}", MU::ERR
|
|
748
|
+
ok = false
|
|
749
|
+
end
|
|
750
|
+
end
|
|
751
|
+
|
|
752
|
+
ok
|
|
753
|
+
end
|
|
754
|
+
|
|
755
|
+
private
|
|
756
|
+
|
|
757
|
+
# Remove a Cache Cluster and associated artifacts
|
|
758
|
+
# @param cluster [OpenStruct]: The cloud provider's description of the Cache Cluster artifact.
|
|
759
|
+
# @param noop [Boolean]: If true, will only print what would be done.
|
|
760
|
+
# @param skipsnapshots [Boolean]: If true, will not create a last snapshot before terminating the Cache Cluster.
|
|
761
|
+
# @param region [String]: The cloud provider's region in which to operate.
|
|
762
|
+
# @param cloud_id [String]: The cloud provider's identifier for this resource.
|
|
763
|
+
# @return [void]
|
|
764
|
+
def self.terminate_cache_cluster(cluster, noop: false, skipsnapshots: false, region: MU.curRegion, deploy_id: MU.deploy_id, mu_name: nil, cloud_id: nil)
|
|
765
|
+
raise MuError, "terminate_cache_cluster requires a non-nil cache cluster descriptor" if cluster.nil? || cluster.empty?
|
|
766
|
+
|
|
767
|
+
cluster_id = cluster.cache_cluster_id
|
|
768
|
+
subnet_group = cluster.cache_subnet_group_name
|
|
769
|
+
parameter_group = cluster.cache_parameter_group.cache_parameter_group_name
|
|
770
|
+
|
|
771
|
+
# hmmmmm we can use an AWS waiter for this...
|
|
772
|
+
unless cluster.cache_cluster_status == "available"
|
|
773
|
+
loop do
|
|
774
|
+
MU.log "Waiting for #{cluster_id} to be in a removable state...", MU::NOTICE
|
|
775
|
+
cluster = MU::Cloud::AWS::CacheCluster.getCacheClusterById(cluster_id, region: region)
|
|
776
|
+
break unless %w{creating modifying backing-up}.include?(cluster.cache_cluster_status)
|
|
777
|
+
sleep 60
|
|
778
|
+
end
|
|
779
|
+
end
|
|
780
|
+
|
|
781
|
+
# The API is broken, cluster.cache_nodes is returnning an empty array, and the only URL we can get is the config one with cluster.configuration_endpoint.address.
|
|
782
|
+
# MU::Cloud::AWS::DNSZone.genericMuDNSEntry(name: cluster_id, target: , cloudclass: MU::Cloud::CacheCluster, delete: true)
|
|
783
|
+
|
|
784
|
+
if %w{deleting deleted}.include?(cluster.cache_cluster_status)
|
|
785
|
+
MU.log "#{cluster_id} has already been terminated", MU::WARN
|
|
786
|
+
else
|
|
787
|
+
unless noop
|
|
788
|
+
def self.clusterSkipSnap(cluster_id, region)
|
|
789
|
+
# We're calling this several times so lets declare it once
|
|
790
|
+
MU.log "Terminating #{cluster_id}. Not saving final snapshot"
|
|
791
|
+
MU::Cloud::AWS.elasticache(region).delete_cache_cluster(cache_cluster_id: cluster_id)
|
|
792
|
+
end
|
|
793
|
+
|
|
794
|
+
def self.clusterCreateSnap(cluster_id, region)
|
|
795
|
+
MU.log "Terminating #{cluster_id}. Final snapshot name: #{cluster_id}-mufinal"
|
|
796
|
+
MU::Cloud::AWS.elasticache(region).delete_cache_cluster(cache_cluster_id: cluster_id, final_snapshot_identifier: "#{cluster_id}-MUfinal")
|
|
797
|
+
end
|
|
798
|
+
|
|
799
|
+
retries = 0
|
|
800
|
+
begin
|
|
801
|
+
if cluster.engine == "memcached"
|
|
802
|
+
clusterSkipSnap(cluster_id, region)
|
|
803
|
+
else
|
|
804
|
+
skipsnapshots ? clusterSkipSnap(cluster_id, region) : clusterCreateSnap(cluster_id, region)
|
|
805
|
+
end
|
|
806
|
+
rescue Aws::ElastiCache::Errors::InvalidCacheClusterState => e
|
|
807
|
+
if retries < 5
|
|
808
|
+
MU.log "#{cluster_id} is not in a removable state, retrying several times", MU::WARN
|
|
809
|
+
retries += 1
|
|
810
|
+
sleep 30
|
|
811
|
+
retry
|
|
812
|
+
else
|
|
813
|
+
MU.log "#{cluster_id} is not in a removable state after several retries, giving up. #{e.inspect}", MU::ERR
|
|
814
|
+
return
|
|
815
|
+
end
|
|
816
|
+
rescue Aws::ElastiCache::Errors::SnapshotAlreadyExistsFault
|
|
817
|
+
MU.log "Snapshot #{cluster_id}-MUfinal already exists", MU::WARN
|
|
818
|
+
clusterSkipSnap(cluster_id, region)
|
|
819
|
+
rescue Aws::ElastiCache::Errors::SnapshotQuotaExceededFault
|
|
820
|
+
MU.log "Snapshot quota exceeded while deleting #{cluster_id}", MU::ERR
|
|
821
|
+
clusterSkipSnap(cluster_id, region)
|
|
822
|
+
end
|
|
823
|
+
|
|
824
|
+
wait_start_time = Time.now
|
|
825
|
+
retries = 0
|
|
826
|
+
begin
|
|
827
|
+
MU::Cloud::AWS.elasticache(region).wait_until(:cache_cluster_deleted, cache_cluster_id: cluster_id) do |waiter|
|
|
828
|
+
waiter.max_attempts = nil
|
|
829
|
+
waiter.before_attempt do |attempts|
|
|
830
|
+
MU.log "Waiting for cache cluster #{cluster_id} to delete..", MU::NOTICE if attempts % 10 == 0
|
|
831
|
+
end
|
|
832
|
+
waiter.before_wait do |attempts, resp|
|
|
833
|
+
throw :success if resp.cache_clusters.first.cache_cluster_status == "deleted"
|
|
834
|
+
throw :failure if Time.now - wait_start_time > 1800
|
|
835
|
+
end
|
|
836
|
+
end
|
|
837
|
+
rescue Aws::Waiters::Errors::TooManyAttemptsError => e
|
|
838
|
+
raise MuError, "Waited for #{(Time.now - wait_start_time).round/60*(retries+1)} minutes for cache cluster to delete, giving up. #{e}" if retries > 2
|
|
839
|
+
wait_start_time = Time.now
|
|
840
|
+
retries += 1
|
|
841
|
+
retry
|
|
842
|
+
rescue Aws::Waiters::Errors::FailureStateError
|
|
843
|
+
MU.log "#{cluster_id} disappeared on us"
|
|
844
|
+
end
|
|
845
|
+
end
|
|
846
|
+
end
|
|
847
|
+
|
|
848
|
+
MU.log "#{cluster_id} has been terminated"
|
|
849
|
+
|
|
850
|
+
unless noop
|
|
851
|
+
MU::Cloud::AWS::CacheCluster.delete_subnet_group(subnet_group, region: region) if subnet_group
|
|
852
|
+
MU::Cloud::AWS::CacheCluster.delete_parameter_group(parameter_group, region: region) if parameter_group && !parameter_group.start_with?("default")
|
|
853
|
+
end
|
|
854
|
+
end
|
|
855
|
+
|
|
856
|
+
# Remove a Cache Cluster Replication Group and associated artifacts
|
|
857
|
+
# @param repl_group [OpenStruct]: The cloud provider's description of the Cache Cluster artifact.
|
|
858
|
+
# @param noop [Boolean]: If true, will only print what would be done.
|
|
859
|
+
# @param skipsnapshots [Boolean]: If true, will not create a last snapshot before terminating the Cache Cluster.
|
|
860
|
+
# @param region [String]: The cloud provider's region in which to operate.
|
|
861
|
+
# @param cloud_id [String]: The cloud provider's identifier for this resource.
|
|
862
|
+
# @return [void]
|
|
863
|
+
def self.terminate_replication_group(repl_group, noop: false, skipsnapshots: false, region: MU.curRegion, deploy_id: MU.deploy_id, mu_name: nil, cloud_id: nil)
|
|
864
|
+
raise MuError, "terminate_replication_group requires a non-nil cache replication group descriptor" if repl_group.nil? || repl_group.empty?
|
|
865
|
+
|
|
866
|
+
repl_group_id = repl_group.replication_group_id
|
|
867
|
+
# We're assuming that all clusters in this replication group where created in the same deployment so have the same subnet group, parameter group, etc...
|
|
868
|
+
cluster_id = repl_group.member_clusters.first
|
|
869
|
+
cluster = MU::Cloud::AWS::CacheCluster.getCacheClusterById(cluster_id, region: region)
|
|
870
|
+
subnet_group = cluster.cache_subnet_group_name
|
|
871
|
+
parameter_group = cluster.cache_parameter_group.cache_parameter_group_name
|
|
872
|
+
|
|
873
|
+
# hmmmmm we can use an AWS waiter for this...
|
|
874
|
+
unless repl_group.status == "available"
|
|
875
|
+
loop do
|
|
876
|
+
MU.log "Waiting for #{repl_group_id} to be in a removable state...", MU::NOTICE
|
|
877
|
+
repl_group = MU::Cloud::AWS::CacheCluster.getCacheReplicationGroupById(repl_group_id, region: region)
|
|
878
|
+
break unless %w{creating modifying backing-up}.include?(repl_group.status)
|
|
879
|
+
sleep 60
|
|
880
|
+
end
|
|
881
|
+
end
|
|
882
|
+
|
|
883
|
+
# What's the likelihood of having more than one node group? maybe iterate over node_groups instead of assuming there is only one?
|
|
884
|
+
MU::Cloud::AWS::DNSZone.genericMuDNSEntry(name: repl_group_id, target: repl_group.node_groups.first.primary_endpoint.address, cloudclass: MU::Cloud::CacheCluster, delete: true)
|
|
885
|
+
# Assuming we also created DNS records for each of our cluster's read endpoint.
|
|
886
|
+
repl_group.node_groups.first.node_group_members.each { |member|
|
|
887
|
+
MU::Cloud::AWS::DNSZone.genericMuDNSEntry(name: member.cache_cluster_id, target: member.read_endpoint.address, cloudclass: MU::Cloud::CacheCluster, delete: true)
|
|
888
|
+
}
|
|
889
|
+
|
|
890
|
+
if %w{deleting deleted}.include?(repl_group.status)
|
|
891
|
+
MU.log "#{repl_group_id} has already been terminated", MU::WARN
|
|
892
|
+
else
|
|
893
|
+
unless noop
|
|
894
|
+
def self.skipSnap(repl_group_id, region)
|
|
895
|
+
# We're calling this several times so lets declare it once
|
|
896
|
+
MU.log "Terminating #{repl_group_id}. Not saving final snapshot"
|
|
897
|
+
MU::Cloud::AWS.elasticache(region).delete_replication_group(
|
|
898
|
+
replication_group_id: repl_group_id,
|
|
899
|
+
retain_primary_cluster: false
|
|
900
|
+
)
|
|
901
|
+
end
|
|
902
|
+
|
|
903
|
+
def self.createSnap(repl_group_id, region)
|
|
904
|
+
MU.log "Terminating #{repl_group_id}. Final snapshot name: #{repl_group_id}-mufinal"
|
|
905
|
+
MU::Cloud::AWS.elasticache(region).delete_replication_group(
|
|
906
|
+
replication_group_id: repl_group_id,
|
|
907
|
+
retain_primary_cluster: false,
|
|
908
|
+
final_snapshot_identifier: "#{repl_group_id}-mufinal"
|
|
909
|
+
)
|
|
910
|
+
end
|
|
911
|
+
|
|
912
|
+
retries = 0
|
|
913
|
+
begin
|
|
914
|
+
skipsnapshots ? skipSnap(repl_group_id, region) : createSnap(repl_group_id, region)
|
|
915
|
+
rescue Aws::ElastiCache::Errors::InvalidReplicationGroupState => e
|
|
916
|
+
if retries < 5
|
|
917
|
+
MU.log "#{repl_group_id} is not in a removable state, retrying several times", MU::WARN
|
|
918
|
+
retries += 1
|
|
919
|
+
sleep 30
|
|
920
|
+
retry
|
|
921
|
+
else
|
|
922
|
+
MU.log "#{repl_group_id} is not in a removable state after several retries, giving up. #{e.inspect}", MU::ERR
|
|
923
|
+
return
|
|
924
|
+
end
|
|
925
|
+
rescue Aws::ElastiCache::Errors::SnapshotAlreadyExistsFault
|
|
926
|
+
MU.log "Snapshot #{repl_group_id}-MUfinal already exists", MU::WARN
|
|
927
|
+
skipSnap(repl_group_id, region)
|
|
928
|
+
rescue Aws::ElastiCache::Errors::SnapshotQuotaExceededFault
|
|
929
|
+
MU.log "Snapshot quota exceeded while deleting #{repl_group_id}", MU::ERR
|
|
930
|
+
skipSnap(repl_group_id, region)
|
|
931
|
+
end
|
|
932
|
+
|
|
933
|
+
wait_start_time = Time.now
|
|
934
|
+
retries = 0
|
|
935
|
+
begin
|
|
936
|
+
MU::Cloud::AWS.elasticache(region).wait_until(:replication_group_deleted, replication_group_id: repl_group_id) do |waiter|
|
|
937
|
+
waiter.max_attempts = nil
|
|
938
|
+
waiter.before_attempt do |attempts|
|
|
939
|
+
MU.log "Waiting for #{repl_group_id} to delete..", MU::NOTICE if attempts % 10 == 0
|
|
940
|
+
end
|
|
941
|
+
waiter.before_wait do |attempts, resp|
|
|
942
|
+
throw :success if resp.replication_groups.first.status == "deleted"
|
|
943
|
+
throw :failure if Time.now - wait_start_time > 1800
|
|
944
|
+
end
|
|
945
|
+
end
|
|
946
|
+
rescue Aws::Waiters::Errors::TooManyAttemptsError => e
|
|
947
|
+
raise MuError, "Waited for #{(Time.now - wait_start_time).round/60*(retries+1)} minutes for #{repl_group_id} to delete, giving up. #{e}" if retries > 2
|
|
948
|
+
wait_start_time = Time.now
|
|
949
|
+
retries += 1
|
|
950
|
+
retry
|
|
951
|
+
rescue Aws::Waiters::Errors::FailureStateError
|
|
952
|
+
MU.log "#{repl_group_id} disappeared on us"
|
|
953
|
+
end
|
|
954
|
+
end
|
|
955
|
+
end
|
|
956
|
+
|
|
957
|
+
MU.log "#{repl_group_id} has been terminated"
|
|
958
|
+
unless noop
|
|
959
|
+
MU::Cloud::AWS::CacheCluster.delete_subnet_group(subnet_group, region: region) if subnet_group
|
|
960
|
+
MU::Cloud::AWS::CacheCluster.delete_parameter_group(parameter_group, region: region) if parameter_group && !parameter_group.start_with?("default")
|
|
961
|
+
end
|
|
962
|
+
end
|
|
963
|
+
|
|
964
|
+
# Remove a Cache Cluster Subnet Group.
|
|
965
|
+
# @param subnet_group_id [string]: The cloud provider's ID of the cache cluster subnet group.
|
|
966
|
+
# @param region [String]: The cloud provider's region in which to operate.
|
|
967
|
+
# @return [void]
|
|
968
|
+
def self.delete_subnet_group(subnet_group_id, region: MU.curRegion)
|
|
969
|
+
retries ||= 0
|
|
970
|
+
MU.log "Deleting Subnet group #{subnet_group_id}"
|
|
971
|
+
MU::Cloud::AWS.elasticache(region).delete_cache_subnet_group(cache_subnet_group_name: subnet_group_id)
|
|
972
|
+
rescue Aws::ElastiCache::Errors::CacheSubnetGroupNotFoundFault
|
|
973
|
+
MU.log "Subnet group #{subnet_group_id} disappeared before we could remove it", MU::WARN
|
|
974
|
+
rescue Aws::ElastiCache::Errors::CacheSubnetGroupInUse => e
|
|
975
|
+
if retries < 5
|
|
976
|
+
MU.log "Subnet group #{subnet_group_id} is not in a removable state, retrying", MU::WARN
|
|
977
|
+
retries += 1
|
|
978
|
+
sleep 30
|
|
979
|
+
retry
|
|
980
|
+
else
|
|
981
|
+
MU.log "Subnet group #{subnet_group_id} is not in a removable state after several retries, giving up. #{e.inspect}", MU::ERR
|
|
982
|
+
end
|
|
983
|
+
end
|
|
984
|
+
|
|
985
|
+
# Remove a Cache Cluster Parameter Group.
|
|
986
|
+
# @param parameter_group_id [string]: The cloud provider's ID of the cache cluster parameter group.
|
|
987
|
+
# @param region [String]: The cloud provider's region in which to operate.
|
|
988
|
+
# @return [void]
|
|
989
|
+
def self.delete_parameter_group(parameter_group_id, region: MU.curRegion)
|
|
990
|
+
retries ||= 0
|
|
991
|
+
MU.log "Deleting parameter group #{parameter_group_id}"
|
|
992
|
+
MU::Cloud::AWS.elasticache(region).delete_cache_parameter_group(
|
|
993
|
+
cache_parameter_group_name: parameter_group_id
|
|
994
|
+
)
|
|
995
|
+
rescue Aws::ElastiCache::Errors::CacheParameterGroupNotFound
|
|
996
|
+
MU.log "Parameter group #{parameter_group_id} disappeared before we could remove it", MU::WARN
|
|
997
|
+
rescue Aws::ElastiCache::Errors::InvalidCacheParameterGroupState => e
|
|
998
|
+
if retries < 5
|
|
999
|
+
MU.log "Parameter group #{parameter_group_id} is not in a removable state, retrying", MU::WARN
|
|
1000
|
+
retries += 1
|
|
1001
|
+
sleep 30
|
|
1002
|
+
retry
|
|
1003
|
+
else
|
|
1004
|
+
MU.log "Parameter group #{parameter_group_id} is not in a removable state after several retries, giving up. #{e.inspect}", MU::ERR
|
|
1005
|
+
end
|
|
1006
|
+
end
|
|
1007
|
+
end
|
|
1008
|
+
end
|
|
1009
|
+
end
|
|
1010
|
+
end
|