Module: Webhooks::Outgoing::DeliverySupport

Extended by:
ActiveSupport::Concern
Included in:
Delivery
Defined in:
app/models/concerns/webhooks/outgoing/delivery_support.rb

Constant Summary collapse

ATTEMPT_SCHEDULE =
{
  1 => 15.seconds,
  2 => 1.minute,
  3 => 5.minutes,
  4 => 15.minutes,
  5 => 1.hour,
  6 => 24.hours,
}

Instance Method Summary collapse

Instance Method Details

#attempt_countObject



52
53
54
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 52

def attempt_count
  delivery_attempts.count
end

#attempts_schedule_period_elapsed?Boolean

Returns:

  • (Boolean)


73
74
75
76
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 73

def attempts_schedule_period_elapsed?
  max_attempts_period = ATTEMPT_SCHEDULE.values.sum
  created_at < max_attempts_period.ago
end

#deliver(force: false) ⇒ Object

This method is used to create an attempt and deliver a webhook. If the endpoint is disabled, the attempt will not be created and the webhook will not be delivered. You can bypass this condition by passing ‘force: true`



41
42
43
44
45
46
47
48
49
50
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 41

def deliver(force: false)
  return if endpoint.deactivated? && !force
  # TODO If we ever do away with the `async: true` default for webhook generation, then I believe this needs to
  # change otherwise we'd be attempting the first delivery of webhooks inline.
  if delivery_attempts.new.attempt
    mark_as_delivered!
  else
    deliver_async
  end
end

#deliver_asyncObject



29
30
31
32
33
34
35
36
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 29

def deliver_async
  if still_attempting?
    Webhooks::Outgoing::DeliveryJob.set(wait: next_reattempt_delay).perform_later(self)
  else
    # All delivery attempts have now failed, should we deactivate the endpoint?
    endpoint.handle_exhausted_delivery_attempts
  end
end

#delivered?Boolean

Returns:

  • (Boolean)


56
57
58
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 56

def delivered?
  delivered_at.present?
end

#failed?Boolean

Returns:

  • (Boolean)


65
66
67
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 65

def failed?
  !delivered? && !still_attempting?
end

#failed_or_not_attempted_or_elapsed?Boolean

This method is used to display delivery statuses in the UI. For deactivated endpoints, we don’t make any delivery attempts, however, the delivery itself is still created, so we show it as “failed” in the UI. We also show deliveries as failed when the maximum attempt period has elapsed.

Returns:

  • (Boolean)


82
83
84
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 82

def failed_or_not_attempted_or_elapsed?
  failed? || not_attempted? || attempts_schedule_period_elapsed?
end

#label_stringObject



21
22
23
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 21

def label_string
  event.short_uuid
end

#mark_as_delivered!Object



94
95
96
97
98
99
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 94

def mark_as_delivered!
  ActiveRecord::Base.transaction do
    touch(:delivered_at)
    endpoint.reset_failed_deliveries_tracking!
  end
end

#max_attemptsObject



90
91
92
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 90

def max_attempts
  ATTEMPT_SCHEDULE.keys.max
end

#nameObject



86
87
88
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 86

def name
  event.short_uuid
end

#next_reattempt_delayObject



25
26
27
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 25

def next_reattempt_delay
  ATTEMPT_SCHEDULE[attempt_count]
end

#not_attempted?Boolean

Returns:

  • (Boolean)


69
70
71
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 69

def not_attempted?
  attempt_count.zero?
end

#still_attempting?Boolean

Returns:

  • (Boolean)


60
61
62
63
# File 'app/models/concerns/webhooks/outgoing/delivery_support.rb', line 60

def still_attempting?
  return false if delivered?
  attempt_count <= max_attempts
end