Module: Gitlab::OptimisticLocking

Included in:
Ci::BuildTraceChunk, Ci::Pipeline, Ci::Ref, Ci::RetryPipelineService, Ci::Stage
Defined in:
lib/gitlab/optimistic_locking.rb

Constant Summary collapse

MAX_RETRIES =
100

Class Method Summary collapse

Class Method Details

.log_optimistic_lock_retries(name:, retry_attempts:, start_time:) ⇒ Object


36
37
38
39
40
41
42
43
44
45
46
# File 'lib/gitlab/optimistic_locking.rb', line 36

def log_optimistic_lock_retries(name:, retry_attempts:, start_time:)
  return unless retry_attempts > 0

  elapsed_time = Gitlab::Metrics::System.monotonic_time - start_time

  retry_lock_logger.info(
    message: "Optimistic Lock released with retries",
    name: name,
    retries: retry_attempts,
    time_s: elapsed_time)
end

.retry_lock(subject, max_retries = MAX_RETRIES, name:, &block) ⇒ Object Also known as: retry_optimistic_lock


9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
# File 'lib/gitlab/optimistic_locking.rb', line 9

def retry_lock(subject, max_retries = MAX_RETRIES, name:, &block)
  start_time = Gitlab::Metrics::System.monotonic_time
  retry_attempts = 0

  begin
    subject.transaction do
      yield(subject)
    end
  rescue ActiveRecord::StaleObjectError
    raise unless retry_attempts < max_retries

    subject.reset

    retry_attempts += 1
    retry
  ensure
    retry_lock_histogram.observe({}, retry_attempts)

    log_optimistic_lock_retries(
      name: name,
      retry_attempts: retry_attempts,
      start_time: start_time)
  end
end

.retry_lock_histogramObject


52
53
54
55
56
57
58
59
60
# File 'lib/gitlab/optimistic_locking.rb', line 52

def retry_lock_histogram
  @retry_lock_histogram ||=
    Gitlab::Metrics.histogram(
      :gitlab_optimistic_locking_retries,
      'Number of retry attempts to execute optimistic retry lock',
      {},
      [0, 1, 2, 3, 5, 10, 50]
    )
end

.retry_lock_loggerObject


48
49
50
# File 'lib/gitlab/optimistic_locking.rb', line 48

def retry_lock_logger
  @retry_lock_logger ||= Gitlab::Services::Logger.build
end