Module: Henitai::ProcessLiveness

Defined in:
lib/henitai/process_liveness.rb

Overview

Answers whether a process id is still running.

Extracted so the one subtle rule here lives in a single place: EPERM means the process exists but belongs to someone else, so it counts as alive. Only ESRCH proves it is gone. Getting that backwards would let OrphanWatchdog kill live children, and would make the reports-directory lock report a running owner as dead.

Constant Summary collapse

KILL =

Captured at load time, before any test double can replace Process.kill. A Method object keeps pointing at the original definition even after the singleton method is redefined, which is what makes this immune to stubbing.

This is not defensiveness for its own sake: a mutant child runs the host project's own suite, and a spec in that suite stubbing Process.kill to raise ESRCH made this answer "parent is dead" while the parent was very much alive. OrphanWatchdog then exited the child, which the scheduler recorded as CompileError. Observed on henitai's own dogfood run.

Process.method(:kill)

Class Method Summary collapse

Class Method Details

.alive?(pid, kill: KILL) ⇒ Boolean

Returns false only when the pid provably does not exist.

Parameters:

  • pid (Integer, nil)

    process id to probe

  • kill (#call) (defaults to: KILL)

    signalling primitive; injected only by specs, which cannot reach KILL by stubbing and must not be able to

Returns:

  • (Boolean)

    false only when the pid provably does not exist



28
29
30
31
32
33
34
35
36
37
38
39
# File 'lib/henitai/process_liveness.rb', line 28

def self.alive?(pid, kill: KILL)
  return false unless pid.is_a?(Integer)

  kill.call(0, pid)
  true
rescue Errno::ESRCH
  false
rescue StandardError
  # EPERM and anything unexpected: assume alive, the conservative answer
  # for every caller.
  true
end