[Supervisor-checkins] r832 - in superlance/trunk: . superlance

Tres Seaver tseaver at palladion.com
Wed Feb 11 13:30:42 EST 2009


Author: Tres Seaver <tseaver at palladion.com>
Date: Wed Feb 11 13:30:41 2009
New Revision: 832

Log:
Added ``eager`` and ``not-eager`` options to httpok.

o If ``not-eager`` is set, and no process being monitored is in the
  RUNNING state, skip the URL check / mail message.


Modified:
   superlance/trunk/CHANGES.txt
   superlance/trunk/superlance/httpok.py
   superlance/trunk/superlance/tests.py

Modified: superlance/trunk/CHANGES.txt
==============================================================================
--- superlance/trunk/CHANGES.txt	(original)
+++ superlance/trunk/CHANGES.txt	Wed Feb 11 13:30:41 2009
@@ -1,11 +1,24 @@
-0.3
+superlance Changelog
+====================
 
-  Add ``gcore`` and ``coredir`` options to httpok.
+0.4 (unreleased)
+----------------
 
-0.2
+- Added ``eager`` and ``not-eager`` options to httpok.  If ``not-eager``
+  is set, and no process being monitored is in the RUNNING state, skip
+  the URL check / mail message.
 
-  Add crashmail script.
+0.3 (2008-12-10)
+----------------
 
-0.1
+- Added ``gcore`` and ``coredir`` options to httpok.
 
-  Initial release
+0.2 (2008-11-21)
+----------------
+
+- Added crashmail script.
+
+0.1 (2008-09-18)
+----------------
+
+- Initial release

Modified: superlance/trunk/superlance/httpok.py
==============================================================================
--- superlance/trunk/superlance/httpok.py	(original)
+++ superlance/trunk/superlance/httpok.py	Wed Feb 11 13:30:41 2009
@@ -59,7 +59,7 @@
       URL.  If this status code is not the status code provided by the
       response, httpok will attempt to restart processes in the
       RUNNING state specified by -p or -a.  This defaults to the
-      string"200".
+      string, "200".
 
 -b -- specify a string which should be present in the body resulting
       from the GET request.  If this string is not present in the
@@ -76,6 +76,12 @@
       address when httpok attempts to restart processes.  If no email
       address is specified, email will not be sent.
 
+-e -- "eager":  check URL / emit mail even if no process we are monitoring
+      is in the RUNNING state.  Enabled by default.
+
+-E -- not "eager":  do not check URL / emit mail if no process we are
+      monitoring is in the RUNNING state.
+
 URL -- The URL to which to issue a GET request.
 
 The -p option may be specified more than once, allowing for
@@ -107,7 +113,7 @@
 class HTTPOk:
     connclass = None
     def __init__(self, rpc, programs, any, url, timeout, status, inbody,
-                 email, sendmail, coredir, gcore):
+                 email, sendmail, coredir, gcore, eager):
         self.rpc = rpc
         self.programs = programs
         self.any = any
@@ -119,10 +125,16 @@
         self.sendmail = sendmail
         self.coredir = coredir
         self.gcore = gcore
+        self.eager = eager
         self.stdin = sys.stdin
         self.stdout = sys.stdout
         self.stderr = sys.stderr
 
+    def listProcesses(self, state=None):
+        return [x for x in self.rpc.supervisor.getAllProcessInfo()
+                   if x['name'] in self.programs and
+                      (state is None or x['state'] == state)]
+
     def runforever(self, test=False):
         parsed = urlparse.urlsplit(self.url)
         scheme = parsed[0].lower()
@@ -160,6 +172,13 @@
 
             act = False
 
+            if not self.eager:
+                specs = self.listProcesses(ProcessStates.RUNNING)
+                if len(specs) == 0:
+                    if test:
+                        break
+                    continue
+
             try:
                 conn.request('GET', path)
                 res = conn.getresponse()
@@ -274,7 +293,7 @@
 
 def main(argv=sys.argv):
     import getopt
-    short_args="hp:at:c:b:s:m:g:d:"
+    short_args="hp:at:c:b:s:m:g:d:eE"
     long_args=[
         "help",
         "program=",
@@ -286,6 +305,8 @@
         "email=",
         "gcore=",
         "coredir=",
+        "eager",
+        "not-eager",
         ]
     arguments = argv[1:]
     try:
@@ -303,6 +324,7 @@
     sendmail = '/usr/sbin/sendmail -t -i'
     gcore = '/usr/bin/gcore -o'
     coredir = None
+    eager = True
     email = None
     timeout = 10
     status = '200'
@@ -340,6 +362,12 @@
         if option in ('-d', '--coredir'):
             coredir = value
 
+        if option in ('-e', '--eager'):
+            eager = True
+
+        if option in ('-E', '--not-eager'):
+            eager = False
+
     url = arguments[-1]
 
     try:
@@ -353,7 +381,7 @@
         return
 
     prog = HTTPOk(rpc, programs, any, url, timeout, status, inbody, email,
-                  sendmail, coredir, gcore)
+                  sendmail, coredir, gcore, eager)
     prog.runforever()
 
 if __name__ == '__main__':

