cloud-mu 3.1.6 → 3.2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (154) hide show
  1. checksums.yaml +4 -4
  2. data/bin/mu-adopt +4 -12
  3. data/bin/mu-azure-tests +57 -0
  4. data/bin/mu-cleanup +2 -4
  5. data/bin/mu-configure +37 -1
  6. data/bin/mu-deploy +3 -3
  7. data/bin/mu-findstray-tests +25 -0
  8. data/bin/mu-gen-docs +2 -4
  9. data/bin/mu-run-tests +23 -10
  10. data/cloud-mu.gemspec +2 -2
  11. data/cookbooks/mu-tools/libraries/helper.rb +1 -1
  12. data/cookbooks/mu-tools/recipes/apply_security.rb +14 -14
  13. data/cookbooks/mu-tools/recipes/aws_api.rb +9 -0
  14. data/extras/generate-stock-images +1 -0
  15. data/modules/mu.rb +82 -95
  16. data/modules/mu/adoption.rb +356 -56
  17. data/modules/mu/cleanup.rb +21 -20
  18. data/modules/mu/cloud.rb +79 -1753
  19. data/modules/mu/cloud/database.rb +49 -0
  20. data/modules/mu/cloud/dnszone.rb +46 -0
  21. data/modules/mu/cloud/machine_images.rb +212 -0
  22. data/modules/mu/cloud/providers.rb +81 -0
  23. data/modules/mu/cloud/resource_base.rb +920 -0
  24. data/modules/mu/cloud/server.rb +40 -0
  25. data/modules/mu/cloud/server_pool.rb +1 -0
  26. data/modules/mu/cloud/ssh_sessions.rb +228 -0
  27. data/modules/mu/cloud/winrm_sessions.rb +237 -0
  28. data/modules/mu/cloud/wrappers.rb +165 -0
  29. data/modules/mu/config.rb +122 -80
  30. data/modules/mu/config/alarm.rb +2 -6
  31. data/modules/mu/config/bucket.rb +1 -1
  32. data/modules/mu/config/cache_cluster.rb +1 -1
  33. data/modules/mu/config/collection.rb +1 -1
  34. data/modules/mu/config/container_cluster.rb +2 -2
  35. data/modules/mu/config/database.rb +83 -104
  36. data/modules/mu/config/database.yml +1 -2
  37. data/modules/mu/config/dnszone.rb +1 -1
  38. data/modules/mu/config/doc_helpers.rb +4 -5
  39. data/modules/mu/config/endpoint.rb +1 -1
  40. data/modules/mu/config/firewall_rule.rb +3 -19
  41. data/modules/mu/config/folder.rb +1 -1
  42. data/modules/mu/config/function.rb +1 -1
  43. data/modules/mu/config/group.rb +1 -1
  44. data/modules/mu/config/habitat.rb +1 -1
  45. data/modules/mu/config/loadbalancer.rb +57 -11
  46. data/modules/mu/config/log.rb +1 -1
  47. data/modules/mu/config/msg_queue.rb +1 -1
  48. data/modules/mu/config/nosqldb.rb +1 -1
  49. data/modules/mu/config/notifier.rb +1 -1
  50. data/modules/mu/config/ref.rb +30 -4
  51. data/modules/mu/config/role.rb +1 -1
  52. data/modules/mu/config/schema_helpers.rb +30 -34
  53. data/modules/mu/config/search_domain.rb +1 -1
  54. data/modules/mu/config/server.rb +4 -12
  55. data/modules/mu/config/server_pool.rb +3 -7
  56. data/modules/mu/config/storage_pool.rb +1 -1
  57. data/modules/mu/config/tail.rb +10 -0
  58. data/modules/mu/config/user.rb +1 -1
  59. data/modules/mu/config/vpc.rb +12 -17
  60. data/modules/mu/defaults/AWS.yaml +32 -32
  61. data/modules/mu/defaults/Azure.yaml +1 -0
  62. data/modules/mu/defaults/Google.yaml +1 -0
  63. data/modules/mu/deploy.rb +16 -15
  64. data/modules/mu/groomer.rb +15 -0
  65. data/modules/mu/groomers/chef.rb +3 -0
  66. data/modules/mu/logger.rb +120 -144
  67. data/modules/mu/master.rb +1 -1
  68. data/modules/mu/mommacat.rb +54 -25
  69. data/modules/mu/mommacat/daemon.rb +10 -7
  70. data/modules/mu/mommacat/naming.rb +82 -3
  71. data/modules/mu/mommacat/search.rb +47 -15
  72. data/modules/mu/mommacat/storage.rb +72 -41
  73. data/modules/mu/{clouds → providers}/README.md +1 -1
  74. data/modules/mu/{clouds → providers}/aws.rb +114 -47
  75. data/modules/mu/{clouds → providers}/aws/alarm.rb +1 -1
  76. data/modules/mu/{clouds → providers}/aws/bucket.rb +2 -2
  77. data/modules/mu/{clouds → providers}/aws/cache_cluster.rb +10 -46
  78. data/modules/mu/{clouds → providers}/aws/collection.rb +3 -3
  79. data/modules/mu/{clouds → providers}/aws/container_cluster.rb +15 -33
  80. data/modules/mu/providers/aws/database.rb +1744 -0
  81. data/modules/mu/{clouds → providers}/aws/dnszone.rb +2 -5
  82. data/modules/mu/{clouds → providers}/aws/endpoint.rb +2 -11
  83. data/modules/mu/{clouds → providers}/aws/firewall_rule.rb +33 -29
  84. data/modules/mu/{clouds → providers}/aws/folder.rb +0 -0
  85. data/modules/mu/{clouds → providers}/aws/function.rb +2 -10
  86. data/modules/mu/{clouds → providers}/aws/group.rb +9 -13
  87. data/modules/mu/{clouds → providers}/aws/habitat.rb +1 -1
  88. data/modules/mu/{clouds → providers}/aws/loadbalancer.rb +41 -33
  89. data/modules/mu/{clouds → providers}/aws/log.rb +2 -2
  90. data/modules/mu/{clouds → providers}/aws/msg_queue.rb +2 -8
  91. data/modules/mu/{clouds → providers}/aws/nosqldb.rb +0 -0
  92. data/modules/mu/{clouds → providers}/aws/notifier.rb +0 -0
  93. data/modules/mu/{clouds → providers}/aws/role.rb +7 -7
  94. data/modules/mu/{clouds → providers}/aws/search_domain.rb +8 -13
  95. data/modules/mu/{clouds → providers}/aws/server.rb +55 -90
  96. data/modules/mu/{clouds → providers}/aws/server_pool.rb +10 -33
  97. data/modules/mu/{clouds → providers}/aws/storage_pool.rb +19 -36
  98. data/modules/mu/{clouds → providers}/aws/user.rb +8 -12
  99. data/modules/mu/{clouds → providers}/aws/userdata/README.md +0 -0
  100. data/modules/mu/{clouds → providers}/aws/userdata/linux.erb +0 -0
  101. data/modules/mu/{clouds → providers}/aws/userdata/windows.erb +0 -0
  102. data/modules/mu/{clouds → providers}/aws/vpc.rb +135 -70
  103. data/modules/mu/{clouds → providers}/aws/vpc_subnet.rb +0 -0
  104. data/modules/mu/{clouds → providers}/azure.rb +4 -1
  105. data/modules/mu/{clouds → providers}/azure/container_cluster.rb +1 -5
  106. data/modules/mu/{clouds → providers}/azure/firewall_rule.rb +8 -1
  107. data/modules/mu/{clouds → providers}/azure/habitat.rb +0 -0
  108. data/modules/mu/{clouds → providers}/azure/loadbalancer.rb +0 -0
  109. data/modules/mu/{clouds → providers}/azure/role.rb +0 -0
  110. data/modules/mu/{clouds → providers}/azure/server.rb +30 -23
  111. data/modules/mu/{clouds → providers}/azure/user.rb +1 -1
  112. data/modules/mu/{clouds → providers}/azure/userdata/README.md +0 -0
  113. data/modules/mu/{clouds → providers}/azure/userdata/linux.erb +0 -0
  114. data/modules/mu/{clouds → providers}/azure/userdata/windows.erb +0 -0
  115. data/modules/mu/{clouds → providers}/azure/vpc.rb +4 -6
  116. data/modules/mu/{clouds → providers}/cloudformation.rb +1 -1
  117. data/modules/mu/{clouds → providers}/cloudformation/alarm.rb +3 -3
  118. data/modules/mu/{clouds → providers}/cloudformation/cache_cluster.rb +3 -3
  119. data/modules/mu/{clouds → providers}/cloudformation/collection.rb +3 -3
  120. data/modules/mu/{clouds → providers}/cloudformation/database.rb +6 -17
  121. data/modules/mu/{clouds → providers}/cloudformation/dnszone.rb +3 -3
  122. data/modules/mu/{clouds → providers}/cloudformation/firewall_rule.rb +3 -3
  123. data/modules/mu/{clouds → providers}/cloudformation/loadbalancer.rb +3 -3
  124. data/modules/mu/{clouds → providers}/cloudformation/log.rb +3 -3
  125. data/modules/mu/{clouds → providers}/cloudformation/server.rb +7 -7
  126. data/modules/mu/{clouds → providers}/cloudformation/server_pool.rb +5 -5
  127. data/modules/mu/{clouds → providers}/cloudformation/vpc.rb +3 -3
  128. data/modules/mu/{clouds → providers}/docker.rb +0 -0
  129. data/modules/mu/{clouds → providers}/google.rb +14 -6
  130. data/modules/mu/{clouds → providers}/google/bucket.rb +1 -1
  131. data/modules/mu/{clouds → providers}/google/container_cluster.rb +28 -13
  132. data/modules/mu/{clouds → providers}/google/database.rb +1 -8
  133. data/modules/mu/{clouds → providers}/google/firewall_rule.rb +2 -2
  134. data/modules/mu/{clouds → providers}/google/folder.rb +4 -8
  135. data/modules/mu/{clouds → providers}/google/function.rb +3 -3
  136. data/modules/mu/{clouds → providers}/google/group.rb +8 -16
  137. data/modules/mu/{clouds → providers}/google/habitat.rb +3 -7
  138. data/modules/mu/{clouds → providers}/google/loadbalancer.rb +1 -1
  139. data/modules/mu/{clouds → providers}/google/role.rb +42 -34
  140. data/modules/mu/{clouds → providers}/google/server.rb +25 -10
  141. data/modules/mu/{clouds → providers}/google/server_pool.rb +10 -10
  142. data/modules/mu/{clouds → providers}/google/user.rb +31 -21
  143. data/modules/mu/{clouds → providers}/google/userdata/README.md +0 -0
  144. data/modules/mu/{clouds → providers}/google/userdata/linux.erb +0 -0
  145. data/modules/mu/{clouds → providers}/google/userdata/windows.erb +0 -0
  146. data/modules/mu/{clouds → providers}/google/vpc.rb +37 -2
  147. data/modules/tests/centos6.yaml +11 -0
  148. data/modules/tests/centos7.yaml +11 -0
  149. data/modules/tests/centos8.yaml +12 -0
  150. data/modules/tests/rds.yaml +108 -0
  151. data/modules/tests/regrooms/rds.yaml +123 -0
  152. data/spec/mu/clouds/azure_spec.rb +2 -2
  153. metadata +108 -89
  154. data/modules/mu/clouds/aws/database.rb +0 -1974
