Class: NewRelic::Agent::ServerlessHandler

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

Constant Summary collapse

ATTRIBUTE_ARN =
'aws.lambda.arn'
ATTRIBUTE_COLD_START =
'aws.lambda.coldStart'
ATTRIBUTE_REQUEST_ID =
'aws.requestId'
AGENT_ATTRIBUTE_DESTINATIONS =
NewRelic::Agent::AttributeFilter::DST_TRANSACTION_TRACER |
NewRelic::Agent::AttributeFilter::DST_TRANSACTION_EVENTS
EXECUTION_ENVIRONMENT =
"AWS_Lambda_ruby#{RUBY_VERSION.rpartition('.').first}".freeze
LAMBDA_MARKER =
'NR_LAMBDA_MONITORING'
LAMBDA_ENVIRONMENT_VARIABLE =
'AWS_LAMBDA_FUNCTION_NAME'
METHOD_BLOCKLIST =
%i[agent_command_results connect get_agent_commands preconnect profile_data
shutdown].freeze
NAMED_PIPE =
'/tmp/newrelic-telemetry'
SUPPORTABILITY_METRIC =
'Supportability/AWSLambda/HandlerInvocation'
FUNCTION_NAME =
'lambda_function'
PAYLOAD_VERSION =
ENV.fetch('NEW_RELIC_SERVERLESS_PAYLOAD_VERSION', 2)

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initializeServerlessHandler

Returns a new instance of ServerlessHandler.



30
31
32
33
# File 'lib/new_relic/agent/serverless_handler.rb', line 30

def initialize
  @context = nil
  @payloads = {}
end

Class Method Details

.env_var_set?Boolean

Returns:

  • (Boolean)


26
27
28
# File 'lib/new_relic/agent/serverless_handler.rb', line 26

def self.env_var_set?
  ENV.key?(LAMBDA_ENVIRONMENT_VARIABLE)
end

Instance Method Details

#error_data(errors) ⇒ Object



83
84
85
# File 'lib/new_relic/agent/serverless_handler.rb', line 83

def error_data(errors)
  store_payload(:error_data, [nil, errors.map(&:to_collector_array)])
end

#invoke_lambda_function_with_new_relic(event:, context:, method_name:, namespace: nil) ⇒ Object



35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
# File 'lib/new_relic/agent/serverless_handler.rb', line 35

def invoke_lambda_function_with_new_relic(event:, context:, method_name:, namespace: nil)
  NewRelic::Agent.increment_metric(SUPPORTABILITY_METRIC)

  @context = context

  NewRelic::Agent::Tracer.in_transaction(category: :other, name: function_name) do
    add_agent_attributes

    NewRelic::LanguageSupport.constantize(namespace).send(method_name, event: event, context: context)
  end
ensure
  harvest!
  write_output
  reset!
end

#metric_data(stats_hash) ⇒ Object



57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
# File 'lib/new_relic/agent/serverless_handler.rb', line 57

def metric_data(stats_hash)
  payload = [nil,
    stats_hash.started_at,
    (stats_hash.harvested_at || Process.clock_gettime(Process::CLOCK_REALTIME)),
    []]
  stats_hash.each do |metric_spec, stats|
    next if stats.is_reset?

    hash = {name: metric_spec.name}
    hash[:scope] = metric_spec.scope unless metric_spec.scope.empty?

    payload.last.push([hash, [
      stats.call_count,
      stats.total_call_time,
      stats.total_exclusive_time,
      stats.min_call_time,
      stats.max_call_time,
      stats.sum_of_squares
    ]])
  end

  return if payload.last.empty?

  store_payload(:metric_data, payload)
end

#store_payload(method, payload) ⇒ Object



51
52
53
54
55
# File 'lib/new_relic/agent/serverless_handler.rb', line 51

def store_payload(method, payload)
  return if METHOD_BLOCKLIST.include?(method)

  @payloads[method] = payload
end