Module: FoodCritic::Notifications

Included in:
Api
Defined in:
lib/foodcritic/notifications.rb

Overview

This module contains the logic for the parsing of

Chef Notifications

(docs.chef.io/resource_common.html#notifications).

Instance Method Summary collapse

Instance Method Details

#notifications(ast) ⇒ Object

Extracts notification details from the provided AST, returning an array of notification hashes.

template "/etc/www/configures-apache.conf" do
  notifies :restart, "service[apache]"
end

=> [{:resource_name=>"apache",
  :resource_type=>:service,
  :type=>:notifies,
  :style=>:new,
  :action=>:restart,
  :timing=>:delayed}]


20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
# File 'lib/foodcritic/notifications.rb', line 20

def notifications(ast)
  # Sanity check the AST provided.
  return [] unless ast.respond_to?(:xpath)

  # We are mapping each `notifies` or `subscribes` line in the provided
  # AST to a Hash with the extracted details.
  notification_nodes(ast).map do |notify|

    # Chef supports two styles of notification.
    notified_resource = if new_style_notification?(notify)
                          # `notifies :restart, "service[foo]"`
                          new_style_notification(notify)
                        else
                          # `notifies :restart, resources(service: "foo")`
                          old_style_notification(notify)
                        end

    # Ignore if the notification was not parsed
    next unless notified_resource

    # Now merge the extract notification details with the attributes
    # that are common to both styles of notification.
    notified_resource.merge(
      {
        # The `:type` of notification: `:subscribes` or `:notifies`.
        type: notification_type(notify),

        # The `:style` of notification: `:new` or `:old`.
        style: new_style_notification?(notify) ? :new : :old,

        # The target resource action.
        action: notification_action(notify),

        # The notification timing: `:before`, `:immediate` or `:delayed`.
        timing: notification_timing(notify),
      }
    )
  end.compact
end