@@ -156,8 +156,8 @@ module MU
156
156
  begin
157
157
  resp = MU::Cloud::AWS.iam(credentials: credentials).list_roles(marker: marker)
158
158
  resp.roles.each{ |role|
159
- # XXX Maybe we should have a more generic way to delete IAM profiles and policies. The call itself should be moved from MU::Cloud::AWS::Server.
160
- # MU::Cloud::AWS::Server.removeIAMProfile(role.role_name) if role.role_name.match(/^#{Regexp.quote(MU.deploy_id)}/)
159
+ # XXX Maybe we should have a more generic way to delete IAM profiles and policies. The call itself should be moved from MU::Cloud.resourceClass("AWS", "Server").
160
+ # MU::Cloud.resourceClass("AWS", "Server").removeIAMProfile(role.role_name) if role.role_name.match(/^#{Regexp.quote(MU.deploy_id)}/)
161
161
  }
162
162
  marker = resp.marker
163
163
  end while resp.is_truncated
@@ -378,9 +378,9 @@ module MU
378
378
 
379
379
  if dom['slow_logs']
380
380
  if configurator.haveLitterMate?(dom['slow_logs'], "log")
381
- dom['dependencies'] << { "name" => dom['slow_logs'], "type" => "log" }
381
+ MU::Config.addDependency(dom, dom['slow_logs'], "log")
382
382
  else
