Class: Salus::Metric

Inherits:
Object
  • Object
show all
Includes:
Lockable, Logging
Defined in:
lib/salus/metric.rb

Direct Known Subclasses

Absolute, Accumulator, Counter, Delta, Derive, Gauge, Text

Defined Under Namespace

Classes: Value

Constant Summary collapse

STORAGE_DEPTH =
2

Class Method Summary collapse

Instance Method Summary collapse

Methods included from Lockable

#broadcast, #signal, #synchronize, #wait, #wait_until

Methods included from Logging

#log

Constructor Details

#initialize(defaults = {}) ⇒ Metric

Returns a new instance of Metric.



40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
# File 'lib/salus/metric.rb', line 40

def initialize(defaults={})
  @values = Fifo.new(self.class::STORAGE_DEPTH)
  @opts   = defaults.clone
  @attributes = {}
  @last_calced_value = nil
  @last_calced_ts    = nil
  @needs_update      = true

  option :mute, TrueClass, FalseClass
  option :value, Numeric
  option :timestamp, Numeric
  option :ttl, Numeric

  @opts.each do |k, v|
    validate(k, v)
  end
end

Class Method Details

.descendantsObject



36
37
38
# File 'lib/salus/metric.rb', line 36

def self.descendants
  @@descendants || []
end

.inherited(subclass) ⇒ Object



31
32
33
34
# File 'lib/salus/metric.rb', line 31

def self.inherited(subclass)
  @@descendants ||= []
  @@descendants << subclass
end

Instance Method Details

#clearObject



147
148
149
150
151
152
153
154
# File 'lib/salus/metric.rb', line 147

def clear
  synchronize do
    @last_calced_value = nil
    @last_calced_ts    = nil
    @needs_update      = true
    @values.clear
  end
end

#expired?(ts = nil) ⇒ Boolean

Returns:

  • (Boolean)


107
108
109
110
111
112
113
114
115
# File 'lib/salus/metric.rb', line 107

def expired?(ts=nil)
  synchronize do
    if @values.empty?
      true
    else
      @values.last.expired?(ts)
    end
  end
end

#load(data) ⇒ Object



117
118
119
120
121
122
123
124
125
126
127
128
129
130
# File 'lib/salus/metric.rb', line 117

def load(data)
  return if data.nil?
  return if data.empty?
  return unless data.key?(:values)
  synchronize do
    if data.key?(:mute)
      @opts[:mute] = data[:mute]
    end
    data[:values].each do |v|
      @values << Value.new(v[:value], v[:timestamp], v[:ttl])
    end
    @needs_update  = true
  end
end

#mute?Boolean

Returns:

  • (Boolean)


58
59
60
# File 'lib/salus/metric.rb', line 58

def mute?
  synchronize { @opts[:mute] || false }
end

#push(opts = {}, &block) ⇒ Object



62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
# File 'lib/salus/metric.rb', line 62

def push(opts={}, &block)
  opts = {} unless opts.is_a?(Hash)

  synchronize do
    opts.each do |k, v|
      validate(k, v)
      @opts[k] = v unless [:value, :ttl, :timestamp].include?(k)
    end

    if block_given?
      v = begin
        yield
      rescue Exception => e
        log DEBUG, e
        nil
      end
      validate(:value, v)
      opts[:value] = v
    end

    @values << Value.new(opts[:value], opts[:timestamp] || Time.now.to_f, opts[:ttl] || @opts[:ttl])
    @needs_update = true
  end
end

#saveObject



132
133
134
# File 'lib/salus/metric.rb', line 132

def save
  to_h
end

#timestampObject



87
88
89
90
91
92
# File 'lib/salus/metric.rb', line 87

def timestamp
  synchronize do
    calc if @needs_update
    @last_calced_ts
  end
end

#to_hObject



136
137
138
139
140
141
142
143
144
145
# File 'lib/salus/metric.rb', line 136

def to_h
  return {} if @values.empty?
  synchronize do
    {
      type: self.class.name.split('::').last,
      mute: mute?,
      values: @values.map { |x| x.to_h }
    }
  end
end

#ttlObject



101
102
103
104
105
# File 'lib/salus/metric.rb', line 101

def ttl
  synchronize do
    @values.empty? ? nil : @values.last.ttl
  end
end

#valueObject



94
95
96
97
98
99
# File 'lib/salus/metric.rb', line 94

def value
  synchronize do
    calc if @needs_update
    @last_calced_value
  end
end