Class: Datadog::Core::Utils::OnlyOnceSuccessful

Inherits:
OnlyOnce
  • Object
show all
Defined in:
lib/datadog/core/utils/only_once_successful.rb

Overview

Helper class to execute something with only one success.

This is useful for cases where we want to ensure that a block of code is only executed once, and only if it succeeds. One such example is sending app-started telemetry event.

Successful execution is determined by the return value of the block: any truthy value is considered success.

Thread-safe when used correctly (e.g. be careful of races when lazily initializing instances of this class).

Note: In its current state, this class is not Ractor-safe. In github.com/DataDog/dd-trace-rb/pull/1398#issuecomment-797378810 we have a discussion of alternatives, including an alternative implementation that is Ractor-safe once spent.

Instance Method Summary collapse

Methods inherited from OnlyOnce

#ran?

Constructor Details

#initialize(limit = 0) ⇒ OnlyOnceSuccessful

Returns a new instance of OnlyOnceSuccessful.



21
22
23
24
25
26
27
# File 'lib/datadog/core/utils/only_once_successful.rb', line 21

def initialize(limit = 0)
  super()

  @limit = limit
  @failed = false
  @retries = 0
end

Instance Method Details

#failed?Boolean

Returns:

  • (Boolean)


49
50
51
# File 'lib/datadog/core/utils/only_once_successful.rb', line 49

def failed?
  @mutex.synchronize { @ran_once && @failed }
end

#runObject



29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
# File 'lib/datadog/core/utils/only_once_successful.rb', line 29

def run
  @mutex.synchronize do
    return if @ran_once

    result = yield
    @ran_once = !!result

    if !@ran_once && limited?
      @retries += 1
      check_limit!
    end

    result
  end
end

#success?Boolean

Returns:

  • (Boolean)


45
46
47
# File 'lib/datadog/core/utils/only_once_successful.rb', line 45

def success?
  @mutex.synchronize { @ran_once && !@failed }
end