383
- log_group = MU::Cloud::AWS::Log.find(cloud_id: dom['slow_logs'], region: dom['region']).values.first
383
+ log_group = MU::Cloud.resourceClass("AWS", "Log").find(cloud_id: dom['slow_logs'], region: dom['region']).values.first
384
384
  if !log_group
385
385
  MU.log "Specified slow_logs CloudWatch log group '#{dom['slow_logs']}' in SearchDomain '#{dom['name']}' doesn't appear to exist", MU::ERR
386
386
  ok = false
@@ -395,7 +395,7 @@ module MU
395
395
  "credentials" => dom['credentials']
396
396
  }
397
397
  ok = false if !configurator.insertKitten(log_group, "logs")
398
- dom['dependencies'] << { "name" => dom['slow_logs'], "type" => "log" }
398
+ MU::Config.addDependency(dom, dom['slow_logs'], "log")
399
399
  end
400
400
 
401
401
  if dom['advanced_options']
@@ -456,12 +456,7 @@ module MU
456
456
  ]
457
457
  }
458
458
  configurator.insertKitten(roledesc, "roles")
459
-
460
- dom['dependencies'] ||= []
461
- dom['dependencies'] << {
462
- "type" => "role",
463
- "name" => dom['name']+"cognitorole"
464
- }
459
+ MU::Config.addDependency(dom, dom['name']+"cognitorole", "role")
465
460
  end
466
461
 
467
462
  end
@@ -525,7 +520,7 @@ module MU
525
520
  arn = @config['slow_logs']
526
521
  else
527
522
  log_group = @deploy.findLitterMate(type: "log", name: @config['slow_logs'])
528
- log_group = MU::Cloud::AWS::Log.find(cloud_id: log_group.mu_name, region: log_group.cloudobj.config['region']).values.first
523
+ log_group = MU::Cloud.resourceClass("AWS", "Log").find(cloud_id: log_group.mu_name, region: log_group.cloudobj.config['region']).values.first
529
524
  if log_group.nil? or log_group.arn.nil?
530
525
  raise MuError, "Failed to retrieve ARN of sibling LogGroup '#{@config['slow_logs']}'"
531
526
  end
