class Wavefront::Writer::Core

Abstract class extended by the other writers. Methods required whatever mechanism actually sends the points.

A point is defined as a hash with the following keys: path [String] metric path. (mandatory) value [Numeric] value of metric. Numeric. Mandatory. ts [Time, Integer] timestamp for point. Defaults to

current UTC time.

source [String] originating source of metric. Defaults to

the local hostname.

tags [Hash] key:value point tags which will be applied in

addition to any tags defined in the #initialize()
method.

Attributes

calling_class[R]
conn[R]
creds[R]
logger[R]
opts[R]
summary[R]

Public Class Methods

new(calling_class) click to toggle source
# File lib/wavefront-sdk/writers/core.rb, line 30
def initialize(calling_class)
  @calling_class = calling_class
  @creds         = calling_class.creds
  @opts          = calling_class.opts
  @logger        = calling_class.logger
  @manage_conn   = calling_class.manage_conn
  @summary       = Wavefront::Writer::Summary.new

  validate_credentials(creds) if respond_to?(:validate_credentials)
  post_initialize(creds, opts) if respond_to?(:post_initialize)
end

Public Instance Methods

chunk_size() click to toggle source

We divide metrics up into manageable chunks and send them in batches. This dictates how large those bundles are. You can override the value with the chunk_size option @return [Integer]

# File lib/wavefront-sdk/writers/core.rb, line 153
def chunk_size
  1000
end
do_write(points, openclose, _prefix) click to toggle source
# File lib/wavefront-sdk/writers/core.rb, line 59
def do_write(points, openclose, _prefix)
  open if openclose && respond_to?(:open)

  begin
    write_loop(points)
  ensure
    close if openclose && respond_to?(:close)
  end

  respond
end
hash_to_wf(point) click to toggle source

Wrapper around calling_class's #_hash_to_wf to facilitate verbosity/debugging. (The actual work is done in the calling class because it is not always on the same data type.)

@param point [Hash] a hash describing a point. See write() for

the format.

@return [String]

# File lib/wavefront-sdk/writers/core.rb, line 100
def hash_to_wf(point)
  wf_point = calling_class.hash_to_wf(point)
  logger.log(wf_point, :debug)
  wf_point
end
log_invalid_point(rawpoint, exception) click to toggle source
# File lib/wavefront-sdk/writers/core.rb, line 140
def log_invalid_point(rawpoint, exception)
  logger.log('Invalid point, skipping.', :warn)
  logger.log(exception.class, :warn)
  logger.log(format('Invalid point: %<rawpoint>s (%<message>s)',
                    rawpoint: rawpoint,
                    message: exception.to_s), :debug)
end
prefix_points(points, prefix = nil) click to toggle source

Prefix points with a given string @param points [Array,Hash] one or more points @param prefix [String] prefix to apply to every point @return [Array] of points

# File lib/wavefront-sdk/writers/core.rb, line 111
def prefix_points(points, prefix = nil)
  ret = [points].flatten
  return ret unless prefix

  ret.map { |pt| pt.tap { |p| p[:path] = prefix + '.' + p[:path] } }
end
respond() click to toggle source
# File lib/wavefront-sdk/writers/core.rb, line 71
def respond
  Wavefront::Response.new(
    { status: { result: summary.result, message: nil, code: nil },
      response: summary.to_h }.to_json, nil, opts
  )
end
screen_points(points) click to toggle source

Filter invalid points out of an array of points @param points [Array,Hash] one or more points @return [Array] of points

# File lib/wavefront-sdk/writers/core.rb, line 122
def screen_points(points)
  return points if opts[:novalidate]

  [points].flatten.select { |p| valid_point?(p) }
end
send_point(point) click to toggle source

Call the inheriting class's #_send_point method, and handle the summary

# File lib/wavefront-sdk/writers/core.rb, line 81
def send_point(point)
  _send_point(point)
  summary.sent += 1
  true
rescue StandardError => e
  summary.unsent += 1
  logger.log('Failed to send point.', :warn)
  logger.log(e.to_s, :debug)
  false
end
valid_point?(point) click to toggle source
# File lib/wavefront-sdk/writers/core.rb, line 128
def valid_point?(point)
  send(calling_class.validation, point)
rescue Wavefront::Exception::InvalidMetricName,
       Wavefront::Exception::InvalidMetricValue,
       Wavefront::Exception::InvalidTimestamp,
       Wavefront::Exception::InvalidSourceId,
       Wavefront::Exception::InvalidTag => e
  log_invalid_point(point, e)
  summary.rejected += 1
  false
end
write(points = [], openclose = manage_conn, prefix = nil) click to toggle source

Send multiple points to Wavefront.

@param points [Array] an array of points. @param openclose [Bool] if this is false, you must have

already opened a connection to the proxy. If it is true, a
connection will be opened for you, used, and closed.

@param prefix [String] prefix all metrics with this string. No

trailing dot is required.

@raise any unhandled point validation error is passed through @return [Wavefront::Response]

# File lib/wavefront-sdk/writers/core.rb, line 53
def write(points = [], openclose = manage_conn, prefix = nil)
  points = screen_points(points)
  points = prefix_points(points, prefix)
  do_write(points, openclose, prefix)
end

Private Instance Methods

write_loop(points) click to toggle source
# File lib/wavefront-sdk/writers/core.rb, line 159
def write_loop(points)
  points.each do |p|
    p[:ts] = p[:ts].to_i if p[:ts].is_a?(Time)
    send_point(hash_to_wf(p))
  end
end