Modified: superlance/trunk/superlance/tests.py
==============================================================================
--- superlance/trunk/superlance/tests.py	(original)
+++ superlance/trunk/superlance/tests.py	Wed Feb 11 13:30:41 2009
@@ -11,7 +11,7 @@
         return self._getTargetClass()(*opts)
 
     def _makeOnePopulated(self, programs, any, response=None, exc=None,
-                          gcore=None, coredir=None):
+                          gcore=None, coredir=None, eager=True):
         if response is None:
             response = DummyResponse()
         rpc = DummyRPCServer()
@@ -24,14 +24,46 @@
         gcore = gcore
         coredir = coredir
         prog = self._makeOne(rpc, programs, any, url, timeout, status,
-                             inbody, email, sendmail, coredir, gcore)
+                             inbody, email, sendmail, coredir, gcore, eager)
         prog.stdin = StringIO()
         prog.stdout = StringIO()
         prog.stderr = StringIO()
         prog.connclass = make_connection(response, exc=exc)
         return prog
-        
-    def test_runforever_notatick(self):
+
+    def test_listProcesses_no_programs(self):
+        programs = []
+        any = None
+        prog = self._makeOnePopulated(programs, any)
+        specs = list(prog.listProcesses())
+        self.assertEqual(len(specs), 0)
+
+    def test_listProcesses_w_RUNNING_programs_default_state(self):
+        programs = ['foo']
+        any = None
+        prog = self._makeOnePopulated(programs, any)
+        specs = list(prog.listProcesses())
+        self.assertEqual(len(specs), 1)
+        self.assertEqual(specs[0],
+                         DummySupervisorRPCNamespace.all_process_info[0])
+
+    def test_listProcesses_w_nonRUNNING_programs_default_state(self):
+        programs = ['bar']
+        any = None
+        prog = self._makeOnePopulated(programs, any)
+        specs = list(prog.listProcesses())
+        self.assertEqual(len(specs), 1)
+        self.assertEqual(specs[0],
+                         DummySupervisorRPCNamespace.all_process_info[1])
+
+    def test_listProcesses_w_nonRUNNING_programs_RUNNING_state(self):
+        programs = ['bar']
+        any = None
+        prog = self._makeOnePopulated(programs, any)
+        specs = list(prog.listProcesses(ProcessStates.RUNNING))
+        self.assertEqual(len(specs), 0, (prog.programs, specs))
+
+    def test_runforever_eager_notatick(self):
         programs = {'foo':0, 'bar':0, 'baz_01':0 }
         groups = {}
         any = None
@@ -41,7 +73,7 @@
         prog.runforever(test=True)
         self.assertEqual(prog.stderr.getvalue(), '')
 
-    def test_runforever_error_on_request_some(self):
+    def test_runforever_eager_error_on_request_some(self):
         programs = ['foo', 'bar', 'baz_01', 'notexisting']
         any = None
         prog = self._makeOnePopulated(programs, any, exc=True)
@@ -67,7 +99,7 @@
         self.assertEqual(mailed[1],
                     'Subject: httpok for http://foo/bar: bad status returned')
 
-    def test_runforever_error_on_request_any(self):
+    def test_runforever_eager_error_on_request_any(self):
         programs = []
         any = True
         prog = self._makeOnePopulated(programs, any, exc=True)
@@ -88,7 +120,7 @@
         self.assertEqual(mailed[1],
                     'Subject: httpok for http://foo/bar: bad status returned')
 
-    def test_runforever_error_on_process_stop(self):
+    def test_runforever_eager_error_on_process_stop(self):
         programs = ['FAILED']
         any = False
         prog = self._makeOnePopulated(programs, any, exc=True)
@@ -109,7 +141,7 @@
         self.assertEqual(mailed[1],
                     'Subject: httpok for http://foo/bar: bad status returned')
 
-    def test_runforever_error_on_process_start(self):
+    def test_runforever_eager_error_on_process_start(self):
         programs = ['SPAWN_ERROR']
         any = False
         prog = self._makeOnePopulated(programs, any, exc=True)
@@ -131,7 +163,7 @@
         self.assertEqual(mailed[1],
                     'Subject: httpok for http://foo/bar: bad status returned')
 
-    def test_runforever_gcore(self):
+    def test_runforever_eager_gcore(self):
         programs = ['foo', 'bar', 'baz_01', 'notexisting']
         any = None
         prog = self._makeOnePopulated(programs, any, exc=True, gcore="true",
@@ -160,6 +192,18 @@
         self.assertEqual(mailed[1],
                     'Subject: httpok for http://foo/bar: bad status returned')
 
+    def test_runforever_not_eager_none_running(self):
+        programs = ['bar', 'baz_01']
+        any = None
+        prog = self._makeOnePopulated(programs, any, exc=True, gcore="true",
+                                      coredir="/tmp", eager=False)
+        prog.stdin.write('eventname:TICK len:0\n')
+        prog.stdin.seek(0)
+        prog.runforever(test=True)
+        lines = filter(None, prog.stderr.getvalue().split('\n'))
+        self.assertEqual(len(lines), 0, lines)
+        self.failIf('mailed' in prog.__dict__)
+
 class CrashMailTests(unittest.TestCase):
     def _getTargetClass(self):
         from superlance.crashmail import CrashMail


More information about the Supervisor-checkins mailing list