Module: GoodJob::SdNotify

Defined in:
lib/good_job/sd_notify.rb

Overview

SdNotify is a pure-Ruby implementation of sd_notify(3). It can be used to notify systemd about state changes. Methods of this package are no-op on non-systemd systems (eg. Darwin).

The API maps closely to the original implementation of sd_notify(3), therefore be sure to check the official man pages prior to using SdNotify.

Defined Under Namespace

Classes: NotifyError

Constant Summary collapse

READY =
"READY=1"
RELOADING =
"RELOADING=1"
STOPPING =
"STOPPING=1"
STATUS =
"STATUS="
ERRNO =
"ERRNO="
MAINPID =
"MAINPID="
WATCHDOG =
"WATCHDOG=1"
FDSTORE =
"FDSTORE=1"

Class Method Summary collapse

Class Method Details

.errno(errno, unset_env = false) ⇒ Object

Parameters:

  • errno (Integer)


77
78
79
# File 'lib/good_job/sd_notify.rb', line 77

def self.errno(errno, unset_env=false)
  notify("#{ERRNO}#{errno}", unset_env)
end

.fdstore(unset_env = false) ⇒ Object



90
91
92
# File 'lib/good_job/sd_notify.rb', line 90

def self.fdstore(unset_env=false)
  notify(FDSTORE, unset_env)
end

.mainpid(pid, unset_env = false) ⇒ Object

Parameters:

  • pid (Integer)


82
83
84
# File 'lib/good_job/sd_notify.rb', line 82

def self.mainpid(pid, unset_env=false)
  notify("#{MAINPID}#{pid}", unset_env)
end

.notify(state, unset_env = false) ⇒ Fixnum?

Notify systemd with the provided state, via the notification socket, if any.

Generally this method will be used indirectly through the other methods of the library.

Parameters:

  • state (String)
  • unset_env (Boolean) (defaults to: false)

Returns:

  • (Fixnum, nil)

    the number of bytes written to the notification socket or nil if there was no socket to report to (eg. the program wasn’t started by systemd)

Raises:

  • (NotifyError)

    if there was an error communicating with the systemd socket

See Also:



138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
# File 'lib/good_job/sd_notify.rb', line 138

def self.notify(state, unset_env=false)
  sock = ENV["NOTIFY_SOCKET"]

  return nil if !sock

  ENV.delete("NOTIFY_SOCKET") if unset_env

  begin
    Addrinfo.unix(sock, :DGRAM).connect do |s|
      s.close_on_exec = true
      s.write(state)
    end
  rescue StandardError => e
    raise NotifyError, "#{e.class}: #{e.message}", e.backtrace
  end
end

.ready(unset_env = false) ⇒ Object



58
59
60
# File 'lib/good_job/sd_notify.rb', line 58

def self.ready(unset_env=false)
  notify(READY, unset_env)
end

.reloading(unset_env = false) ⇒ Object



62
63
64
# File 'lib/good_job/sd_notify.rb', line 62

def self.reloading(unset_env=false)
  notify(RELOADING, unset_env)
end

.status(status, unset_env = false) ⇒ Object

Parameters:

  • status (String)

    a custom status string that describes the current state of the service



72
73
74
# File 'lib/good_job/sd_notify.rb', line 72

def self.status(status, unset_env=false)
  notify("#{STATUS}#{status}", unset_env)
end

.stopping(unset_env = false) ⇒ Object



66
67
68
# File 'lib/good_job/sd_notify.rb', line 66

def self.stopping(unset_env=false)
  notify(STOPPING, unset_env)
end

.watchdog(unset_env = false) ⇒ Object



86
87
88
# File 'lib/good_job/sd_notify.rb', line 86

def self.watchdog(unset_env=false)
  notify(WATCHDOG, unset_env)
end

.watchdog?Boolean

Note:

Unlike sd_watchdog_enabled(3), this method does not mutate the environment.

If the $WATCHDOG_USEC environment variable is set, and the $WATCHDOG_PID variable is unset or set to the PID of the current process

Returns:

  • (Boolean)

    true if the service manager expects watchdog keep-alive notification messages to be sent from this process.



103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
# File 'lib/good_job/sd_notify.rb', line 103

def self.watchdog?
  wd_usec = ENV["WATCHDOG_USEC"]
  wd_pid = ENV["WATCHDOG_PID"]

  return false if !wd_usec

  begin
    wd_usec = Integer(wd_usec)
  rescue
    return false
  end

  return false if wd_usec <= 0
  return true if !wd_pid || wd_pid == $$.to_s

  false
end