Class: NewRelic::Agent::WorkerLoop

Inherits:
Object
  • Object
show all
Defined in:
lib/new_relic/agent/worker_loop.rb

Overview

A worker loop executes a set of registered tasks on a single thread.

A task is a proc or block with a specified call period in seconds.

Instance Method Summary collapse

Constructor Details

#initializeWorkerLoop

Returns a new instance of WorkerLoop.



9
10
11
12
# File 'lib/new_relic/agent/worker_loop.rb', line 9

def initialize
  @log = log
  @should_run = true
end

Instance Method Details

#keep_runningObject



40
41
42
# File 'lib/new_relic/agent/worker_loop.rb', line 40

def keep_running
  @should_run
end

#lockObject



14
15
16
# File 'lib/new_relic/agent/worker_loop.rb', line 14

def lock
  @@lock ||= Mutex.new
end

#logObject



18
19
20
# File 'lib/new_relic/agent/worker_loop.rb', line 18

def log
  NewRelic::Control.instance.log
end

#run(period, &block) ⇒ Object

Run infinitely, calling the registered tasks at their specified call periods. The caller is responsible for creating the thread that runs this worker loop



24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
# File 'lib/new_relic/agent/worker_loop.rb', line 24

def run(period, &block)
  @period = period
  @next_invocation_time = Time.now + @period
  @task = block
  while keep_running do
    now = Time.now
    while now < @next_invocation_time
      # sleep until this next task's scheduled invocation time
      sleep_time = @next_invocation_time - now
      sleep sleep_time if sleep_time > 0
      now = Time.now
    end
    run_task if keep_running
  end
end

#run_taskObject



48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
# File 'lib/new_relic/agent/worker_loop.rb', line 48

def run_task
  lock.synchronize do
    @task.call 
  end
rescue ServerError => e
  log.debug "Server Error: #{e}"
rescue NewRelic::Agent::ForceRestartException, NewRelic::Agent::ForceDisconnectException
  # blow out the loop
  raise
rescue RuntimeError => e
  # This is probably a server error which has been logged in the server along
  # with your account name.  Check and see if the agent listener is in the
  # stack trace and log it quietly if it is.
  message = "Error running task in worker loop, likely a server error (#{e})"
  if e.backtrace.grep(/agent_listener/).empty?
    log.error message
  else
    log.debug message
    log.debug e.backtrace.join("\n")
  end
rescue Timeout::Error, NewRelic::Agent::ServerConnectionException
  # Want to ignore these because they are handled already
rescue ScriptError, StandardError => e 
  log.error "Error running task in Agent Worker Loop '#{e}': #{e.backtrace.first}" 
  log.debug e.backtrace.join("\n")
ensure
  while @next_invocation_time < Time.now
    @next_invocation_time += @period
  end        
end

#stopObject



44
45
46
# File 'lib/new_relic/agent/worker_loop.rb', line 44

def stop
  @should_run = false
end