Class: VCAP::Component

Inherits:
Object
  • Object
show all
Defined in:
lib/vcap/component.rb

Overview

Common component setup for discovery and monitoring

Constant Summary collapse

CONFIG_SUPPRESS =

We will suppress these from normal varz reporting by default.

Set.new([:mbus, :service_mbus, :keys, :database_environment, :mysql, :password])

Class Attribute Summary collapse

Class Method Summary collapse

Class Attribute Details

.healthzObject

Returns the value of attribute healthz.



53
54
55
# File 'lib/vcap/component.rb', line 53

def healthz
  @healthz
end

.varzObject (readonly)

Returns the value of attribute varz.



52
53
54
# File 'lib/vcap/component.rb', line 52

def varz
  @varz
end

Class Method Details

.clear_level(h) ⇒ Object



149
150
151
152
153
154
155
156
157
# File 'lib/vcap/component.rb', line 149

def clear_level(h)
  h.each do |k, v|
    if CONFIG_SUPPRESS.include?(k.to_sym)
      h.delete(k)
    else
      clear_level(h[k]) if v.instance_of? Hash
    end
  end
end

.register(opts) ⇒ Object



101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
# File 'lib/vcap/component.rb', line 101

def register(opts)
  uuid = VCAP.secure_uuid
  type = opts[:type]
  index = opts[:index]
  uuid = "#{index}-#{uuid}" if index
  host = opts[:host] || VCAP.local_ip
  port = opts[:port] || VCAP.grab_ephemeral_port
  nats = opts[:nats] || NATS
  auth = [opts[:user] || VCAP.secure_uuid, opts[:password] || VCAP.secure_uuid]
  logger = opts[:logger] || Logger.new(nil)

  # Discover message limited
  @discover = {
    :type => type,
    :index => index,
    :uuid => uuid,
    :host => "#{host}:#{port}",
    :credentials => auth,
    :start => Time.now
  }

  # Varz is customizable
  @varz = @discover.dup
  @varz[:num_cores] = VCAP.num_cores
  @varz[:config] = sanitize_config(opts[:config]) if opts[:config]

  @healthz = "ok\n".freeze

  # Next steps require EM
  raise "EventMachine reactor needs to be running" if !EventMachine.reactor_running?

  # Startup the http endpoint for /varz and /healthz
  start_http_server(host, port, auth, logger)

  # Listen for discovery requests
  nats.subscribe('vcap.component.discover') do |msg, reply|
    update_discover_uptime
    nats.publish(reply, @discover.to_json)
  end

  # Also announce ourselves on startup..
  nats.publish('vcap.component.announce', @discover.to_json)
end

.sanitize_config(config) ⇒ Object



159
160
161
162
163
164
165
166
167
168
169
# File 'lib/vcap/component.rb', line 159

def sanitize_config(config)
  # Can't Marshal/Deep Copy logger instances that services use
  if config[:logger]
    config = config.dup
    config.delete(:logger)
  end
  # Deep copy
  config = Marshal.load(Marshal.dump(config))
  clear_level(config)
  config
end

.start_http_server(host, port, auth, logger) ⇒ Object



81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
# File 'lib/vcap/component.rb', line 81

def start_http_server(host, port, auth, logger)
  http_server = Thin::Server.new(host, port, :signals => false) do
    Thin::Logging.silent = true
    use Rack::Auth::Basic do |username, password|
      [username, password] == auth
    end
    map '/healthz' do
      run Healthz.new(logger)
    end
    map '/varz' do
      run Varz.new(logger)
    end
  end
  http_server.start!
end

.update_discover_uptimeObject



145
146
147
# File 'lib/vcap/component.rb', line 145

def update_discover_uptime
  @discover[:uptime] = VCAP.uptime_string(Time.now - @discover[:start])
end

.updated_healthzObject



71
72
73
74
75
76
77
78
79
# File 'lib/vcap/component.rb', line 71

def updated_healthz
  @last_healthz_update ||= 0
  if Time.now.to_f - @last_healthz_update >= 1
    # ...
    @last_healthz_update = Time.now.to_f
  end

  healthz
end

.updated_varzObject



55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
# File 'lib/vcap/component.rb', line 55

def updated_varz
  @last_varz_update ||= 0
  if Time.now.to_f - @last_varz_update >= 1
    # Snapshot uptime
    @varz[:uptime] = VCAP.uptime_string(Time.now - @varz[:start])

    # Grab current cpu and memory usage.
    rss, pcpu = `ps -o rss=,pcpu= -p #{Process.pid}`.split
    @varz[:mem] = rss.to_i
    @varz[:cpu] = pcpu.to_f

    @last_varz_update = Time.now.to_f
  end
  varz
end

.uuidObject



97
98
99
# File 'lib/vcap/component.rb', line 97

def uuid
  @discover[:uuid]
end