@@ -552,7 +547,7 @@ module MU
552
547
  params[:log_publishing_options]["SEARCH_SLOW_LOGS"] = {}
553
548
  params[:log_publishing_options]["SEARCH_SLOW_LOGS"][:enabled] = true
554
549
  params[:log_publishing_options]["SEARCH_SLOW_LOGS"][:cloud_watch_logs_log_group_arn] = arn
555
- MU::Cloud::AWS::Log.allowService("es.amazonaws.com", arn, @config['region'])
550
+ MU::Cloud.resourceClass("AWS", "Log").allowService("es.amazonaws.com", arn, @config['region'])
556
551
  end
557
552
  end
558
553
 
@@ -145,7 +145,7 @@ module MU
145
145
  raise MuError, "My second argument should be a hash of variables to pass into ERB templates"
146
146
  end
147
147
  $mu = OpenStruct.new(template_variables)
148
- userdata_dir = File.expand_path(MU.myRoot+"/modules/mu/clouds/aws/userdata")
148
+ userdata_dir = File.expand_path(MU.myRoot+"/modules/mu/providers/aws/userdata")
149
149
  platform = "linux" if %w{centos centos6 centos7 ubuntu ubuntu14 rhel rhel7 rhel71 amazon}.include? platform
150
150
  platform = "windows" if %w{win2k12r2 win2k12 win2k8 win2k8r2 win2k16}.include? platform
151
151
  erbfile = "#{userdata_dir}/#{platform}.erb"
@@ -299,7 +299,7 @@ module MU
299
299
  raise MuError, "Got null subnet id out of #{@config['vpc']}"
300
300
  end
301
301
  MU.log "Deploying #{@mu_name} into VPC #{@vpc.cloud_id} Subnet #{subnet.cloud_id}"
302
- punchAdminNAT
302
+ allowBastionAccess
303
303
  instance_descriptor[:subnet_id] = subnet.cloud_id
304
304
  end
305
305
 
@@ -399,13 +399,13 @@ module MU
399
399
  # Figure out what's needed to SSH into this server.
400
400
  # @return [Array<String>]: nat_ssh_key, nat_ssh_user, nat_ssh_host, canonical_ip, ssh_user, ssh_key_name, alternate_names
401
401
  def getSSHConfig
402
- describe(cloud_id: @cloud_id)
402
+ cloud_desc(use_cache: false) # make sure we're current
403
403
  # XXX add some awesome alternate names from metadata and make sure they end
404
404
  # up in MU::MommaCat's ssh config wangling
405
405
  return nil if @config.nil? or @deploy.nil?
406
406
 
407
407
  nat_ssh_key = nat_ssh_user = nat_ssh_host = nil
408
- if !@config["vpc"].nil? and !MU::Cloud::AWS::VPC.haveRouteToInstance?(cloud_desc, region: @config['region'], credentials: @config['credentials'])
408
+ if !@config["vpc"].nil? and !MU::Cloud.resourceClass("AWS", "VPC").haveRouteToInstance?(cloud_desc, region: @config['region'], credentials: @config['credentials'])
409
409
  if !@nat.nil?
410
410
  if @nat.is_a?(Struct) && @nat.nat_gateway_id && @nat.nat_gateway_id.start_with?("nat-")
411
411
  raise MuError, "Configured to use NAT Gateway, but I have no route to instance. Either use Bastion, or configure VPC peering"
@@ -444,8 +444,7 @@ module MU
444
444
  # administravia for a new instance.
445
445
  def postBoot(instance_id = nil)
446
446
  @cloud_id ||= instance_id
447
- node, _config, deploydata = describe(cloud_id: @cloud_id)
448
- @mu_name ||= node
447
+ _node, _config, deploydata = describe(cloud_id: @cloud_id)
449
448
 
450
449
  raise MuError, "Couldn't find instance #{@mu_name} (#{@cloud_id})" if !cloud_desc
451
450
  return false if !MU::MommaCat.lock(@cloud_id+"-orchestrate", true)
@@ -482,7 +481,7 @@ module MU
482
481
  end
483
482
  }
484
483
 
485
- punchAdminNAT
484
+ allowBastionAccess
486
485
 
487
486
  setAlarms
488
487
 
@@ -615,7 +614,7 @@ module MU
615
614
  return nil
616
615
  end
617
616
 
