bin/handler-ec2_node.rb in sensu-plugins-aws-2.0.1 vs bin/handler-ec2_node.rb in sensu-plugins-aws-2.1.0
- old
+ new
@@ -1,8 +1,11 @@
#!/usr/bin/env ruby
#
# CHANGELOG:
+# * 0.7.0:
+# - Update to new API event naming and simplifying ec2_node_should_be_deleted method and fixing
+# match that will work with any user state defined.
# * 0.6.0:
# - Fixed ec2_node_should_be_deleted to account for an empty insances array
# * 0.5.0:
# - Adds configuration to filter by state reason
# * 0.4.0:
@@ -30,10 +33,26 @@
# expressions to match state reasons against. This is useful if you want to fail
# on any `Client.*` state reason or on `Server.*` state reason. The default is
# to match any state reason `.*` Regardless, eventually a client will be
# deleted once AWS stops responding that the instance id exists.
#
+# You could specify a ec2_states.json config file for the states like so:
+#
+# {
+# "ec2_node": {
+# "ec2_states": [
+# "terminated",
+# "stopping",
+# "shutting-down",
+# "stopped"
+# ]
+# }
+# }
+#
+# And add that to your /etc/sensu/conf.d directory.
+# If you do not specify any states the handler would not work
+#
# NOTE: The implementation for correlating Sensu clients to EC2 instances may
# need to be modified to fit your organization. The current implementation
# assumes that Sensu clients' names are the same as their instance IDs in EC2.
# If this is not the case, you can either sub-class this handler and override
# `ec2_node_should_be_deleted?` in your own organization-specific handler, or modify this
@@ -79,11 +98,11 @@
# "attributes": {
# "check": {
# "name": "keepalive",
# "status": 2
# },
-# "occurences": "eval: value > 2"
+# "occurrences": "eval: value > 2"
# }
# }
# },
# "handlers": {
# "ec2_node": {
@@ -112,35 +131,61 @@
class Ec2Node < Sensu::Handler
include Common
def filter; end
+ # Method handle
def handle
+ # Call ec2_node_should_be_deleted method and check for instance state and if valid delete from the sensu API otherwise
+ # instance is in invalid state
if ec2_node_should_be_deleted?
delete_sensu_client!
else
puts "[EC2 Node] #{@event['client']['name']} is in an invalid state"
end
end
+ # Method to delete client from sensu API
def delete_sensu_client!
response = api_request(:DELETE, '/clients/' + @event['client']['name']).code
deletion_status(response)
end
+ # Method to check if there is any insance and if instance is in a valid state that could be deleted
def ec2_node_should_be_deleted?
+ # Defining region for aws SDK object
ec2 = Aws::EC2::Client.new(region: region)
- states = @event['client']['ec2_states'] || settings['ec2_node']['ec2_states'] || ['shutting-down', 'terminated', 'stopping', 'stopped']
+ # Check if attributes or json objects are not defined
+ if @event['client']['ec2_states'].nil? && settings['ec2_node']['ec2_states'].nil?
+ puts 'ec2_states is not define, please add the attributes or create a json config file with valid states keys'
+ else
+ # Asigning valid states
+ instance_states = @event['client']['ec2_states'] || settings['ec2_node']['ec2_states'] || ['shutting-down', 'terminated', 'stopping', 'stopped']
+ end
+
begin
+ # Finding the instance
instances = ec2.describe_instances(instance_ids: [@event['client']['name']]).reservations[0]
+ # If instance is empty/nil instance id is not valid so client can be deleted
if instances.nil? || instances.empty?
true
else
- instance = instances.instances[0]
- state_reason = instance.state_reason.nil? ? nil : instance.state_reason.code
- state = instance.state.name
- states.include?(state) && state_reasons.any? { |reason| Regexp.new(reason) =~ state_reason }
+ # Checking for instance state and reason, and if matches any of the user defined or default reasons then
+ # method returns True
+
+ # Returns Instance object
+ instance_obj = instances.instances[0]
+ # Returns instance state reason in AWS i.e: "Client.UserInitiatedShutdown"
+ instance_state_reason = instance_obj.state_reason.code
+ # Returns the instance state i.e: "terminated"
+ instance_state = instance_obj.state.name
+ # Defining the default reasons why an instance could be deleted or not
+ instance_default_reasons = %w(Client.UserInitiatedShutdown Server.SpotInstanceTermination Client.InstanceInitiatedShutdown)
+ # If user specified a reason use those otherwise use default
+ instance_reasons = @event['client']['ec2_state_reasons'] || settings['ec2_node']['ec2_state_reasons'] || instance_default_reasons
+ # Return true is instance state and instance reason is valid
+ instance_states.include?(instance_state) && instance_reasons.include?(instance_state_reason)
end
rescue Aws::EC2::Errors::InvalidInstanceIDNotFound
true
end
end
@@ -156,15 +201,9 @@
region_check = matches.captures[0]
end
end
region_check
end
- end
-
- def state_reasons
- default_reasons = %w('UserInitiatedShutdown', 'SpotInstanceTermination', 'InstanceInitiatedShutdown')
- reasons = @event['client']['ec2_state_reasons'] || settings['ec2_node']['ec2_state_reasons'] || default_reasons
- @state_reasons ||= reasons.each { |reason| Regexp.new(reason) }
end
def deletion_status(code)
case code
when '202'