eye 0.8.pre2 → 0.8.rc
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.rubocop.yml +141 -0
- data/.travis.yml +5 -3
- data/README.md +1 -2
- data/Rakefile +5 -5
- data/bin/leye +9 -4
- data/bin/loader_eye +14 -15
- data/examples/custom_check.eye +24 -0
- data/examples/custom_trigger.eye +3 -1
- data/examples/delayed_job.eye +3 -3
- data/examples/dependency.eye +10 -11
- data/examples/leye_example/Eyefile +10 -0
- data/examples/notify.eye +3 -4
- data/examples/plugin/main.eye +5 -5
- data/examples/plugin/plugin.rb +10 -2
- data/examples/process_thin.rb +8 -8
- data/examples/processes/em.rb +18 -12
- data/examples/processes/forking.rb +5 -5
- data/examples/processes/sample.rb +46 -44
- data/examples/puma.eye +9 -8
- data/examples/rbenv.eye +5 -5
- data/examples/sidekiq.eye +3 -3
- data/examples/stress_test.eye +4 -4
- data/examples/syslog.eye +1 -1
- data/examples/test.eye +1 -2
- data/examples/thin-farm.eye +7 -8
- data/examples/triggers.eye +13 -15
- data/examples/unicorn.eye +12 -13
- data/eye.gemspec +14 -12
- data/lib/eye.rb +2 -3
- data/lib/eye/application.rb +5 -6
- data/lib/eye/checker.rb +36 -19
- data/lib/eye/checker/children_count.rb +1 -1
- data/lib/eye/checker/file_ctime.rb +1 -1
- data/lib/eye/checker/http.rb +13 -15
- data/lib/eye/checker/nop.rb +1 -0
- data/lib/eye/checker/socket.rb +60 -63
- data/lib/eye/checker/ssl_socket.rb +5 -5
- data/lib/eye/child_process.rb +6 -4
- data/lib/eye/cli.rb +50 -41
- data/lib/eye/cli/commands.rb +4 -5
- data/lib/eye/cli/render.rb +61 -41
- data/lib/eye/cli/server.rb +19 -16
- data/lib/eye/client.rb +1 -0
- data/lib/eye/config.rb +19 -19
- data/lib/eye/controller.rb +2 -3
- data/lib/eye/controller/commands.rb +1 -1
- data/lib/eye/controller/helpers.rb +2 -2
- data/lib/eye/controller/load.rb +18 -12
- data/lib/eye/controller/options.rb +1 -5
- data/lib/eye/controller/send_command.rb +21 -23
- data/lib/eye/controller/status.rb +17 -15
- data/lib/eye/dsl.rb +3 -0
- data/lib/eye/dsl/application_opts.rb +4 -3
- data/lib/eye/dsl/chain.rb +2 -2
- data/lib/eye/dsl/child_process_opts.rb +3 -3
- data/lib/eye/dsl/config_opts.rb +7 -7
- data/lib/eye/dsl/group_opts.rb +3 -3
- data/lib/eye/dsl/helpers.rb +1 -1
- data/lib/eye/dsl/main.rb +4 -3
- data/lib/eye/dsl/opts.rb +31 -28
- data/lib/eye/dsl/process_opts.rb +13 -7
- data/lib/eye/dsl/pure_opts.rb +13 -9
- data/lib/eye/dsl/validation.rb +48 -35
- data/lib/eye/group.rb +20 -6
- data/lib/eye/group/chain.rb +6 -6
- data/lib/eye/loader.rb +1 -1
- data/lib/eye/local.rb +9 -4
- data/lib/eye/logger.rb +11 -4
- data/lib/eye/notify.rb +10 -6
- data/lib/eye/notify/jabber.rb +1 -1
- data/lib/eye/notify/mail.rb +2 -2
- data/lib/eye/notify/slack.rb +4 -3
- data/lib/eye/process.rb +2 -0
- data/lib/eye/process/children.rb +4 -4
- data/lib/eye/process/commands.rb +28 -31
- data/lib/eye/process/config.rb +21 -19
- data/lib/eye/process/data.rb +11 -9
- data/lib/eye/process/monitor.rb +30 -29
- data/lib/eye/process/notify.rb +10 -10
- data/lib/eye/process/scheduler.rb +36 -31
- data/lib/eye/process/states.rb +5 -4
- data/lib/eye/process/states_history.rb +9 -3
- data/lib/eye/process/system.rb +5 -4
- data/lib/eye/process/trigger.rb +1 -5
- data/lib/eye/process/watchers.rb +6 -9
- data/lib/eye/reason.rb +4 -1
- data/lib/eye/server.rb +2 -1
- data/lib/eye/system.rb +16 -13
- data/lib/eye/system_resources.rb +13 -8
- data/lib/eye/trigger.rb +18 -16
- data/lib/eye/trigger/check_dependency.rb +7 -4
- data/lib/eye/trigger/flapping.rb +24 -7
- data/lib/eye/trigger/starting_guard.rb +7 -6
- data/lib/eye/trigger/stop_children.rb +2 -2
- data/lib/eye/trigger/transition.rb +1 -1
- data/lib/eye/trigger/wait_dependency.rb +3 -2
- data/lib/eye/utils.rb +4 -3
- data/lib/eye/utils/alive_array.rb +9 -4
- data/lib/eye/utils/celluloid_chain.rb +12 -10
- data/lib/eye/utils/mini_active_support.rb +16 -16
- data/lib/eye/utils/pmap.rb +2 -0
- data/lib/eye/utils/tail.rb +2 -2
- metadata +34 -4
- data/lib/eye/utils/leak_19.rb +0 -10
data/lib/eye/notify.rb
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
require 'celluloid'
|
|
2
2
|
|
|
3
3
|
class Eye::Notify
|
|
4
|
+
|
|
4
5
|
include Celluloid
|
|
5
6
|
include Eye::Dsl::Validation
|
|
6
7
|
|
|
@@ -8,7 +9,7 @@ class Eye::Notify
|
|
|
8
9
|
autoload :Jabber, 'eye/notify/jabber'
|
|
9
10
|
autoload :Slack, 'eye/notify/slack'
|
|
10
11
|
|
|
11
|
-
TYPES = {:
|
|
12
|
+
TYPES = { mail: 'Mail', jabber: 'Jabber', slack: 'Slack' }
|
|
12
13
|
|
|
13
14
|
def self.get_class(type)
|
|
14
15
|
klass = eval("Eye::Notify::#{TYPES[type]}") rescue nil
|
|
@@ -35,19 +36,19 @@ class Eye::Notify
|
|
|
35
36
|
|
|
36
37
|
create_proc = lambda do |nh|
|
|
37
38
|
type = nh[:type]
|
|
38
|
-
config = (settings[type] || {}).merge(nh[:opts] || {}).merge(:
|
|
39
|
+
config = (settings[type] || {}).merge(nh[:opts] || {}).merge(contact: nh[:contact])
|
|
39
40
|
klass = get_class(type)
|
|
40
41
|
notify = klass.new(config, message_h)
|
|
41
42
|
notify.async_notify if notify
|
|
42
43
|
end
|
|
43
44
|
|
|
44
45
|
if needed_hash.is_a?(Array)
|
|
45
|
-
needed_hash.each{|nh| create_proc[nh] }
|
|
46
|
+
needed_hash.each { |nh| create_proc[nh] }
|
|
46
47
|
else
|
|
47
48
|
create_proc[needed_hash]
|
|
48
49
|
end
|
|
49
50
|
|
|
50
|
-
rescue
|
|
51
|
+
rescue Object => ex
|
|
51
52
|
log_ex(ex)
|
|
52
53
|
end
|
|
53
54
|
|
|
@@ -66,7 +67,7 @@ class Eye::Notify
|
|
|
66
67
|
|
|
67
68
|
def async_notify
|
|
68
69
|
async.notify
|
|
69
|
-
after(TIMEOUT){ terminate }
|
|
70
|
+
after(TIMEOUT) { terminate }
|
|
70
71
|
end
|
|
71
72
|
|
|
72
73
|
def notify
|
|
@@ -102,15 +103,18 @@ class Eye::Notify
|
|
|
102
103
|
end
|
|
103
104
|
|
|
104
105
|
class Custom < Eye::Notify
|
|
106
|
+
|
|
105
107
|
def self.inherited(base)
|
|
106
108
|
super
|
|
107
109
|
register(base)
|
|
108
110
|
end
|
|
111
|
+
|
|
109
112
|
end
|
|
110
113
|
|
|
111
|
-
%w
|
|
114
|
+
%w[at host message name full_name pid level].each do |name|
|
|
112
115
|
define_method("msg_#{name}") do
|
|
113
116
|
@message_h[name.to_sym]
|
|
114
117
|
end
|
|
115
118
|
end
|
|
119
|
+
|
|
116
120
|
end
|
data/lib/eye/notify/jabber.rb
CHANGED
data/lib/eye/notify/mail.rb
CHANGED
|
@@ -41,8 +41,8 @@ class Eye::Notify::Mail < Eye::Notify
|
|
|
41
41
|
h << "To: <#{contact}>"
|
|
42
42
|
h << "Subject: #{message_subject}"
|
|
43
43
|
h << "Date: #{msg_at.httpdate}"
|
|
44
|
-
h << "Message-Id: <#{rand(
|
|
44
|
+
h << "Message-Id: <#{rand(1_000_000_000).to_s(36)}.#{$$}.#{contact}>"
|
|
45
45
|
"#{h * "\n"}\n#{message_body}"
|
|
46
46
|
end
|
|
47
47
|
|
|
48
|
-
end
|
|
48
|
+
end
|
data/lib/eye/notify/slack.rb
CHANGED
|
@@ -8,8 +8,8 @@ class Eye::Notify::Slack < Eye::Notify
|
|
|
8
8
|
# end
|
|
9
9
|
|
|
10
10
|
param :webhook_url, String, true
|
|
11
|
-
param :channel, String, nil,
|
|
12
|
-
param :username, String, nil,
|
|
11
|
+
param :channel, String, nil, '#default'
|
|
12
|
+
param :username, String, nil, 'eye'
|
|
13
13
|
|
|
14
14
|
param :icon, String
|
|
15
15
|
|
|
@@ -35,4 +35,5 @@ class Eye::Notify::Slack < Eye::Notify
|
|
|
35
35
|
payload << "> #{msg_message}"
|
|
36
36
|
payload
|
|
37
37
|
end
|
|
38
|
-
|
|
38
|
+
|
|
39
|
+
end
|
data/lib/eye/process.rb
CHANGED
data/lib/eye/process/children.rb
CHANGED
|
@@ -31,17 +31,17 @@ module Eye::Process::Children
|
|
|
31
31
|
|
|
32
32
|
if new_children.present?
|
|
33
33
|
new_children.each do |child_pid|
|
|
34
|
-
cfg = self[:monitor_children].try :update, :
|
|
34
|
+
cfg = self[:monitor_children].try :update, notify: self[:notify]
|
|
35
35
|
self.children[child_pid] = Eye::ChildProcess.new(child_pid, cfg, logger.prefix, current_actor)
|
|
36
36
|
end
|
|
37
37
|
end
|
|
38
38
|
|
|
39
39
|
if removed_children.present?
|
|
40
|
-
removed_children.each{|child_pid| remove_child(child_pid) }
|
|
40
|
+
removed_children.each { |child_pid| remove_child(child_pid) }
|
|
41
41
|
end
|
|
42
42
|
|
|
43
|
-
h = {:
|
|
44
|
-
debug { "children info: #{
|
|
43
|
+
h = { new: new_children.size, removed: removed_children.size, exists: exist_children.size }
|
|
44
|
+
debug { "children info: #{h.inspect}" }
|
|
45
45
|
|
|
46
46
|
@updating_children = false
|
|
47
47
|
h
|
data/lib/eye/process/commands.rb
CHANGED
|
@@ -99,10 +99,9 @@ private
|
|
|
99
99
|
if self[:stop_command]
|
|
100
100
|
cmd = prepare_command(self[:stop_command])
|
|
101
101
|
info "executing: `#{cmd}` with stop_timeout: #{self[:stop_timeout].to_f}s and stop_grace: #{self[:stop_grace].to_f}s"
|
|
102
|
-
res = execute(cmd, config.merge(:
|
|
102
|
+
res = execute(cmd, config.merge(timeout: self[:stop_timeout]))
|
|
103
103
|
|
|
104
104
|
if res[:error]
|
|
105
|
-
|
|
106
105
|
if res[:error].class == Timeout::Error
|
|
107
106
|
error "stop_command failed with #{res[:error].inspect}; try tuning the stop_timeout value"
|
|
108
107
|
else
|
|
@@ -115,7 +114,6 @@ private
|
|
|
115
114
|
elsif self[:stop_signals]
|
|
116
115
|
info "executing stop_signals #{self[:stop_signals].inspect}"
|
|
117
116
|
stop_signals = self[:stop_signals].clone
|
|
118
|
-
|
|
119
117
|
signal = stop_signals.shift
|
|
120
118
|
send_signal(signal)
|
|
121
119
|
|
|
@@ -123,7 +121,7 @@ private
|
|
|
123
121
|
delay = stop_signals.shift
|
|
124
122
|
signal = stop_signals.shift
|
|
125
123
|
|
|
126
|
-
if wait_for_condition(delay.to_f, 0.3){ !process_really_running? }
|
|
124
|
+
if wait_for_condition(delay.to_f, 0.3) { !process_really_running? }
|
|
127
125
|
info 'has terminated'
|
|
128
126
|
break
|
|
129
127
|
end
|
|
@@ -136,7 +134,6 @@ private
|
|
|
136
134
|
else # default command
|
|
137
135
|
debug { "executing: `kill -TERM #{self.pid}` with stop_grace: #{self[:stop_grace].to_f}s" }
|
|
138
136
|
send_signal(:TERM)
|
|
139
|
-
|
|
140
137
|
sleep_grace(:stop_grace)
|
|
141
138
|
|
|
142
139
|
# if process not die here, by default we force kill it
|
|
@@ -157,7 +154,7 @@ private
|
|
|
157
154
|
cmd = prepare_command(self[:restart_command])
|
|
158
155
|
info "executing: `#{cmd}` with restart_timeout: #{self[:restart_timeout].to_f}s and restart_grace: #{self[:restart_grace].to_f}s"
|
|
159
156
|
|
|
160
|
-
res = execute(cmd, config.merge(:
|
|
157
|
+
res = execute(cmd, config.merge(timeout: self[:restart_timeout]))
|
|
161
158
|
|
|
162
159
|
if res[:error]
|
|
163
160
|
|
|
@@ -172,11 +169,9 @@ private
|
|
|
172
169
|
end
|
|
173
170
|
|
|
174
171
|
def daemonize_process
|
|
175
|
-
time_before = Time.now
|
|
176
172
|
res = daemonize(self[:start_command], config)
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
info "daemonizing: `#{self[:start_command]}` with start_grace: #{self[:start_grace].to_f}s, env: '#{environment_string}', <#{res[:pid]}> (in #{self[:working_dir]})"
|
|
173
|
+
info "daemonizing: `#{self[:start_command]}` with start_grace: #{self[:start_grace].to_f}s, env: '#{environment_string}'}" \
|
|
174
|
+
", <#{res[:pid]}> (in #{self[:working_dir]})"
|
|
180
175
|
|
|
181
176
|
if res[:error]
|
|
182
177
|
|
|
@@ -186,21 +181,21 @@ private
|
|
|
186
181
|
error "daemonize failed with #{res[:error].inspect}"
|
|
187
182
|
end
|
|
188
183
|
|
|
189
|
-
return {:
|
|
184
|
+
return { error: res[:error].inspect }
|
|
190
185
|
end
|
|
191
186
|
|
|
192
187
|
self.pid = res[:pid]
|
|
193
188
|
|
|
194
189
|
unless self.pid
|
|
195
190
|
error 'no pid was returned'
|
|
196
|
-
return {:
|
|
191
|
+
return { error: :empty_pid }
|
|
197
192
|
end
|
|
198
193
|
|
|
199
194
|
sleep_grace(:start_grace)
|
|
200
195
|
|
|
201
196
|
unless process_really_running?
|
|
202
197
|
error "process <#{self.pid}> not found, it may have crashed (#{check_logs_str})"
|
|
203
|
-
return {:
|
|
198
|
+
return { error: :not_really_running }
|
|
204
199
|
end
|
|
205
200
|
|
|
206
201
|
# if we using leaf child stratedy, pid should be used as last child process
|
|
@@ -215,43 +210,45 @@ private
|
|
|
215
210
|
end
|
|
216
211
|
|
|
217
212
|
if control_pid? && !failsafe_save_pid
|
|
218
|
-
return {:
|
|
213
|
+
return { error: :cant_write_pid }
|
|
219
214
|
end
|
|
220
215
|
|
|
221
216
|
res
|
|
222
217
|
end
|
|
223
218
|
|
|
224
219
|
def execute_process
|
|
225
|
-
info "executing: `#{self[:start_command]}` with start_timeout: #{config[:start_timeout].to_f}s
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
res = execute(self[:start_command], config.merge(:timeout => config[:start_timeout]))
|
|
229
|
-
start_time = Time.now - time_before
|
|
220
|
+
info "executing: `#{self[:start_command]}` with start_timeout: #{config[:start_timeout].to_f}s" \
|
|
221
|
+
", start_grace: #{self[:start_grace].to_f}s, env: '#{environment_string}' (in #{self[:working_dir]})"
|
|
222
|
+
res = execute(self[:start_command], config.merge(timeout: config[:start_timeout]))
|
|
230
223
|
|
|
231
224
|
if res[:error]
|
|
232
225
|
|
|
233
226
|
if res[:error].message == 'Permission denied - open'
|
|
234
227
|
error "execution failed with #{res[:error].inspect}; ensure that #{[self[:stdout], self[:stderr]]} are writable"
|
|
235
228
|
elsif res[:error].class == Timeout::Error
|
|
236
|
-
error "execution failed with #{res[:error].inspect}; try increasing the start_timeout value
|
|
229
|
+
error "execution failed with #{res[:error].inspect}; try increasing the start_timeout value" \
|
|
230
|
+
"(the current value of #{self[:start_timeout]}s seems too short)"
|
|
237
231
|
else
|
|
238
232
|
error "execution failed with #{res[:error].inspect}"
|
|
239
233
|
end
|
|
240
234
|
|
|
241
|
-
return {:
|
|
235
|
+
return { error: res[:error].inspect }
|
|
242
236
|
end
|
|
243
237
|
|
|
244
238
|
sleep_grace(:start_grace)
|
|
245
239
|
|
|
246
240
|
case load_external_pid_file
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
241
|
+
when :ok
|
|
242
|
+
res.merge(pid: self.pid)
|
|
243
|
+
when :no_pid_file
|
|
244
|
+
error "exit status #{res[:exitstatus]}, pid_file (#{self[:pid_file_ex]}) did not appear within the " \
|
|
245
|
+
"start_grace period (#{self[:start_grace].to_f}s); check your start_command, or tune the start_grace " \
|
|
246
|
+
'value (eye expect process to create pid_file in self-daemonization mode)'
|
|
247
|
+
{ error: :pid_not_found }
|
|
248
|
+
when :not_running
|
|
249
|
+
error "exit status #{res[:exitstatus]}, process <#{@last_loaded_pid}> (from #{self[:pid_file_ex]}) was not found; " \
|
|
250
|
+
"ensure that the pid_file is being updated correctly (#{check_logs_str})"
|
|
251
|
+
{ error: :not_really_running }
|
|
255
252
|
end
|
|
256
253
|
end
|
|
257
254
|
|
|
@@ -285,7 +282,7 @@ private
|
|
|
285
282
|
# cmd is string, or array of signals
|
|
286
283
|
if cmd.is_a?(String)
|
|
287
284
|
cmd = prepare_command(cmd)
|
|
288
|
-
res = execute(cmd, config.merge(:
|
|
285
|
+
res = execute(cmd, config.merge(timeout: 120))
|
|
289
286
|
error "cmd #{cmd} error #{res.inspect}" if res[:error]
|
|
290
287
|
elsif cmd.is_a?(Array)
|
|
291
288
|
signals = cmd.clone
|
|
@@ -295,7 +292,7 @@ private
|
|
|
295
292
|
while signals.present?
|
|
296
293
|
delay = signals.shift
|
|
297
294
|
signal = signals.shift
|
|
298
|
-
if wait_for_condition(delay.to_f, 0.3){ !process_really_running? }
|
|
295
|
+
if wait_for_condition(delay.to_f, 0.3) { !process_really_running? }
|
|
299
296
|
info 'has terminated'
|
|
300
297
|
break
|
|
301
298
|
end
|
data/lib/eye/process/config.rb
CHANGED
|
@@ -1,29 +1,29 @@
|
|
|
1
1
|
module Eye::Process::Config
|
|
2
2
|
|
|
3
3
|
DEFAULTS = {
|
|
4
|
-
:
|
|
5
|
-
:
|
|
4
|
+
keep_alive: true, # restart when crashed
|
|
5
|
+
check_alive_period: 5.seconds,
|
|
6
6
|
|
|
7
|
-
:
|
|
8
|
-
:
|
|
9
|
-
:
|
|
7
|
+
check_identity: true,
|
|
8
|
+
check_identity_period: 60.seconds,
|
|
9
|
+
check_identity_grace: 60.seconds,
|
|
10
10
|
|
|
11
|
-
:
|
|
12
|
-
:
|
|
13
|
-
:
|
|
11
|
+
start_timeout: 15.seconds,
|
|
12
|
+
stop_timeout: 10.seconds,
|
|
13
|
+
restart_timeout: 10.seconds,
|
|
14
14
|
|
|
15
|
-
:
|
|
16
|
-
:
|
|
17
|
-
:
|
|
15
|
+
start_grace: 2.5.seconds,
|
|
16
|
+
stop_grace: 0.5.seconds,
|
|
17
|
+
restart_grace: 1.second,
|
|
18
18
|
|
|
19
|
-
:
|
|
20
|
-
:
|
|
19
|
+
daemonize: false,
|
|
20
|
+
auto_start: true, # auto start on monitor action
|
|
21
21
|
|
|
22
|
-
:
|
|
23
|
-
:
|
|
22
|
+
children_update_period: 30.seconds,
|
|
23
|
+
clear_pid: true, # by default clear pid on stop
|
|
24
24
|
|
|
25
|
-
:
|
|
26
|
-
:
|
|
25
|
+
auto_update_pidfile_grace: 30.seconds,
|
|
26
|
+
revert_fuckup_pidfile_grace: 120.seconds
|
|
27
27
|
}
|
|
28
28
|
|
|
29
29
|
def prepare_config(new_config)
|
|
@@ -31,12 +31,14 @@ module Eye::Process::Config
|
|
|
31
31
|
h[:pid_file_ex] = Eye::System.normalized_file(h[:pid_file], h[:working_dir]) if h[:pid_file]
|
|
32
32
|
h[:checks] = {} if h[:checks].blank?
|
|
33
33
|
h[:triggers] = {} if h[:triggers].blank?
|
|
34
|
-
|
|
34
|
+
if upd = h.try(:[], :monitor_children).try(:[], :children_update_period)
|
|
35
|
+
h[:children_update_period] = upd
|
|
36
|
+
end
|
|
35
37
|
|
|
36
38
|
# check speedy flapping by default
|
|
37
39
|
if h[:triggers].blank? || !h[:triggers][:flapping]
|
|
38
40
|
h[:triggers] ||= {}
|
|
39
|
-
h[:triggers][:flapping] = {:
|
|
41
|
+
h[:triggers][:flapping] = { type: :flapping, times: 10, within: 10.seconds }
|
|
40
42
|
end
|
|
41
43
|
|
|
42
44
|
h[:stdout] = Eye::System.normalized_file(h[:stdout], h[:working_dir]) if h[:stdout]
|
data/lib/eye/process/data.rb
CHANGED
|
@@ -20,30 +20,32 @@ module Eye::Process::Data
|
|
|
20
20
|
@full_name ||= [app_name, group_name, self[:name]].compact.join(':')
|
|
21
21
|
end
|
|
22
22
|
|
|
23
|
-
def status_data(
|
|
24
|
-
p_st = self_status_data(
|
|
23
|
+
def status_data(opts = {})
|
|
24
|
+
p_st = self_status_data(opts)
|
|
25
25
|
|
|
26
26
|
if children.present?
|
|
27
|
-
p_st.merge(:
|
|
27
|
+
p_st.merge(subtree: Eye::Utils::AliveArray.new(children.values).map { |c| c.status_data(opts) })
|
|
28
28
|
elsif self[:monitor_children] && self.up?
|
|
29
|
-
p_st.merge(:
|
|
29
|
+
p_st.merge(subtree: [{ name: '=loading children=' }])
|
|
30
30
|
else
|
|
31
31
|
# common state
|
|
32
32
|
p_st
|
|
33
33
|
end
|
|
34
34
|
end
|
|
35
35
|
|
|
36
|
-
def self_status_data(
|
|
37
|
-
h = { name: name,
|
|
36
|
+
def self_status_data(opts)
|
|
37
|
+
h = { name: name,
|
|
38
|
+
state: state,
|
|
38
39
|
type: (self.class == Eye::ChildProcess ? :child_process : :process),
|
|
39
40
|
resources: Eye::SystemResources.resources(pid) }
|
|
40
41
|
|
|
41
42
|
if @states_history
|
|
42
|
-
h
|
|
43
|
-
|
|
43
|
+
h[:state_changed_at] = @states_history.last_state_changed_at.to_i
|
|
44
|
+
h[:state_reason] = @states_history.last_reason.to_s
|
|
44
45
|
end
|
|
45
46
|
|
|
46
|
-
h[:debug] = debug_data if debug
|
|
47
|
+
h[:debug] = debug_data if opts[:debug]
|
|
48
|
+
h[:procline] = Eye::SystemResources.args(self.pid) if opts[:procline]
|
|
47
49
|
h[:current_command] = current_scheduled_command if current_scheduled_command
|
|
48
50
|
|
|
49
51
|
h
|
data/lib/eye/process/monitor.rb
CHANGED
|
@@ -7,7 +7,7 @@ private
|
|
|
7
7
|
|
|
8
8
|
if !newpid
|
|
9
9
|
self.pid = nil
|
|
10
|
-
info
|
|
10
|
+
info 'load_external_pid_file: pid_file not found'
|
|
11
11
|
:no_pid_file
|
|
12
12
|
elsif process_pid_running?(newpid)
|
|
13
13
|
self.pid = newpid
|
|
@@ -16,7 +16,8 @@ private
|
|
|
16
16
|
warn "load_external_pid_file: process <#{self.pid}> from pid_file failed check_identity"
|
|
17
17
|
:bad_identity
|
|
18
18
|
else
|
|
19
|
-
|
|
19
|
+
args = Eye::SystemResources.args(self.pid)
|
|
20
|
+
info "load_external_pid_file: process <#{self.pid}> from pid_file found and running (identity: #{res}) (#{args})"
|
|
20
21
|
:ok
|
|
21
22
|
end
|
|
22
23
|
else
|
|
@@ -28,18 +29,17 @@ private
|
|
|
28
29
|
end
|
|
29
30
|
|
|
30
31
|
def check_alive
|
|
31
|
-
|
|
32
|
+
return unless up?
|
|
32
33
|
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
34
|
+
# check that process runned
|
|
35
|
+
if process_really_running?
|
|
36
|
+
check_pid_file
|
|
37
|
+
else
|
|
38
|
+
warn "check_alive: process <#{self.pid}> not found"
|
|
39
|
+
notify :info, 'crashed!'
|
|
40
|
+
clear_pid_file(true) if control_pid?
|
|
38
41
|
|
|
39
|
-
|
|
40
|
-
else
|
|
41
|
-
check_pid_file
|
|
42
|
-
end
|
|
42
|
+
switch :crashed, Eye::Reason.new(:crashed)
|
|
43
43
|
end
|
|
44
44
|
end
|
|
45
45
|
|
|
@@ -51,25 +51,25 @@ private
|
|
|
51
51
|
if control_pid?
|
|
52
52
|
msg += ", reverting to <#{self.pid}> (the pid_file is controlled by eye)"
|
|
53
53
|
unless failsafe_save_pid
|
|
54
|
-
msg +=
|
|
54
|
+
msg += ', pid_file write failed! O_o'
|
|
55
55
|
end
|
|
56
56
|
else
|
|
57
57
|
changed_ago_s = Time.now - pid_file_ctime
|
|
58
58
|
|
|
59
|
-
if ppid
|
|
59
|
+
if !ppid
|
|
60
60
|
msg += ", reverting to <#{self.pid}> (the pid_file is empty)"
|
|
61
61
|
unless failsafe_save_pid
|
|
62
|
-
msg +=
|
|
62
|
+
msg += ', pid_file write failed! O_o'
|
|
63
63
|
end
|
|
64
64
|
|
|
65
65
|
elsif (changed_ago_s > self[:auto_update_pidfile_grace]) && process_pid_running?(ppid) && (compare_identity(ppid) != :fail)
|
|
66
66
|
msg += ", trusting this change, and now monitor <#{ppid}>"
|
|
67
67
|
self.pid = ppid
|
|
68
68
|
|
|
69
|
-
elsif
|
|
69
|
+
elsif changed_ago_s > self[:revert_fuckup_pidfile_grace]
|
|
70
70
|
msg += " over #{self[:revert_fuckup_pidfile_grace]}s ago, reverting to <#{self.pid}>, because <#{ppid}> not alive"
|
|
71
71
|
unless failsafe_save_pid
|
|
72
|
-
msg +=
|
|
72
|
+
msg += ', pid_file write failed! O_o'
|
|
73
73
|
end
|
|
74
74
|
|
|
75
75
|
else
|
|
@@ -92,21 +92,22 @@ private
|
|
|
92
92
|
end
|
|
93
93
|
|
|
94
94
|
def check_crash
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
95
|
+
unless down?
|
|
96
|
+
debug { 'check crashed: skipped, process is not in down' }
|
|
97
|
+
return
|
|
98
|
+
end
|
|
99
|
+
|
|
100
|
+
if self[:keep_alive]
|
|
101
|
+
warn 'check crashed: process is down'
|
|
102
|
+
|
|
103
|
+
if self[:restore_in]
|
|
104
|
+
schedule_in self[:restore_in].to_f, :restore, Eye::Reason.new(:crashed)
|
|
104
105
|
else
|
|
105
|
-
|
|
106
|
-
schedule :unmonitor, Eye::Reason.new(:crashed)
|
|
106
|
+
schedule :restore, Eye::Reason.new(:crashed)
|
|
107
107
|
end
|
|
108
108
|
else
|
|
109
|
-
|
|
109
|
+
warn 'check crashed: process without keep_alive'
|
|
110
|
+
schedule :unmonitor, Eye::Reason.new(:crashed)
|
|
110
111
|
end
|
|
111
112
|
end
|
|
112
113
|
|