618
- asgs = MU::Cloud::AWS::ServerPool.find(
617
+ asgs = MU::Cloud.resourceClass("AWS", "ServerPool").find(
619
618
  instance_id: @cloud_id,
620
619
  region: @config['region'],
621
620
  credentials: @credentials
@@ -725,15 +724,15 @@ module MU
725
724
 
726
725
  if int.groups.size > 0
727
726
 
728
- require 'mu/clouds/aws/firewall_rule'
729
- ifaces = MU::Cloud::AWS::FirewallRule.getAssociatedInterfaces(int.groups.map { |sg| sg.group_id }, credentials: @credentials, region: @config['region'])
727
+ require 'mu/providers/aws/firewall_rule'
728
+ ifaces = MU::Cloud.resourceClass("AWS", "FirewallRule").getAssociatedInterfaces(int.groups.map { |sg| sg.group_id }, credentials: @credentials, region: @config['region'])
730
729
  done_local_rules = false
731
730
  int.groups.each { |sg|
732
731
  if !done_local_rules and ifaces[sg.group_id].size == 1
733
- sg_desc = MU::Cloud::AWS::FirewallRule.find(cloud_id: sg.group_id, credentials: @credentials, region: @config['region']).values.first
732
+ sg_desc = MU::Cloud.resourceClass("AWS", "FirewallRule").find(cloud_id: sg.group_id, credentials: @credentials, region: @config['region']).values.first
734
733
  if sg_desc
735
- bok["ingress_rules"] = MU::Cloud::AWS::FirewallRule.rulesToBoK(sg_desc.ip_permissions)
736
- bok["ingress_rules"].concat(MU::Cloud::AWS::FirewallRule.rulesToBoK(sg_desc.ip_permissions_egress, egress: true))
734
+ bok["ingress_rules"] = MU::Cloud.resourceClass("AWS", "FirewallRule").rulesToBoK(sg_desc.ip_permissions)
735
+ bok["ingress_rules"].concat(MU::Cloud.resourceClass("AWS", "FirewallRule").rulesToBoK(sg_desc.ip_permissions_egress, egress: true))
737
736
  done_local_rules = true
738
737
  next
739
738
  end
@@ -802,44 +801,13 @@ module MU
802
801
  end
803
802
  deploydata["region"] = @config['region'] if !@config['region'].nil?
804
803
  if !@named
805
- MU::MommaCat.nameKitten(self)
804
+ MU::MommaCat.nameKitten(self, no_dns: true)
806
805
  @named = true
807
806
  end
808
807
 
809
808
  return deploydata
810
809
  end
811
810
 
812
- # If the specified server is in a VPC, and has a NAT, make sure we'll
813
- # be letting ssh traffic in from said NAT.
814
- def punchAdminNAT
815
- if @config['vpc'].nil? or
816
- (
817
- !@config['vpc'].has_key?("nat_host_id") and
818
- !@config['vpc'].has_key?("nat_host_tag") and
819
- !@config['vpc'].has_key?("nat_host_ip") and
820
- !@config['vpc'].has_key?("nat_host_name")
821
- )
822
- return nil
823
- end
824
-
825
- return nil if @nat.is_a?(Struct) && @nat.nat_gateway_id && @nat.nat_gateway_id.start_with?("nat-")
826
-
827
- dependencies if @nat.nil?
828
- if @nat.nil? or @nat.cloud_desc.nil?
829
- raise MuError, "#{@mu_name} (#{MU.deploy_id}) is configured to use #{@config['vpc']} but I can't find the cloud descriptor for a matching NAT instance"
830
- end
831
- MU.log "Adding administrative holes for NAT host #{@nat.cloud_desc.private_ip_address} to #{@mu_name}"
832
- if !@deploy.kittens['firewall_rules'].nil?
833
- @deploy.kittens['firewall_rules'].values.each { |acl|
834
- if acl.config["admin"]
835
- acl.addRule([@nat.cloud_desc.private_ip_address], proto: "tcp")
836
- acl.addRule([@nat.cloud_desc.private_ip_address], proto: "udp")
837
- acl.addRule([@nat.cloud_desc.private_ip_address], proto: "icmp")
838
- end
839
- }
840
- end
841
- end
842
-
843
811
  # Called automatically by {MU::Deploy#createResources}
844
812
  def groom
845
813
  MU::MommaCat.lock(@cloud_id+"-groom")
@@ -851,7 +819,7 @@ module MU
851
819
  end
852
820
  end
853
821
 
854
- punchAdminNAT
822
+ allowBastionAccess
855
823
 
856
824
  tagVolumes
857
825
 
@@ -883,12 +851,25 @@ module MU
883
851
 
884
852
  begin
885
853
  getIAMProfile
854
+
855
+ dbs = @deploy.findLitterMate(type: "database", return_all: true)
856
+ if dbs
857
+ dbs.each_pair { |sib_name, sib|
858
+ @groomer.groomer_class.grantSecretAccess(@mu_name, sib_name, "database_credentials")
859
+ if sib.config and sib.config['auth_vault']
860
+ @groomer.groomer_class.grantSecretAccess(@mu_name, sib.config['auth_vault']['vault'], sib.config['auth_vault']['item'])
861
+ end
862
+ }
863
+ end
864
+
886
865
  if @config['groom'].nil? or @config['groom']
887
866
  @groomer.run(purpose: "Full Initial Run", max_retries: 15, reboot_first_fail: (windows? and @config['groomer'] != "Ansible"), timeout: @config['groomer_timeout'])
888
867
  end
889
868
  rescue MU::Groomer::RunError => e
869
+ raise e if !@config['create_image'].nil? and !@config['image_created']
890
870
  MU.log "Proceeding after failed initial Groomer run, but #{@mu_name} may not behave as expected!", MU::WARN, details: e.message
891
871
  rescue StandardError => e
872
+ raise e if !@config['create_image'].nil? and !@config['image_created']
892
873
  MU.log "Caught #{e.inspect} on #{@mu_name} in an unexpected place (after @groomer.run on Full Initial Run)", MU::ERR
893
874
  end
894
875
 
@@ -961,7 +942,7 @@ module MU
961
942
  # Our deploydata gets corrupted often with server pools, this will cause us to use the wrong IP to identify a node
962
943
  # which will cause us to create certificates, DNS records and other artifacts with incorrect information which will cause our deploy to fail.
963
944
  # The cloud_id is always correct so lets use 'cloud_desc' to get the correct IPs
964
- if MU::Cloud::AWS::VPC.haveRouteToInstance?(cloud_desc, region: @config['region'], credentials: @config['credentials']) or @deploydata["public_ip_address"].nil?
945
+ if MU::Cloud.resourceClass("AWS", "VPC").haveRouteToInstance?(cloud_desc, region: @config['region'], credentials: @config['credentials']) or @deploydata["public_ip_address"].nil?
965
946
  @config['canonical_ip'] = cloud_desc.private_ip_address
966
947
  @deploydata["private_ip_address"] = cloud_desc.private_ip_address
967
948
  return cloud_desc.private_ip_address
@@ -1181,10 +1162,7 @@ module MU
1181
1162
  end
1182
1163
  end
1183
1164
 
1184
- if @cloud_id.nil?
1185
- describe
1186
- @cloud_id = cloud_desc.instance_id
1187
- end
1165
+ @cloud_id ||= cloud_desc(use_cache: false).instance_id
1188
1166
  ssh_keydir = "#{Etc.getpwuid(Process.uid).dir}/.ssh"
1189
1167
  ssh_key_name = @deploy.ssh_key_name
1190
1168
 
@@ -1318,7 +1296,7 @@ module MU
1318
1296
 
1319
1297
  if @deploy
1320
1298
  MU::Cloud::AWS.createStandardTags(
1321
- resource_id,
1299
+ creation.volume_id,
1322
1300
  region: @config['region'],
1323
1301
  credentials: @config['credentials'],
1324
1302
  optional: @config['optional_tags'],
@@ -1577,7 +1555,11 @@ module MU
1577
1555
  return if !instance
1578
1556
 
1579
1557
  id ||= instance.instance_id
1580
- MU::MommaCat.lock(".cleanup-"+id)
1558
+ begin
1559
+ MU::MommaCat.lock(".cleanup-"+id)
1560
+ rescue Errno::ENOENT => e
1561
+ MU.log "No lock for terminating instance #{id} due to missing metadata", MU::DEBUG
1562
+ end
1581
1563
 
1582
1564
  ips, names = getAddresses(instance, region: region, credentials: credentials)
1583
1565
  targets = ips +names
@@ -1632,7 +1614,11 @@ module MU
1632
1614
  end
1633
1615
 
1634
1616
  MU.log "#{instance.instance_id}#{server_obj ? " ("+server_obj.mu_name+")" : ""} terminated" if !noop
1635
- MU::MommaCat.unlock(".cleanup-"+id)
1617
+ begin
1618
+ MU::MommaCat.unlock(".cleanup-"+id)
1619
+ rescue Errno::ENOENT => e
1620
+ MU.log "No lock for terminating instance #{id} due to missing metadata", MU::DEBUG
1621
+ end
1636
1622
 
1637
1623
  end
1638
1624
 
@@ -1690,26 +1676,7 @@ module MU
1690
1676
  "type" => "object"
1691
1677
  }
1692
1678
  },
1693
- "ingress_rules" => {
1694
- "items" => {
1695
- "properties" => {
1696
- "sgs" => {
1697
- "type" => "array",
1698
- "items" => {
1699
- "description" => "Other AWS Security Groups; resources that are associated with this group will have this rule applied to their traffic",
1700
- "type" => "string"
1701
- }
1702
- },
1703
- "lbs" => {
1704
- "type" => "array",
1705
- "items" => {
1706
- "description" => "AWS Load Balancers which will have this rule applied to their traffic",
1707
- "type" => "string"
1708
- }
1709
- }
1710
- }
1711
- }
1712
- },
1679
+ "ingress_rules" => MU::Cloud.resourceClass("AWS", "FirewallRule").ingressRuleAddtlSchema,
1713
1680
  "ssh_user" => {
1714
1681
  "type" => "string",
1715
1682
  "default" => "root",
@@ -1777,8 +1744,7 @@ module MU
1777
1744
 
1778
1745
  MU::Cloud.availableClouds.each { |cloud|
1779
1746
  next if cloud == "AWS"
1780
- cloudbase = Object.const_get("MU").const_get("Cloud").const_get(cloud)
1781
- foreign_types = (cloudbase.listInstanceTypes).values.first
1747
+ foreign_types = (MU::Cloud.cloudClass(cloud).listInstanceTypes).values.first
1782
1748
  if foreign_types.size == 1
1783
1749
  foreign_types = foreign_types.values.first
1784
1750
  end
@@ -1845,12 +1811,7 @@ module MU
1845
1811
  end
1846
1812
 
1847
1813
  configurator.insertKitten(role, "roles")
1848
-
1849
- server["dependencies"] ||= []
1850
- server["dependencies"] << {
1851
- "type" => "role",
1852
- "name" => server["name"]
1853
- }
1814
+ MU::Config.addDependency(server, server["name"], "role")
1854
1815
  end
1855
1816
 
1856
1817
  # Cloud-specific pre-processing of {MU::Config::BasketofKittens::servers}, bare and unvalidated.
@@ -1901,10 +1862,7 @@ module MU
1901
1862
  server["loadbalancers"].each { |lb|
1902
1863
  lb["name"] ||= lb["concurrent_load_balancer"]
1903
1864
  if lb["name"]
1904
- server["dependencies"] << {
1905
- "type" => "loadbalancer",
1906
- "name" => lb["name"]
1907
- }
1865
+ MU::Config.addDependency(server, lb["name"], "loadbalancer")
1908
1866
  end
1909
1867
  }
1910
1868
  end
@@ -2019,6 +1977,13 @@ module MU
2019
1977
  configured_storage
2020
1978
  end
2021
1979
 
1980
+ # Return all of the IP addresses, public and private, from all of our
1981
+ # network interfaces.
1982
+ # @return [Array<String>]
1983
+ def listIPs
1984
+ MU::Cloud::AWS::Server.getAddresses(cloud_desc).first
1985
+ end
1986
+
2022
1987
  private
2023
1988
 
2024
1989
  def bootstrapGroomer
@@ -2144,7 +2109,7 @@ module MU
2144
2109
  subnet = @vpc.getSubnet(cloud_id: cloud_desc.subnet_id)
2145
2110
 
2146
2111
  _nat_ssh_key, _nat_ssh_user, nat_ssh_host, _canonical_ip, _ssh_user, _ssh_key_name = getSSHConfig
2147
- if subnet.private? and !nat_ssh_host and !MU::Cloud::AWS::VPC.haveRouteToInstance?(cloud_desc, region: @config['region'], credentials: @config['credentials'])
2112
+ if subnet.private? and !nat_ssh_host and !MU::Cloud.resourceClass("AWS", "VPC").haveRouteToInstance?(cloud_desc, region: @config['region'], credentials: @config['credentials'])
2148
2113
  raise MuError, "#{@mu_name} is in a private subnet (#{subnet}), but has no bastion host configured, and I have no other route to it"
2149
2114
  end
2150
2115
 
@@ -2236,15 +2201,15 @@ module MU
2236
2201
  alarm["dimensions"] = [{:name => "InstanceId", :value => @cloud_id}]
2237
2202
 
2238
2203
  if alarm["enable_notifications"]
2239
- topic_arn = MU::Cloud::AWS::Notification.createTopic(alarm["notification_group"], region: @config["region"], credentials: @config['credentials'])
2240
- MU::Cloud::AWS::Notification.subscribe(arn: topic_arn, protocol: alarm["notification_type"], endpoint: alarm["notification_endpoint"], region: @config["region"], credentials: @config["credentials"])
2204
+ topic_arn = MU::Cloud.resourceClass("AWS", "Notification").createTopic(alarm["notification_group"], region: @config["region"], credentials: @config['credentials'])
2205
+ MU::Cloud.resourceClass("AWS", "Notification").subscribe(arn: topic_arn, protocol: alarm["notification_type"], endpoint: alarm["notification_endpoint"], region: @config["region"], credentials: @config["credentials"])
2241
2206
  alarm["alarm_actions"] = [topic_arn]
2242
2207
  alarm["ok_actions"] = [topic_arn]
2243
2208
  end
2244
2209
 
2245
2210
  alarm_name = alarm_obj ? alarm_obj.cloud_id : "#{@mu_name}-#{alarm['name']}".upcase
2246
2211
 
2247
- MU::Cloud::AWS::Alarm.setAlarm(
2212
+ MU::Cloud.resourceClass("AWS", "Alarm").setAlarm(
2248
2213
  name: alarm_name,
2249
2214
  ok_actions: alarm["ok_actions"],
2250
2215
  alarm_actions: alarm["alarm_actions"],
@@ -120,7 +120,7 @@ module MU
120
120
  if !@deploy.nocleanup
121
121
  Thread.new {
122
122
  MU.dupGlobals(parent_thread_id)
123
- MU::Cloud::AWS::Server.terminateInstance(id: member.instance_id)
123
+ MU::Cloud.resourceClass("AWS", "Server").terminateInstance(id: member.instance_id)
124
124
  }
125
125
  end
126
126
  end
@@ -813,26 +813,7 @@ module MU
813
813
  }
814
814
  }
815
815
  },
816
- "ingress_rules" => {
817
- "items" => {
818
- "properties" => {
819
- "sgs" => {
820
- "type" => "array",
821
- "items" => {
822
- "description" => "Other AWS Security Groups; resources that are associated with this group will have this rule applied to their traffic",
823
- "type" => "string"
824
- }
825
- },
826
- "lbs" => {
827
- "type" => "array",
828
- "items" => {
829
- "description" => "AWS Load Balancers which will have this rule applied to their traffic",
830
- "type" => "string"
831
- }
832
- }
833
- }
834
- }
835
- }
816
+ "ingress_rules" => MU::Cloud.resourceClass("AWS", "FirewallRule").ingressRuleAddtlSchema
836
817
  }
837
818
  [toplevel_required, schema]
838
819
  end
@@ -905,7 +886,7 @@ module MU
905
886
  launch = pool["basis"]["launch_config"]
906
887
  launch['iam_policies'] ||= pool['iam_policies']
907
888
 
908
- launch['size'] = MU::Cloud::AWS::Server.validateInstanceType(launch["size"], pool["region"])
889
+ launch['size'] = MU::Cloud.resourceClass("AWS", "Server").validateInstanceType(launch["size"], pool["region"])
909
890
  ok = false if launch['size'].nil?
910
891
  if !launch['generate_iam_role']
911
892
  if !launch['iam_role'] and pool['cloud'] != "CloudFormation"
@@ -949,11 +930,7 @@ module MU
949
930
 
950
931
  role['credentials'] = pool['credentials'] if pool['credentials']
951
932
  configurator.insertKitten(role, "roles")
952
- pool["dependencies"] ||= []
953
- pool["dependencies"] << {
954
- "type" => "role",
955
- "name" => pool["name"]
956
- }
933
+ MU::Config.addDependency(pool, pool['name'], "role")
957
934
  end
958
935
  launch["ami_id"] ||= launch["image_id"]
959
936
  if launch["server"].nil? and launch["instance_id"].nil? and launch["ami_id"].nil?
@@ -967,7 +944,7 @@ module MU
967
944
  end
968
945
  end
969
946
  if launch["server"] != nil
970
- pool["dependencies"] << {"type" => "server", "name" => launch["server"]}
947
+ MU::Config.addDependency(pool, launch["server"], "server", phase: "groom")
971
948
  # XXX I dunno, maybe toss an error if this isn't done already
972
949
  # servers.each { |server|
973
950
  # if server["name"] == launch["server"]
@@ -1123,7 +1100,7 @@ module MU
1123
1100
  end
1124
1101
  end
1125
1102
 
1126
- # MU::Cloud::AWS::Server.removeIAMProfile(resource_id)
1103
+ # MU::Cloud.resourceClass("AWS", "Server").removeIAMProfile(resource_id)
1127
1104
 
1128
1105
  # Generally there should be a launch_configuration of the same name
1129
1106
  # XXX search for these independently, too?
@@ -1164,14 +1141,14 @@ module MU
1164
1141
  @config['basis']['launch_config']["ami_id"] = @deploy.deployment["images"][@config['basis']['launch_config']["server"]]["image_id"]
1165
1142
  MU.log "Using AMI '#{@config['basis']['launch_config']["ami_id"]}' from sibling server #{@config['basis']['launch_config']["server"]} in ServerPool #{@mu_name}"
1166
1143
  elsif !@config['basis']['launch_config']["instance_id"].nil?
1167
- @config['basis']['launch_config']["ami_id"] = MU::Cloud::AWS::Server.createImage(
1144
+ @config['basis']['launch_config']["ami_id"] = MU::Cloud.resourceClass("AWS", "Server").createImage(
1168
1145
  name: @mu_name,
1169
1146
  instance_id: @config['basis']['launch_config']["instance_id"],
1170
1147
  credentials: @config['credentials'],
1171
1148
  region: @config['region']
1172
1149
  )[@config['region']]
1173
1150
  end
1174
- MU::Cloud::AWS::Server.waitForAMI(@config['basis']['launch_config']["ami_id"], credentials: @config['credentials'])
1151
+ MU::Cloud.resourceClass("AWS", "Server").waitForAMI(@config['basis']['launch_config']["ami_id"], credentials: @config['credentials'])
1175
1152
 
1176
1153
  oldlaunch = MU::Cloud::AWS.autoscale(region: @config['region'], credentials: @config['credentials']).describe_launch_configurations(
1177
1154
  launch_configuration_names: [@mu_name]
@@ -1226,12 +1203,12 @@ module MU
1226
1203
  vol.delete("encrypted")
1227
1204
  end
1228
1205
  end
1229
- mapping, _cfm_mapping = MU::Cloud::AWS::Server.convertBlockDeviceMapping(vol)
1206
+ mapping, _cfm_mapping = MU::Cloud.resourceClass("AWS", "Server").convertBlockDeviceMapping(vol)
1230
1207
  storage << mapping
1231
1208
  }
1232
1209
  end
1233
1210
 
1234
- storage.concat(MU::Cloud::AWS::Server.ephemeral_mappings)
1211
+ storage.concat(MU::Cloud.resourceClass("AWS", "Server").ephemeral_mappings)
1235
1212
 
1236
1213
  if @config['basis']['launch_config']['generate_iam_role']
1237
1214
  role = @deploy.findLitterMate(name: @config['name'], type: "roles")