Exemple #1
0
    def handle_dealer(self, cmd, opts, msg, endpoint, timeout, ssh_server,
                      ssh_keyfile):
        if endpoint is not None:
            client = CircusClient(endpoint=endpoint,
                                  timeout=timeout,
                                  ssh_server=ssh_server,
                                  ssh_keyfile=ssh_keyfile)
        else:
            client = self.client

        try:
            if isinstance(msg, list):
                for i, command in enumerate(msg):
                    clm = self._console(client, command['cmd'], opts,
                                        command['msg'])
                    print("%s: %s" % (i, clm))
            else:
                print(self._console(client, cmd, opts, msg))
        except CallError as e:
            sys.stderr.write(str(e) + " Try to raise the --timeout value\n")
            return 1
        finally:
            if endpoint is not None:
                client.stop()

        return 0
Exemple #2
0
    def handle_dealer(self, cmd, opts, msg, endpoint, timeout, ssh_server,
                      ssh_keyfile):
        if endpoint is not None:
            client = CircusClient(endpoint=endpoint,
                                  timeout=timeout,
                                  ssh_server=ssh_server,
                                  ssh_keyfile=ssh_keyfile)
        else:
            client = self.client

        try:
            if isinstance(msg, list):
                for i, command in enumerate(msg):
                    clm = self._console(client, command['cmd'], opts,
                                        command['msg'])
                    print("%s: %s" % (i, clm))
            else:
                print(self._console(client, cmd, opts, msg))
        except CallError as e:
            msg = str(e)
            if 'timed out' in str(e).lower():
                msg += TIMEOUT_MSG
            sys.stderr.write(msg)
            return 1
        finally:
            if endpoint is not None:
                client.stop()

        return 0
Exemple #3
0
    def handle_dealer(self, command, opts, msg, endpoint, timeout, ssh_server,
                      ssh_keyfile):
        if endpoint is not None:
            client = CircusClient(endpoint=endpoint, timeout=timeout,
                                  ssh_server=ssh_server,
                                  ssh_keyfile=ssh_keyfile)
        else:
            client = self.client

        try:
            if isinstance(msg, list):
                for i, c in enumerate(msg):
                    clm = self._console(client, c['cmd'], opts,
                                        c['msg'])
                    print("%s: %s" % (i, clm))
            else:
                print(self._console(client, command, opts, msg))
        except CallError as e:
            msg = str(e)
            if 'timed out' in str(e).lower():
                msg += TIMEOUT_MSG
            sys.stderr.write(msg)
            return 1
        finally:
            if endpoint is not None:
                client.stop()

        return 0
Exemple #4
0
class TestCircus(unittest.TestCase):

    def setUp(self):
        self.arbiters = []
        self.files = []
        self.tmpfiles = []
        self.cli = CircusClient()

    def tearDown(self):
        self._stop_runners()
        for file in self.files + self.tmpfiles:
            if os.path.exists(file):
                os.remove(file)
        self.cli.stop()

    def get_tmpfile(self, content=None):
        fd, file = mkstemp()
        os.close(fd)
        self.tmpfiles.append(file)
        if content is not None:
            with open(file, 'w') as f:
                f.write(content)
        return file

    @classmethod
    def _create_circus(cls, callable, plugins=None, stats=False, **kw):
        resolve_name(callable)   # used to check the callable
        fd, testfile = mkstemp()
        os.close(fd)
        wdir = os.path.dirname(__file__)
        args = ['generic.py', callable, testfile]
        worker = {'cmd': _CMD, 'args': args, 'working_dir': wdir,
                  'name': 'test', 'graceful_timeout': 4}
        worker.update(kw)
        if stats:
            arbiter = get_arbiter([worker], background=True, plugins=plugins,
                                  stats_endpoint=DEFAULT_ENDPOINT_STATS,
                                  debug=kw.get('debug', False))
        else:
            arbiter = get_arbiter([worker], background=True, plugins=plugins,
                                  debug=kw.get('debug', False))
        arbiter.start()
        return testfile, arbiter

    def _run_circus(self, callable, plugins=None, stats=False, **kw):

        testfile, arbiter = TestCircus._create_circus(callable, plugins, stats,
                                                      **kw)
        self.arbiters.append(arbiter)
        self.files.append(testfile)
        return testfile

    def _stop_runners(self):
        for arbiter in self.arbiters:
            arbiter.stop()
        self.arbiters = []

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)
Exemple #5
0
    def handle_dealer(self, cmd, opts, msg, endpoint, timeout, ssh_server,
                      ssh_keyfile):
        if endpoint is not None:
            client = CircusClient(endpoint=endpoint, timeout=timeout,
                                  ssh_server=ssh_server,
                                  ssh_keyfile=ssh_keyfile)
        else:
            client = self.client

        try:
            if isinstance(msg, list):
                for i, command in enumerate(msg):
                    clm = self._console(client, command['cmd'], opts,
                                        command['msg'])
                    print("%s: %s" % (i, clm))
            else:
                print(self._console(client, cmd, opts, msg))
        except CallError as e:
            sys.stderr.write(str(e) + " Try to raise the --timeout value\n")
            return 1
        finally:
            if endpoint is not None:
                client.stop()

        return 0
class TestWatcher(TestCircus):
    def setUp(self):
        super(TestWatcher, self).setUp()
        self.stream = QueueStream()
        dummy_process = 'circus.tests.test_watcher.run_process'
        self.test_file = self._run_circus(
            dummy_process, stdout_stream={'stream': self.stream})
        self.cli = CircusClient()

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)

    def tearDown(self):
        super(TestWatcher, self).tearDown()
        self.cli.stop()

    def status(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('status')

    def numprocesses(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('numprocesses')

    def test_signal(self):
        self.assertEquals(self.numprocesses('incr', name='test'), 2)

        def get_pids():
            return self.call('list', name='test').get('pids')

        pids = get_pids()
        self.assertEquals(len(pids), 2)
        to_kill = pids[0]
        self.assertEquals(
            self.status('signal',
                        name='test',
                        pid=to_kill,
                        signum=signal.SIGKILL), 'ok')

        time.sleep(1)  # wait for the process to die

        # we still should have two processes, but not the same pids for them
        pids = get_pids()
        self.assertEquals(len(pids), 2)
        self.assertTrue(to_kill not in pids)

    def test_stats(self):
        resp = self.call("stats").get('infos')
        self.assertTrue("test" in resp)
        watchers = resp['test']

        self.assertEqual(watchers[watchers.keys()[0]]['cmdline'],
                         sys.executable.split(os.sep)[-1])

    def test_streams(self):
        time.sleep(1.)
        # let's see what we got
        self.assertTrue(self.stream.qsize() > 1)
Exemple #7
0
class TestWatcher(TestCircus):
    def setUp(self):
        super(TestWatcher, self).setUp()
        self.stream = QueueStream()
        dummy_process = 'circus.tests.test_watcher.run_process'
        self.test_file = self._run_circus(
            dummy_process, stdout_stream={'stream': self.stream})
        self.cli = CircusClient()

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)

    def tearDown(self):
        super(TestWatcher, self).tearDown()
        self.cli.stop()

    def status(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('status')

    def numprocesses(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('numprocesses')

    def testSignal(self):
        self.assertEquals(self.numprocesses("incr", name="test"), 2)
        self.assertEquals(
            self.call("list", name="test").get('processes'), [1, 2])
        self.assertEquals(
            self.status("signal",
                        name="test",
                        process=2,
                        signum=signal.SIGKILL), "ok")

        time.sleep(1.0)
        self.assertEquals(
            self.call("list", name="test").get('processes'), [1, 3])

        processes = self.call("list", name="test").get('processes')
        self.assertEquals(
            self.status("signal", name="test", signum=signal.SIGKILL), "ok")

        time.sleep(1.0)
        self.assertNotEqual(
            self.call("list", name="test").get('processes'), processes)

    def testStats(self):
        resp = self.call("stats").get('infos')
        self.assertTrue("test" in resp)

        self.assertEqual(resp['test']['1']['cmdline'],
                         sys.executable.split(os.sep)[-1])

    def test_streams(self):
        time.sleep(2.)
        # let's see what we got
        self.assertTrue(self.stream.qsize() > 1)
Exemple #8
0
class TestWatcher(TestCircus):

    def setUp(self):
        super(TestWatcher, self).setUp()
        self.stream = QueueStream()
        dummy_process = 'circus.tests.test_watcher.run_process'
        self.test_file = self._run_circus(dummy_process,
                stdout_stream={'stream': self.stream})
        self.cli = CircusClient()

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)

    def tearDown(self):
        super(TestWatcher, self).tearDown()
        self.cli.stop()

    def status(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('status')

    def numprocesses(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('numprocesses')

    def test_signal(self):
        self.assertEquals(self.numprocesses('incr', name='test'), 2)

        def get_pids():
            return self.call('list', name='test').get('pids')

        pids = get_pids()
        self.assertEquals(len(pids), 2)
        to_kill = pids[0]
        self.assertEquals(self.status('signal', name='test', pid=to_kill,
                                      signum=signal.SIGKILL), 'ok')

        time.sleep(1)  # wait for the process to die

        # we still should have two processes, but not the same pids for them
        pids = get_pids()
        self.assertEquals(len(pids), 2)
        self.assertTrue(to_kill not in pids)

    def test_stats(self):
        resp = self.call("stats").get('infos')
        self.assertTrue("test" in resp)
        watchers = resp['test']

        self.assertEqual(watchers[watchers.keys()[0]]['cmdline'],
                         sys.executable.split(os.sep)[-1])

    def test_streams(self):
        time.sleep(1.)
        # let's see what we got
        self.assertTrue(self.stream.qsize() > 1)
Exemple #9
0
class TestWatcher(TestCircus):

    def setUp(self):
        super(TestWatcher, self).setUp()
        self.stream = QueueStream()
        dummy_process = 'circus.tests.test_watcher.run_process'
        self.test_file = self._run_circus(dummy_process,
                stdout_stream={'stream': self.stream})
        self.cli = CircusClient()

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)

    def tearDown(self):
        super(TestWatcher, self).tearDown()
        self.cli.stop()

    def status(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('status')

    def numprocesses(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('numprocesses')

    def testSignal(self):
        self.assertEquals(self.numprocesses("incr", name="test"), 2)
        self.assertEquals(self.call("list", name="test").get('processes'),
                          [1, 2])
        self.assertEquals(self.status("signal", name="test", process=2,
            signum=signal.SIGKILL), "ok")

        time.sleep(1.0)
        self.assertEquals(self.call("list", name="test").get('processes'),
                          [1, 3])

        processes = self.call("list", name="test").get('processes')
        self.assertEquals(self.status("signal", name="test",
            signum=signal.SIGKILL), "ok")

        time.sleep(1.0)
        self.assertNotEqual(self.call("list", name="test").get('processes'),
                processes)

    def testStats(self):
        resp = self.call("stats").get('infos')
        self.assertTrue("test" in resp)

        self.assertEqual(resp['test']['1']['cmdline'],
                         sys.executable.split(os.sep)[-1])

    def test_streams(self):
        time.sleep(2.)
        # let's see what we got
        self.assertTrue(self.stream.qsize() > 1)
Exemple #10
0
    def _client_test(self, ssh_server):
        test_file = self._run_circus('circus.tests.support.run_process')
        self.assertTrue(poll_for(test_file, 'START'))  # process started

        # playing around with the watcher
        client = CircusClient(ssh_server=ssh_server)

        def call(cmd, **props):
            msg = make_message(cmd, **props)
            return client.call(msg)

        def status(cmd, **props):
            resp = call(cmd, **props)
            return resp.get('status')

        def numprocesses(cmd, **props):
            resp = call(cmd, **props)
            return resp.get('numprocesses')

        def numwatchers(cmd, **props):
            resp = call(cmd, **props)
            return resp.get('numwatchers')

        def set(name, **opts):
            return status("set", name=name, options=opts)

        self.assertEquals(set("test", numprocesses=10), 'ok')
        self.assertEquals(numprocesses("numprocesses"), 10)
        self.assertEquals(set("test", numprocesses=1), 'ok')
        self.assertEquals(numprocesses("numprocesses"), 1)
        self.assertEquals(numwatchers("numwatchers"), 1)

        self.assertEquals(call("list").get('watchers'), ['test'])
        self.assertEquals(numprocesses("incr", name="test"), 2)
        self.assertEquals(numprocesses("numprocesses"), 2)
        self.assertEquals(numprocesses("incr", name="test", nb=2), 4)
        self.assertEquals(numprocesses("decr", name="test", nb=3), 1)
        self.assertEquals(numprocesses("numprocesses"), 1)
        self.assertEquals(set("test", env={"test": 1, "test": 2}), 'error')
        self.assertEquals(set("test", env={"test": '1', "test": '2'}),
                'ok')
        resp = call('get', name='test', keys=['env'])
        options = resp.get('options', {})

        self.assertEquals(options.get('env'), {'test': '1', 'test': '2'})

        resp = call('stats', name='test')
        self.assertEqual(resp['status'], 'ok')

        resp = call('globaloptions', name='test')
        self.assertEqual(resp['options']['pubsub_endpoint'],
                        'tcp://127.0.0.1:5556')
        client.stop()
Exemple #11
0
    def test_handler(self):
        self._run_circus('circus.tests.test_client.run_process')
        time.sleep(.5)

        # playing around with the watcher
        client = CircusClient()

        def call(cmd, **props):
            msg = make_message(cmd, **props)
            return client.call(msg)

        def status(cmd, **props):
            resp = call(cmd, **props)
            return resp.get('status')

        def numprocesses(cmd, **props):
            resp = call(cmd, **props)
            return resp.get('numprocesses')

        def numwatchers(cmd, **props):
            resp = call(cmd, **props)
            return resp.get('numwatchers')

        def set(name, **opts):
            return status("set", name=name, options=opts)

        self.assertEquals(set("test", numprocesses=10), 'ok')
        self.assertEquals(numprocesses("numprocesses"), 10)
        self.assertEquals(set("test", numprocesses=1), 'ok')
        self.assertEquals(numprocesses("numprocesses"), 1)
        self.assertEquals(numwatchers("numwatchers"), 1)

        self.assertEquals(call("list").get('watchers'), ['test'])
        self.assertEquals(call("list", name="test").get('processes'), [10])
        self.assertEquals(numprocesses("incr", name="test"), 2)
        self.assertEquals(numprocesses("numprocesses"), 2)
        self.assertEquals(numprocesses("decr", name="test"), 1)
        self.assertEquals(numprocesses("numprocesses"), 1)
        self.assertEquals(set("test", env={"test": 1, "test": 2}), 'error')
        self.assertEquals(set("test", env={"test": '1', "test": '2'}),
                'ok')
        resp = call('get', name='test', keys=['env'])
        options = resp.get('options', {})

        self.assertEquals(options.get('env'), {'test': '1', 'test': '2'})

        resp = call('stats', name='test')
        self.assertEqual(resp['status'], 'ok')

        resp = call('globaloptions', name='test')
        self.assertEqual(resp['options']['pubsub_endpoint'],
                        'tcp://127.0.0.1:5556')
        client.stop()
Exemple #12
0
    def _client_test(self, ssh_server):
        self._run_circus('circus.tests.support.run_process')
        time.sleep(.5)

        # playing around with the watcher
        client = CircusClient(ssh_server=ssh_server)

        def call(cmd, **props):
            msg = make_message(cmd, **props)
            return client.call(msg)

        def status(cmd, **props):
            resp = call(cmd, **props)
            return resp.get('status')

        def numprocesses(cmd, **props):
            resp = call(cmd, **props)
            return resp.get('numprocesses')

        def numwatchers(cmd, **props):
            resp = call(cmd, **props)
            return resp.get('numwatchers')

        def set(name, **opts):
            return status("set", name=name, options=opts)

        self.assertEquals(set("test", numprocesses=10), 'ok')
        self.assertEquals(numprocesses("numprocesses"), 10)
        self.assertEquals(set("test", numprocesses=1), 'ok')
        self.assertEquals(numprocesses("numprocesses"), 1)
        self.assertEquals(numwatchers("numwatchers"), 1)

        self.assertEquals(call("list").get('watchers'), ['test'])
        self.assertEquals(numprocesses("incr", name="test"), 2)
        self.assertEquals(numprocesses("numprocesses"), 2)
        self.assertEquals(numprocesses("incr", name="test", nb=2), 4)
        self.assertEquals(numprocesses("decr", name="test", nb=3), 1)
        self.assertEquals(numprocesses("numprocesses"), 1)
        self.assertEquals(set("test", env={"test": 1, "test": 2}), 'error')
        self.assertEquals(set("test", env={"test": '1', "test": '2'}), 'ok')
        resp = call('get', name='test', keys=['env'])
        options = resp.get('options', {})

        self.assertEquals(options.get('env'), {'test': '1', 'test': '2'})

        resp = call('stats', name='test')
        self.assertEqual(resp['status'], 'ok')

        resp = call('globaloptions', name='test')
        self.assertEqual(resp['options']['pubsub_endpoint'],
                         'tcp://127.0.0.1:5556')
        client.stop()
Exemple #13
0
class TestWatcher(TestCircus):

    def setUp(self):
        super(TestWatcher, self).setUp()
        dummy_process = 'circus.tests.test_watcher.run_process'
        self.test_file = self._run_circus(dummy_process)
        self.cli = CircusClient()

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)

    def tearDown(self):
        super(TestWatcher, self).tearDown()
        self.cli.stop()

    def status(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('status')

    def numprocesses(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('numprocesses')

    def testSignal(self):
        self.assertEquals(self.numprocesses("incr", name="test"), 2)
        self.assertEquals(self.call("list", name="test").get('processes'),
                          [1, 2])
        self.assertEquals(self.status("signal", name="test", process=2,
            signum=signal.SIGKILL), "ok")

        time.sleep(1.0)
        self.assertEquals(self.call("list", name="test").get('processes'),
                          [1, 3])

        processes = self.call("list", name="test").get('processes')
        self.assertEquals(self.status("signal", name="test",
            signum=signal.SIGKILL), "ok")

        time.sleep(1.0)
        self.assertNotEqual(self.call("list", name="test").get('processes'),
                processes)

    def testStats(self):
        resp = self.call("stats").get('infos')
        self.assertTrue("test" in resp)

        self.assertEqual(resp['test']['1']['cmdline'], 'python')
Exemple #14
0
    def handle_dealer(self, cmd, opts, msg, endpoint, timeout):
        client = CircusClient(endpoint=endpoint, timeout=timeout)
        try:
            if isinstance(msg, list):
                for i, cmd in enumerate(msg):
                    clm = self._console(client, cmd, opts, msg)
                    print("%s: %s" % (i, clm))
            else:
                print(self._console(client, cmd, opts, msg))
        except CallError as e:

            sys.stderr.write(str(e))
            return 1
        finally:
            client.stop()
        return 0
Exemple #15
0
    def test_handler(self):
        self._run_circus('circus.tests.test_client.run_process')
        time.sleep(.5)

        # playing around with the watcher
        client = CircusClient()

        def call(cmd, **props):
            msg = make_message(cmd, **props)
            return client.call(msg)

        def status(cmd, **props):
            resp = call(cmd, **props)
            return resp.get('status')

        def numprocesses(cmd, **props):
            resp = call(cmd, **props)
            return resp.get('numprocesses')

        def numwatchers(cmd, **props):
            resp = call(cmd, **props)
            return resp.get('numwatchers')

        def set(name, **opts):
            return status("set", name=name, options=opts)

        self.assertEquals(set("test", numprocesses=10), 'ok')
        self.assertEquals(numprocesses("numprocesses"), 10)
        self.assertEquals(set("test", numprocesses=1), 'ok')
        self.assertEquals(numprocesses("numprocesses"), 1)
        self.assertEquals(numwatchers("numwatchers"), 1)

        self.assertEquals(call("list").get('watchers'), ['test'])
        self.assertEquals(call("list", name="test").get('processes'), [10])
        self.assertEquals(numprocesses("incr", name="test"), 2)
        self.assertEquals(numprocesses("numprocesses"), 2)
        self.assertEquals(numprocesses("decr", name="test"), 1)
        self.assertEquals(numprocesses("numprocesses"), 1)
        self.assertEquals(set("test", env={"test": 1, "test": 2}), 'error')
        self.assertEquals(set("test", env={"test": '1', "test": '2'}), 'ok')
        resp = call('get', name='test', keys=['env'])
        options = resp.get('options', {})

        self.assertEquals(options.get('env'), {'test': '1', 'test': '2'})

        client.stop()
Exemple #16
0
    def handle_dealer(self, cmd, opts, msg, endpoint, timeout):
        client = CircusClient(endpoint=endpoint, timeout=timeout)
        try:
            if isinstance(msg, list):
                for i, command in enumerate(msg):
                    clm = self._console(client, command['cmd'], opts,
                                        command['msg'])
                    print("%s: %s" % (i, clm))
            else:
                print(self._console(client, cmd, opts, msg))
        except CallError as e:

            sys.stderr.write(str(e))
            return 1
        finally:
            client.stop()
        return 0
Exemple #17
0
class TestWatcher(TestCircus):

    def setUp(self):
        super(TestWatcher, self).setUp()
        dummy_process = 'circus.tests.test_stream.run_process'
        fd, log = tempfile.mkstemp()
        self.log = log
        os.close(fd)
        stream = {'stream': FileStream(log)}
        self.test_file = self._run_circus(dummy_process,
                stdout_stream=stream, stderr_stream=stream, debug=True)
        self.cli = CircusClient()

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)

    def tearDown(self):
        super(TestWatcher, self).tearDown()
        self.cli.stop()
        os.remove(self.log)

    def test_stream(self):
        time.sleep(2.)
        self.call("stats").get('infos')
        # let's see what we got in the file
        with open(self.log) as f:
            data = f.read()

        self.assertTrue('stderr' in data)
        self.assertTrue('stdout' in data)

        # restarting
        self.call('restart')
        time.sleep(1.)

        current = time.time()
        # should be running
        with open(self.log) as f:
            data = f.readlines()

        # last log should be less than one second old
        last = data[-1]
        delta = abs(current - int(last.split('-')[0]))
        self.assertTrue(delta < 1, delta)
Exemple #18
0
class TestWatcher(TestCircus):
    def setUp(self):
        super(TestWatcher, self).setUp()
        dummy_process = "circus.tests.test_stream.run_process"
        fd, self.stdout = tempfile.mkstemp()
        os.close(fd)
        fd, self.stderr = tempfile.mkstemp()
        os.close(fd)
        self.test_file = self._run_circus(
            dummy_process,
            stdout_stream={"stream": FileStream(self.stdout)},
            stderr_stream={"stream": FileStream(self.stderr)},
            debug=True,
        )
        self.cli = CircusClient()

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)

    def tearDown(self):
        super(TestWatcher, self).tearDown()
        self.cli.stop()
        os.remove(self.stdout)
        os.remove(self.stderr)

    def test_stream(self):
        # wait for the process to be started
        self.assertTrue(poll_for(self.stdout, "stdout"))
        self.assertTrue(poll_for(self.stderr, "stderr"))

        # clean slate
        truncate_file(self.stdout)
        truncate_file(self.stderr)
        # restart and make sure streams are still working
        self.call("restart")

        # wait for the process to be restarted
        self.assertTrue(poll_for(self.stdout, "stdout"))
        self.assertTrue(poll_for(self.stderr, "stderr"))
Exemple #19
0
class TestWatcher(TestCircus):

    def setUp(self):
        super(TestWatcher, self).setUp()
        dummy_process = 'circus.tests.test_stream.run_process'
        fd, self.stdout = tempfile.mkstemp()
        os.close(fd)
        fd, self.stderr = tempfile.mkstemp()
        os.close(fd)
        self.test_file = self._run_circus(
            dummy_process,
            stdout_stream={'stream': FileStream(self.stdout)},
            stderr_stream={'stream': FileStream(self.stderr)},
            debug=True)
        self.cli = CircusClient()

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)

    def tearDown(self):
        super(TestWatcher, self).tearDown()
        self.cli.stop()
        os.remove(self.stdout)
        os.remove(self.stderr)

    def test_stream(self):
        # wait for the process to be started
        self.assertTrue(poll_for(self.stdout, 'stdout'))
        self.assertTrue(poll_for(self.stderr, 'stderr'))

        # clean slate
        truncate_file(self.stdout)
        truncate_file(self.stderr)
        # restart and make sure streams are still working
        self.call('restart')

        # wait for the process to be restarted
        self.assertTrue(poll_for(self.stdout, 'stdout'))
        self.assertTrue(poll_for(self.stderr, 'stderr'))
Exemple #20
0
class LiveClient(object):
    def __init__(self, endpoint):
        self.endpoint = str(endpoint)
        self.stats_endpoint = None
        self.client = CircusClient(endpoint=self.endpoint)
        self.connected = False
        self.watchers = []
        self.stats = defaultdict(list)
        self.refresher = Refresher(self)
        self.dstats = []

    def stop(self):
        self.client.stop()
        self.refresher.running = False
        self.refresher.join()

    def verify(self):
        self.watchers = []
        # trying to list the watchers
        msg = cmds['list'].make_message()
        try:
            res = self.client.call(msg)
            self.connected = True
            for watcher in res['watchers']:
                if watcher == 'circusd-stats':
                    continue
                msg = cmds['options'].make_message(name=watcher)
                options = self.client.call(msg)
                self.watchers.append((watcher, options['options']))
            self.watchers.sort()
            self.stats_endpoint = self.get_global_options()['stats_endpoint']
            if not self.refresher.running:
                self.refresher.start()
        except CallError:
            self.connected = False

    def killproc(self, name, pid):
        msg = cmds['signal'].make_message(name=name,
                                          process=int(pid),
                                          signum=9)
        res = self.client.call(msg)
        self.verify()  # will do better later
        return res['status'] == 'ok'

    def get_option(self, name, option):
        watchers = dict(self.watchers)
        return watchers[name][option]

    def get_global_options(self):
        msg = cmds['globaloptions'].make_message()
        options = self.client.call(msg)
        return options['options']

    def get_options(self, name):
        watchers = dict(self.watchers)
        return watchers[name].items()

    def incrproc(self, name):
        msg = cmds['incr'].make_message(name=name)
        res = self.client.call(msg)
        self.verify()  # will do better later
        return res['numprocesses']

    def decrproc(self, name):
        msg = cmds['decr'].make_message(name=name)
        res = self.client.call(msg)
        self.verify()  # will do better later
        return res['numprocesses']

    def get_stats(self, name, start=0, end=-1):
        return self.stats[name][start:end]

    def get_dstats(self, field, start=0, end=-1):
        stats = self.dstats[start:end]
        res = []
        for stat in stats:
            res.append(stat[field])
        return res

    def get_pids(self, name):
        msg = cmds['listpids'].make_message(name=name)
        res = self.client.call(msg)
        return res['pids']

    def get_series(self, name, pid, field, start=0, end=-1):
        stats = self.get_stats(name, start, end)
        res = []
        for stat in stats:
            pids = stat['pid']
            if isinstance(pids, list):
                continue
            if str(pid) == str(stat['pid']):
                res.append(stat[field])
        return res

    def get_status(self, name):
        msg = cmds['status'].make_message(name=name)
        res = self.client.call(msg)
        return res['status']

    def switch_status(self, name):
        msg = cmds['status'].make_message(name=name)
        res = self.client.call(msg)
        status = res['status']
        if status == 'active':
            # stopping the watcher
            msg = cmds['stop'].make_message(name=name)
        else:
            msg = cmds['start'].make_message(name=name)
        res = self.client.call(msg)
        return res

    def add_watcher(self, name, cmd, **kw):
        msg = cmds['add'].make_message(name=name, cmd=cmd)
        res = self.client.call(msg)
        if res['status'] == 'ok':
            # now configuring the options
            options = {}
            options['numprocesses'] = int(kw.get('numprocesses', '5'))
            options['working_dir'] = kw.get('working_dir')
            options['shell'] = kw.get('shell', 'off') == 'on'
            msg = cmds['set'].make_message(name=name, options=options)
            res = self.client.call(msg)
            self.verify()  # will do better later
            return res['status'] == 'ok'
        else:
            return False
Exemple #21
0
class TestTrainer(TestCircus):

    def setUp(self):
        super(TestTrainer, self).setUp()
        dummy_process = 'circus.tests.test_arbiter.run_dummy'
        self.test_file = self._run_circus(dummy_process)
        self.cli = CircusClient()

    def tearDown(self):
        super(TestTrainer, self).tearDown()
        self.cli.stop()

    def test_numwatchers(self):
        msg = make_message("numwatchers")
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("numwatchers"), 1)

    def test_numprocesses(self):
        msg = make_message("numprocesses")
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("numprocesses"), 1)

    def test_processes(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        self.assertEqual(resp.get('processes'), [1])

        msg2 = make_message("incr", name="test")
        self.cli.call(msg2)

        resp = self.cli.call(msg1)
        self.assertEqual(resp.get('processes'), [1, 2])

    def test_watchers(self):
        resp = self.cli.call(make_message("list"))
        self.assertEqual(resp.get('watchers'), ["test"])

    def _get_cmd(self):
        fd, testfile = mkstemp()
        os.close(fd)
        cmd = '%s generic.py %s %s' % (sys.executable,
                        'circus.tests.test_arbiter.run_dummy', testfile)

        return cmd

    def _get_cmd_args(self):
        fd, testfile = mkstemp()
        os.close(fd)
        cmd = sys.executable
        args = ['generic.py', 'circus.tests.test_arbiter.run_dummy',
                testfile]
        return cmd, args

    def test_add_watcher(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

    def test_add_watcher1(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        resp = self.cli.call(make_message("list"))
        self.assertEqual(resp.get('watchers'), ["test", "test1"])

    def test_add_watcher2(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        resp = self.cli.call(make_message("numwatchers"))
        self.assertEqual(resp.get("numwatchers"), 2)

    def test_add_watcher3(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        resp = self.cli.call(msg)
        self.assertTrue(resp.get('status'), 'error')

    def test_add_watcher4(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

    def test_add_watcher5(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("start", name="test1"))
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

    def test_rm_watcher(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        msg = make_message("rm", name="test1")
        self.cli.call(msg)
        resp = self.cli.call(make_message("numwatchers"))
        self.assertEqual(resp.get("numwatchers"), 1)

    def test_stop(self):
        resp = self.cli.call(make_message("quit"))
        self.assertEqual(resp.get("status"), "ok")
        self.assertRaises(CallError, self.cli.call, make_message("list"))

    def test_reload(self):
        resp = self.cli.call(make_message("reload"))
        self.assertEqual(resp.get("status"), "ok")

    def test_reload1(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        processes1 = resp.get('processes')

        self.cli.call(make_message("reload"))
        time.sleep(0.5)

        msg2 = make_message("list", name="test")
        resp = self.cli.call(msg2)
        processes2 = resp.get('processes')

        self.assertNotEqual(processes1, processes2)

    def test_reload2(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        processes1 = resp.get('processes')
        self.assertEqual(processes1, [1])

        self.cli.call(make_message("reload"))
        time.sleep(0.5)

        make_message("list", name="test")
        resp = self.cli.call(msg1)

        processes2 = resp.get('processes')
        self.assertEqual(processes2, [2])

    def test_stop_watchers(self):
        resp = self.cli.call(make_message("stop"))
        self.assertEqual(resp.get("status"), "ok")

    def test_stop_watchers1(self):
        self.cli.call(make_message("stop"))
        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get("status"), "stopped")

    def test_stop_watchers2(self):
        self.cli.call(make_message("stop", name="test"))
        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get('status'), "stopped")

    def test_stop_watchers3(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("start", name="test1"))
        self.assertEqual(resp.get("status"), "ok")

        self.cli.call(make_message("stop", name="test1"))
        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get('status'), "stopped")

        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get('status'), "active")
Exemple #22
0
class TestWatcher(TestCircus):
    def setUp(self):
        super(TestWatcher, self).setUp()
        self.stream = QueueStream()
        dummy_process = 'circus.tests.test_watcher.run_process'
        self.test_file = self._run_circus(
            dummy_process, stdout_stream={'stream': self.stream})
        self.arbiter = self.arbiters[-1]
        self.cli = CircusClient()

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)

    def tearDown(self):
        super(TestWatcher, self).tearDown()
        self.cli.stop()

    def status(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('status')

    def numprocesses(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('numprocesses')

    def pids(self):
        return self.call('list', name='test').get('pids')

    def test_signal(self):
        self.assertEquals(self.numprocesses('incr', name='test'), 2)

        pids = self.pids()
        self.assertEquals(len(pids), 2)
        to_kill = pids[0]
        self.assertEquals(
            self.status('signal',
                        name='test',
                        pid=to_kill,
                        signum=signal.SIGKILL), 'ok')

        time.sleep(1)  # wait for the process to die

        # we still should have two processes, but not the same pids for them
        pids = self.pids()
        self.assertEquals(len(pids), 2)
        self.assertTrue(to_kill not in pids)

    def test_unexisting(self):
        watcher = self.arbiter.get_watcher("test")

        self.assertEquals(len(watcher.processes), 1)
        process = watcher.processes.values()[0]
        to_kill = process.pid
        # the process is killed in an unsual way
        os.kill(to_kill, signal.SIGSEGV)
        # and wait for it to die
        pid, status = os.waitpid(to_kill, 0)
        # ansure the old process is considered "unexisting"
        self.assertEquals(process.status, UNEXISTING)

        # this should clean up and create a new process
        watcher.reap_and_manage_processes()

        # we should have a new process here now
        self.assertEquals(len(watcher.processes), 1)
        process = watcher.processes.values()[0]
        # and that one needs to have a new pid.
        self.assertNotEqual(process.pid, to_kill)
        # and should not be unexisting...
        self.assertNotEqual(process.status, UNEXISTING)

    def test_stats(self):
        resp = self.call("stats").get('infos')
        self.assertTrue("test" in resp)
        watchers = resp['test']

        self.assertEqual(watchers[watchers.keys()[0]]['cmdline'],
                         sys.executable.split(os.sep)[-1])

    def test_streams(self):
        time.sleep(1.)
        # let's see what we got
        self.assertTrue(self.stream.qsize() > 1)

    def test_max_age(self):
        result = self.call('set',
                           name='test',
                           options={
                               'max_age': 1,
                               'max_age_variance': 0
                           })
        self.assertEquals(result.get('status'), 'ok')
        initial_pids = self.pids()
        time.sleep(3.0)  # allow process to reach max_age and restart
        current_pids = self.pids()
        self.assertEqual(len(current_pids), 1)
        self.assertNotEqual(initial_pids, current_pids)
Exemple #23
0
class TestWatcher(TestCircus):

    def setUp(self):
        super(TestWatcher, self).setUp()
        self.stream = QueueStream()
        dummy_process = 'circus.tests.test_watcher.run_process'
        self.test_file = self._run_circus(dummy_process,
                stdout_stream={'stream': self.stream})
        self.arbiter = self.arbiters[-1]
        self.cli = CircusClient()

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)

    def tearDown(self):
        super(TestWatcher, self).tearDown()
        self.cli.stop()

    def status(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('status')

    def numprocesses(self, cmd, **props):
        resp = self.call(cmd, **props)
        return resp.get('numprocesses')

    def pids(self):
        return self.call('list', name='test').get('pids')

    def test_signal(self):
        self.assertEquals(self.numprocesses('incr', name='test'), 2)

        pids = self.pids()
        self.assertEquals(len(pids), 2)
        to_kill = pids[0]
        self.assertEquals(self.status('signal', name='test', pid=to_kill,
                                      signum=signal.SIGKILL), 'ok')

        time.sleep(1)  # wait for the process to die

        # we still should have two processes, but not the same pids for them
        pids = self.pids()
        self.assertEquals(len(pids), 2)
        self.assertTrue(to_kill not in pids)

    def test_unexisting(self):
        watcher = self.arbiter.get_watcher("test")

        self.assertEquals(len(watcher.processes), 1)
        process = watcher.processes.values()[0]
        to_kill = process.pid
        # the process is killed in an unsual way
        os.kill(to_kill, signal.SIGSEGV)
        # and wait for it to die
        pid, status = os.waitpid(to_kill, 0)
        # ansure the old process is considered "unexisting"
        self.assertEquals(process.status, UNEXISTING)

        # this should clean up and create a new process
        watcher.reap_and_manage_processes()

        # we should have a new process here now
        self.assertEquals(len(watcher.processes), 1)
        process = watcher.processes.values()[0]
        # and that one needs to have a new pid.
        self.assertNotEqual(process.pid, to_kill)
        # and should not be unexisting...
        self.assertNotEqual(process.status, UNEXISTING)

    def test_stats(self):
        resp = self.call("stats").get('infos')
        self.assertTrue("test" in resp)
        watchers = resp['test']

        self.assertEqual(watchers[watchers.keys()[0]]['cmdline'],
                         sys.executable.split(os.sep)[-1])

    def test_streams(self):
        time.sleep(1.)
        # let's see what we got
        self.assertTrue(self.stream.qsize() > 1)

    def test_max_age(self):
        result = self.call('set', name='test',
                           options={'max_age': 1, 'max_age_variance': 0})
        self.assertEquals(result.get('status'), 'ok')
        initial_pids = self.pids()
        time.sleep(3.0)  # allow process to reach max_age and restart
        current_pids = self.pids()
        self.assertEqual(len(current_pids), 1)
        self.assertNotEqual(initial_pids, current_pids)
Exemple #24
0
class TestTrainer(TestCircus):

    def setUp(self):
        super(TestTrainer, self).setUp()
        dummy_process = 'circus.tests.test_arbiter.run_dummy'
        self.test_file = self._run_circus(dummy_process)
        self.cli = CircusClient()

    def tearDown(self):
        super(TestTrainer, self).tearDown()
        self.cli.stop()

    def test_numwatchers(self):
        msg = make_message("numwatchers")
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("numwatchers"), 1)

    def test_numprocesses(self):
        msg = make_message("numprocesses")
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("numprocesses"), 1)

    def test_processes(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        self.assertEqual(resp.get('processes'), [1])

        msg2 = make_message("incr", name="test")
        self.cli.call(msg2)

        resp = self.cli.call(msg1)
        self.assertEqual(resp.get('processes'), [1, 2])

    def test_watchers(self):
        resp = self.cli.call(make_message("list"))
        self.assertEqual(resp.get('watchers'), ["test"])

    def _get_cmd(self):
        fd, testfile = mkstemp()
        os.close(fd)
        cmd = '%s generic.py %s %s' % (sys.executable,
                        'circus.tests.test_arbiter.run_dummy', testfile)

        return cmd

    def _get_cmd_args(self):
        cmd = sys.executable
        args = ['generic.py', 'circus.tests.test_arbiter.run_dummy1']
        return cmd, args

    def test_add_watcher(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

    def test_add_watcher1(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        resp = self.cli.call(make_message("list"))
        self.assertEqual(resp.get('watchers'), ["test", "test1"])

    def test_add_watcher2(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        resp = self.cli.call(make_message("numwatchers"))
        self.assertEqual(resp.get("numwatchers"), 2)

    def test_add_watcher3(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        resp = self.cli.call(msg)
        self.assertTrue(resp.get('status'), 'error')

    def test_add_watcher4(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

    def test_add_watcher5(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("start", name="test1"))
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

    def test_add_watcher6(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args,
                start=True)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

    def test_add_watcher7(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args,
                start=True, options={"flapping_window": 100})
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

        resp = self.cli.call(make_message("options", name="test1"))
        options = resp.get('options', {})
        self.assertEqual(options.get("flapping_window"), 100)

    def test_rm_watcher(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        msg = make_message("rm", name="test1")
        self.cli.call(msg)
        resp = self.cli.call(make_message("numwatchers"))
        self.assertEqual(resp.get("numwatchers"), 1)

    def test_stop(self):
        resp = self.cli.call(make_message("quit"))
        self.assertEqual(resp.get("status"), "ok")
        self.assertRaises(CallError, self.cli.call, make_message("list"))

    def test_reload(self):
        resp = self.cli.call(make_message("reload"))
        self.assertEqual(resp.get("status"), "ok")

    def test_reload1(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        processes1 = resp.get('processes')

        self.cli.call(make_message("reload"))
        time.sleep(0.5)

        msg2 = make_message("list", name="test")
        resp = self.cli.call(msg2)
        processes2 = resp.get('processes')

        self.assertNotEqual(processes1, processes2)

    def test_reload2(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        processes1 = resp.get('processes')
        self.assertEqual(processes1, [1])

        self.cli.call(make_message("reload"))
        time.sleep(0.5)

        make_message("list", name="test")
        resp = self.cli.call(msg1)

        processes2 = resp.get('processes')
        self.assertEqual(processes2, [2])

    def test_stop_watchers(self):
        resp = self.cli.call(make_message("stop"))
        self.assertEqual(resp.get("status"), "ok")

    def test_stop_watchers1(self):
        self.cli.call(make_message("stop"))
        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get("status"), "stopped")

    def test_stop_watchers2(self):
        self.cli.call(make_message("stop", name="test"))
        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get('status'), "stopped")

    def test_stop_watchers3(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("start", name="test1"))
        self.assertEqual(resp.get("status"), "ok")

        self.cli.call(make_message("stop", name="test1"))
        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get('status'), "stopped")

        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get('status'), "active")

    def test_plugins(self):
        # killing the setUp runner
        self._stop_runners()
        self.cli.stop()

        # setting up a circusd with a plugin
        dummy_process = 'circus.tests.test_arbiter.run_dummy'
        plugin = 'circus.tests.test_arbiter.Plugin'
        plugins = [{'use': plugin}]
        self._run_circus(dummy_process, plugins=plugins)

        # doing a few operations
        cli = CircusClient()
        msg1 = make_message("list", name="test")
        resp = cli.call(msg1)
        self.assertEqual(resp.get('processes'), [1])
        msg2 = make_message("incr", name="test")
        cli.call(msg2)
        resp = cli.call(msg1)
        self.assertEqual(resp.get('processes'), [1, 2])

        # checking what the plugin did
        wanted = [('test', 'spawn'), ('test', 'start'), ('test', 'spawn')]
        self.assertEqual(Plugin.events, wanted)
Exemple #25
0
class LiveClient(object):
    def __init__(self, endpoint):
        self.endpoint = str(endpoint)
        self.stats_endpoint = None
        self.client = CircusClient(endpoint=self.endpoint)
        self.connected = False
        self.watchers = []
        self.plugins = []
        self.stats = defaultdict(list)
        self.dstats = []

    def stop(self):
        self.client.stop()

    def update_watchers(self):
        """Calls circus and initialize the list of watchers.

        If circus is not connected raises an error.
        """
        self.watchers = []
        # trying to list the watchers
        try:
            self.connected = True
            for watcher in self.client.send_message('list')['watchers']:
                if watcher == 'circusd-stats':
                    continue
                options = self.client.send_message('options', name=watcher)
                self.watchers.append((watcher, options['options']))
                if watcher.startswith('plugin:'):
                    self.plugins.append(watcher)

            self.watchers.sort()
            self.stats_endpoint = self.get_global_options()['stats_endpoint']
        except CallError:
            self.connected = False

    def killproc(self, name, pid):
        res = self.client.send_message('signal',
                                       name=name,
                                       process=int(pid),
                                       signum=9)
        self.update_watchers()  # will do better later
        return res

    def get_option(self, name, option):
        watchers = dict(self.watchers)
        return watchers[name][option]

    def get_global_options(self):
        return self.client.send_message('globaloptions')['options']

    def get_options(self, name):
        watchers = dict(self.watchers)
        return watchers[name].items()

    def incrproc(self, name):
        res = self.client.send_message('incr', name=name)
        self.update_watchers()  # will do better later
        return res

    def decrproc(self, name):
        res = self.client.send_message('decr', name=name)
        self.update_watchers()  # will do better later
        return res

    def get_stats(self, name, start=0, end=-1):
        return self.stats[name][start:end]

    def get_dstats(self, field, start=0, end=-1):
        stats = self.dstats[start:end]
        res = []
        for stat in stats:
            res.append(stat[field])
        return res

    def get_pids(self, name):
        res = self.client.send_message('list', name=name)
        return res['pids']

    def get_series(self, name, pid, field, start=0, end=-1):
        stats = self.get_stats(name, start, end)
        res = []
        for stat in stats:
            pids = stat['pid']
            if isinstance(pids, list):
                continue
            if str(pid) == str(stat['pid']):
                res.append(stat[field])
        return res

    def get_status(self, name):
        return self.client.send_message('status', name=name)['status']

    def switch_status(self, name):
        msg = cmds['status'].make_message(name=name)
        res = self.client.call(msg)
        status = res['status']
        if status == 'active':
            # stopping the watcher
            msg = cmds['stop'].make_message(name=name)
        else:
            msg = cmds['start'].make_message(name=name)
        res = self.client.call(msg)
        return res

    def add_watcher(self, name, cmd, **kw):
        res = self.client.send_message('add', name=name, cmd=cmd)
        if res['status'] == 'ok':
            # now configuring the options
            options = {}
            options['numprocesses'] = int(kw.get('numprocesses', '5'))
            options['working_dir'] = kw.get('working_dir')
            options['shell'] = kw.get('shell', 'off') == 'on'
            res = self.client.send_message('set', name=name, options=options)
            self.update_watchers()  # will do better later
        return res
Exemple #26
0
class TestCircus(unittest.TestCase):
    def setUp(self):
        self.arbiters = []
        self.files = []
        self.tmpfiles = []
        self.cli = CircusClient()

    def tearDown(self):
        self._stop_runners()
        for file in self.files + self.tmpfiles:
            if os.path.exists(file):
                os.remove(file)
        self.cli.stop()

    def get_tmpfile(self, content=None):
        fd, file = mkstemp()
        os.close(fd)
        self.tmpfiles.append(file)
        if content is not None:
            with open(file, 'w') as f:
                f.write(content)
        return file

    def _run_circus(self, callable, plugins=None, stats=False, **kw):
        resolve_name(callable)  # used to check the callable
        fd, testfile = mkstemp()
        os.close(fd)
        wdir = os.path.dirname(__file__)
        args = ['generic.py', callable, testfile]
        worker = {
            'cmd': _CMD,
            'args': args,
            'working_dir': wdir,
            'name': 'test',
            'graceful_timeout': 4
        }
        worker.update(kw)
        if stats:
            arbiter = get_arbiter([worker],
                                  background=True,
                                  plugins=plugins,
                                  stats_endpoint=DEFAULT_ENDPOINT_STATS,
                                  debug=kw.get('debug', False))
        else:
            arbiter = get_arbiter([worker],
                                  background=True,
                                  plugins=plugins,
                                  debug=kw.get('debug', False))

        arbiter.start()
        time.sleep(.3)
        self.arbiters.append(arbiter)
        self.files.append(testfile)
        return testfile

    def _stop_runners(self):
        for arbiter in self.arbiters:
            arbiter.stop()
        self.arbiters = []

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)
Exemple #27
0
class LiveClient(object):
    def __init__(self, endpoint):
        self.endpoint = str(endpoint)
        self.client = CircusClient(endpoint=self.endpoint)
        self.connected = False
        self.watchers = []
        self.stats = defaultdict(list)
        self.refresher = Refresher(self)
        self.dstats = []

    def stop(self):
        self.client.stop()
        self.refresher.running = False
        self.refresher.join()

    def verify(self):
        self.watchers = []
        # trying to list the watchers
        msg = cmds['list'].make_message()
        try:
            res = self.client.call(msg)
            self.connected = True
            for watcher in res['watchers']:
                msg = cmds['options'].make_message(name=watcher)
                options = self.client.call(msg)
                self.watchers.append((watcher, options['options']))
            self.watchers.sort()
            if not self.refresher.running:
                self.refresher.start()
        except CallError:
            self.connected = False

    def killproc(self, name, pid):
        msg = cmds['signal'].make_message(name=name, process=int(pid),
                signum=9)
        res = self.client.call(msg)
        self.verify()  # will do better later
        return res['status'] == 'ok'

    def get_option(self, name, option):
        watchers = dict(self.watchers)
        return watchers[name][option]

    def get_global_options(self):
        msg = cmds['globaloptions'].make_message()
        options = self.client.call(msg)
        return options['options']

    def get_options(self, name):
        watchers = dict(self.watchers)
        return watchers[name].items()

    def incrproc(self, name):
        msg = cmds['incr'].make_message(name=name)
        res = self.client.call(msg)
        self.verify()  # will do better later
        return res['numprocesses']

    def decrproc(self, name):
        msg = cmds['decr'].make_message(name=name)
        res = self.client.call(msg)
        self.verify()  # will do better later
        return res['numprocesses']

    def get_stats(self, name, start=0, end=-1):
        return self.stats[name][start:end]

    def get_dstats(self, field, start=0, end=-1):
        stats = self.dstats[start:end]
        res = []
        for stat in stats:
            res.append(stat[field])
        return res

    def get_pids(self, name):
        msg = cmds['list'].make_message(name=name)
        res = self.client.call(msg)
        return res['processes']

    def get_series(self, name, pid, field, start=0, end=-1):
        stats = self.get_stats(name, start, end)
        res = []
        pid = str(pid)
        for stat in stats:
            if pid not in stat:
                continue
            res.append(stat[pid][field])
        return res

    def get_status(self, name):
        msg = cmds['status'].make_message(name=name)
        res = self.client.call(msg)
        return res['status']

    def switch_status(self, name):
        msg = cmds['status'].make_message(name=name)
        res = self.client.call(msg)
        status = res['status']
        if status == 'active':
            # stopping the watcher
            msg = cmds['stop'].make_message(name=name)
        else:
            msg = cmds['start'].make_message(name=name)
        res = self.client.call(msg)
        return res

    def add_watcher(self, name, cmd, **kw):
        msg = cmds['add'].make_message(name=name, cmd=cmd)
        res = self.client.call(msg)
        if res['status'] == 'ok':
            # now configuring the options
            options = {}
            options['numprocesses'] = int(kw.get('numprocesses', '5'))
            options['working_dir'] = kw.get('working_dir')
            options['shell'] = kw.get('shell', 'off') == 'on'
            msg = cmds['set'].make_message(name=name, options=options)
            res = self.client.call(msg)
            self.verify()  # will do better later
            return res['status'] == 'ok'
        else:
            return False
Exemple #28
0
class TestCircus(unittest.TestCase):
    def setUp(self):
        self.arbiters = []
        self.files = []
        self.dirs = []
        self.tmpfiles = []
        self.cli = CircusClient()

    def tearDown(self):
        self._stop_runners()
        for file in self.files + self.tmpfiles:
            if os.path.exists(file):
                os.remove(file)

        for dir in self.dirs:
            shutil.rmtree(dir)

        self.cli.stop()

    def get_tmpdir(self):
        dir_ = mkdtemp()
        self.dirs.append(dir_)
        return dir_

    def get_tmpfile(self, content=None):
        fd, file = mkstemp()
        os.close(fd)
        self.tmpfiles.append(file)
        if content is not None:
            with open(file, "w") as f:
                f.write(content)
        return file

    @classmethod
    def _create_circus(cls, callable, plugins=None, stats=False, **kw):
        resolve_name(callable)  # used to check the callable
        fd, testfile = mkstemp()
        os.close(fd)
        wdir = os.path.dirname(__file__)
        args = ["generic.py", callable, testfile]
        worker = {"cmd": _CMD, "args": args, "working_dir": wdir, "name": "test", "graceful_timeout": 4}
        worker.update(kw)
        debug = kw.get("debug", False)

        if stats:
            arbiter = get_arbiter(
                [worker],
                background=True,
                plugins=plugins,
                stats_endpoint=DEFAULT_ENDPOINT_STATS,
                statsd=True,
                debug=debug,
                statsd_close_outputs=not debug,
            )
        else:
            arbiter = get_arbiter([worker], background=True, plugins=plugins, debug=debug)
        arbiter.start()
        return testfile, arbiter

    def _run_circus(self, callable, plugins=None, stats=False, **kw):

        testfile, arbiter = TestCircus._create_circus(callable, plugins, stats, **kw)
        self.arbiters.append(arbiter)
        self.files.append(testfile)
        return testfile

    def _stop_runners(self):
        for arbiter in self.arbiters:
            arbiter.stop()
        self.arbiters = []

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)
Exemple #29
0
class Client(object):

    def __init__(self, port=6000):
        self._client = CircusClient(endpoint='tcp://127.0.0.1:{}'.format(port))

    def startup(self):
        click.echo('startup')
        sp.call(['circusd', 'basic.ini', '--daemon'])

    def quit(self):
        self._client.call({
            'command': 'quit',
            'properties': {}
        })

    def stop(self):
        self._client.stop()

    def start_aiida_daemon(self, profile):
        if not get_daemon_name(profile) in self.list_watchers():
            # ~ command = {
                # ~ 'command': 'add',
                # ~ 'properties': {
                    # ~ 'name': WATCHER_NAME,
                    # ~ 'cmd': 'verdi devel run_daemon',
                    # ~ 'virtualenv': path.abspath(path.join(executable, '../../')),
                    # ~ 'copy_env': True,
                    # ~ 'pidfile': '{}/circus-aiida-{}'.format(path.dirname(path.abspath(__file__)), PROFILE_UUID),
                    # ~ 'autostart': True,
                    # ~ 'warmup_delay': 5
                # ~ }
            # ~ }
            click.echo('adding the watcher...')
            command = {
                'command': 'add',
                'properties': get_daemon_properties(profile)
            }
            click.echo(command)
            self._client.call(command)
            return self.start_watcher()
        elif not self.is_watcher_active(get_daemon_name(profile)):
            click.echo('starting the watcher...')
            return self.start_watcher(get_daemon_name(profile))
        return None

    def start_outstreamer(self, msg):
        if not streamer_name(msg) in self.list_watchers():
            streamer = get_streamer(msg)
            command = {
                'command': 'add',
                'properties': streamer,
            }
            self._client.call(command)
            return self.start_watcher(streamer_name(msg))
            self._client.call({
                'command': 'set',
                'properties': {
                    'name': streamer_name(msg),
                    'options': {'stdout_stream.filename': 'stream.log'}
                }
            })
        elif not self.is_watcher_active(streamer_name(msg)):
            return self.start_watcher(streamer_name(msg))

    def stop_aiida_daemon(self, profile):
        if get_daemon_name(profile) in self.list_watchers():
            return self._client.call({
                'command': 'stop',
                'properties': {
                    'name': get_daemon_name(profile)
                }
            })
        return None

    def start_watcher(self, name=None):
        response = self._client.call({
            'command': 'start',
            'properties': {
                'name': name
            }
        })

        return bool(response.get('status', None) == 'ok')

    def status(self, name=None):
        response = self._client.call({
            'command': 'status',
            'properties': {
                'name': name
            }
        })
        if response.get('status', None):
            return str(response['status'])

    def is_watcher_active(self, name):
        return bool(self.status(name) == 'active')

    def list_watchers(self):
        response = self._client.call({
            'command': 'list',
            'properties': {}
        })
        return [str(watcher) for watcher in response['watchers']] if response['status'] == u'ok' else []
Exemple #30
0
class TestTrainer(TestCircus):

    def setUp(self):
        super(TestTrainer, self).setUp()
        self.test_file = self._run_circus('circus.tests.test_trainer.run_dummy')
        time.sleep(0.5)
        self.cli = CircusClient(TEST_ENDPOINT)

    def tearDown(self):
        super(TestTrainer, self).tearDown()
        self.cli.stop()

    def test_numshows(self):
        resp = self.cli.call("numshows")
        self.assertEqual(resp, "1")

    def test_numflies(self):
        resp = self.cli.call("numflies")
        self.assertEqual(resp, "1")

    def test_flies(self):
        resp = self.cli.call("flies")
        self.assertEqual(resp, "test: 1")

    def test_shows(self):
        resp = self.cli.call("shows")
        self.assertEqual(resp, "test")

    def _get_cmd(self):
        fd, testfile = mkstemp()
        os.close(fd)
        cmd = '%s generic.py %s %s' % (sys.executable,
                        'circus.tests.test_trainer.run_dummy', testfile)

        return cmd

    def test_add_show(self):
        cmd = self._get_cmd()
        resp = self.cli.call("add_show test1 %s" % cmd)
        self.assertEqual(resp, "ok")

    def test_add_show1(self):
        cmd = self._get_cmd()
        self.cli.call("add_show test1 %s" % cmd)
        resp = self.cli.call("shows")
        self.assertTrue(resp.endswith("test1"))

    def test_add_show2(self):
        cmd = self._get_cmd()
        self.cli.call("add_show test1 %s" % cmd)
        resp = self.cli.call("numshows")
        self.assertEqual(resp, "2")

    def test_add_show3(self):
        cmd = self._get_cmd()
        self.cli.call("add_show test1 %s" % cmd)
        resp = self.cli.call("add_show test1 %s" % cmd)
        self.assertTrue(resp.startswith("error:"))

    def test_del_show(self):
        cmd = self._get_cmd()
        self.cli.call("add_show test1 %s" % cmd)
        self.cli.call("del_show test1")
        resp = self.cli.call("numshows")
        self.assertEqual(resp, "1")

    def test_stop(self):
        self.cli.call("stop")
        self.assertRaises(CallError, self.cli.call, "shows")

    def test_reload(self):
        resp = self.cli.call("reload")
        self.assertEqual(resp, "ok")


    def test_reload1(self):
        flies0 = self.cli.call("flies")
        resp = self.cli.call("reload")
        time.sleep(0.5)
        flies1 = self.cli.call("flies")
        self.assertNotEqual(flies0, flies1)

    def test_reload(self):
        self.cli.call("reload")
        time.sleep(0.5)
        flies = self.cli.call("flies")
        self.assertEqual(flies, "test: 2")

    def test_stop_shows(self):
        resp = self.cli.call("stop_shows")
        self.assertEqual(resp, "ok")

    def test_stop_shows1(self):
        self.cli.call("stop_shows")
        resp = self.cli.call("status test")
        self.assertEqual(resp, "stopped")
Exemple #31
0
class TestTrainer(TestCircus):
    def setUp(self):
        super(TestTrainer, self).setUp()
        dummy_process = 'circus.tests.test_arbiter.run_dummy'
        self.test_file = self._run_circus(dummy_process)
        self.cli = CircusClient()

    def tearDown(self):
        super(TestTrainer, self).tearDown()
        self.cli.stop()

    def test_numwatchers(self):
        msg = make_message("numwatchers")
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("numwatchers"), 1)

    def test_numprocesses(self):
        msg = make_message("numprocesses")
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("numprocesses"), 1)

    def test_processes(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        self.assertEqual(resp.get('processes'), [1])

        msg2 = make_message("incr", name="test")
        self.cli.call(msg2)

        resp = self.cli.call(msg1)
        self.assertEqual(resp.get('processes'), [1, 2])

    def test_watchers(self):
        resp = self.cli.call(make_message("list"))
        self.assertEqual(resp.get('watchers'), ["test"])

    def _get_cmd(self):
        fd, testfile = mkstemp()
        os.close(fd)
        cmd = '%s generic.py %s %s' % (
            sys.executable, 'circus.tests.test_arbiter.run_dummy', testfile)

        return cmd

    def _get_cmd_args(self):
        cmd = sys.executable
        args = ['generic.py', 'circus.tests.test_arbiter.run_dummy1']
        return cmd, args

    def test_add_watcher(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

    def test_add_watcher1(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        resp = self.cli.call(make_message("list"))
        self.assertEqual(resp.get('watchers'), ["test", "test1"])

    def test_add_watcher2(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        resp = self.cli.call(make_message("numwatchers"))
        self.assertEqual(resp.get("numwatchers"), 2)

    def test_add_watcher3(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        resp = self.cli.call(msg)
        self.assertTrue(resp.get('status'), 'error')

    def test_add_watcher4(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

    def test_add_watcher5(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("start", name="test1"))
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

    def test_add_watcher6(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args, start=True)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

    def test_add_watcher7(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add",
                           name="test1",
                           cmd=cmd,
                           args=args,
                           start=True,
                           options={"flapping_window": 100})
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

        resp = self.cli.call(make_message("options", name="test1"))
        options = resp.get('options', {})
        self.assertEqual(options.get("flapping_window"), 100)

    def test_rm_watcher(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        msg = make_message("rm", name="test1")
        self.cli.call(msg)
        resp = self.cli.call(make_message("numwatchers"))
        self.assertEqual(resp.get("numwatchers"), 1)

    def test_stop(self):
        resp = self.cli.call(make_message("quit"))
        self.assertEqual(resp.get("status"), "ok")
        self.assertRaises(CallError, self.cli.call, make_message("list"))

    def test_reload(self):
        resp = self.cli.call(make_message("reload"))
        self.assertEqual(resp.get("status"), "ok")

    def test_reload1(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        processes1 = resp.get('processes')

        self.cli.call(make_message("reload"))
        time.sleep(0.5)

        msg2 = make_message("list", name="test")
        resp = self.cli.call(msg2)
        processes2 = resp.get('processes')

        self.assertNotEqual(processes1, processes2)

    def test_reload2(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        processes1 = resp.get('processes')
        self.assertEqual(processes1, [1])

        self.cli.call(make_message("reload"))
        time.sleep(0.5)

        make_message("list", name="test")
        resp = self.cli.call(msg1)

        processes2 = resp.get('processes')
        self.assertEqual(processes2, [2])

    def test_stop_watchers(self):
        resp = self.cli.call(make_message("stop"))
        self.assertEqual(resp.get("status"), "ok")

    def test_stop_watchers1(self):
        self.cli.call(make_message("stop"))
        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get("status"), "stopped")

    def test_stop_watchers2(self):
        self.cli.call(make_message("stop", name="test"))
        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get('status'), "stopped")

    def test_stop_watchers3(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("start", name="test1"))
        self.assertEqual(resp.get("status"), "ok")

        self.cli.call(make_message("stop", name="test1"))
        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get('status'), "stopped")

        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get('status'), "active")
Exemple #32
0
class TestTrainer(TestCircus):

    def setUp(self):
        super(TestTrainer, self).setUp()
        dummy_process = 'circus.tests.support.run_process'
        self.test_file = self._run_circus(dummy_process)
        self.cli = CircusClient()

    def tearDown(self):
        super(TestTrainer, self).tearDown()
        self.cli.stop()

    def test_numwatchers(self):
        msg = make_message("numwatchers")
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("numwatchers"), 1)

    def test_numprocesses(self):
        msg = make_message("numprocesses")
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("numprocesses"), 1)

    def test_processes(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        self.assertEqual(len(resp.get('pids')), 1)

        msg2 = make_message("incr", name="test")
        self.cli.call(msg2)

        resp = self.cli.call(msg1)
        self.assertEqual(len(resp.get('pids')), 2)

        self.cli.send_message("incr", name="test", nb=2)
        resp = self.cli.call(msg1)
        self.assertEqual(len(resp.get('pids')), 4)

    def test_watchers(self):
        resp = self.cli.call(make_message("list"))
        self.assertEqual(resp.get('watchers'), ["test"])

    def _get_cmd(self):
        fd, testfile = mkstemp()
        os.close(fd)
        cmd = '%s generic.py %s %s' % (
            sys.executable,
            'circus.tests.support.run_process',
            testfile)

        return cmd

    def _get_cmd_args(self):
        cmd = sys.executable
        args = ['generic.py', 'circus.tests.support.run_process']
        return cmd, args

    def _get_options(self, **kwargs):
        if 'graceful_timeout' not in kwargs:
            kwargs['graceful_timeout'] = 4
        return kwargs

    def test_add_watcher(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd(),
                           options=self._get_options())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

    def test_add_watcher1(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd(),
                           options=self._get_options())
        self.cli.call(msg)
        resp = self.cli.call(make_message("list"))
        self.assertEqual(resp.get('watchers'), ["test", "test1"])

    def test_add_watcher2(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd(),
                           options=self._get_options())
        self.cli.call(msg)
        resp = self.cli.call(make_message("numwatchers"))
        self.assertEqual(resp.get("numwatchers"), 2)

    def test_add_watcher3(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd(),
                           options=self._get_options())
        self.cli.call(msg)
        resp = self.cli.call(msg)
        self.assertTrue(resp.get('status'), 'error')

    def test_add_watcher4(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args,
                           options=self._get_options())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

    def test_add_watcher5(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args,
                           options=self._get_options())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("start", name="test1"))
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

    def test_add_watcher6(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args,
                           start=True, options=self._get_options())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

    def test_add_watcher7(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args, start=True,
                           options=self._get_options(flapping_window=100))
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

        resp = self.cli.call(make_message("options", name="test1"))
        options = resp.get('options', {})
        self.assertEqual(options.get("flapping_window"), 100)

    def test_rm_watcher(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd(),
                           options=self._get_options())
        self.cli.call(msg)
        msg = make_message("rm", name="test1")
        self.cli.call(msg)
        resp = self.cli.call(make_message("numwatchers"))
        self.assertEqual(resp.get("numwatchers"), 1)

    def test_stop(self):
        resp = self.cli.call(make_message("quit"))
        self.assertEqual(resp.get("status"), "ok")
        self.assertRaises(CallError, self.cli.call, make_message("list"))

    def test_reload(self):
        resp = self.cli.call(make_message("reload"))
        self.assertEqual(resp.get("status"), "ok")

    def test_reload1(self):
        self.assertTrue(poll_for(self.test_file, 'START'))  # process started
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        processes1 = resp.get('pids')

        truncate_file(self.test_file)  # clean slate
        self.cli.call(make_message("reload"))
        self.assertTrue(poll_for(self.test_file, 'START'))  # restarted

        msg2 = make_message("list", name="test")
        resp = self.cli.call(msg2)
        processes2 = resp.get('pids')

        self.assertNotEqual(processes1, processes2)

    def test_reload2(self):
        self.assertTrue(poll_for(self.test_file, 'START'))  # process started
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        processes1 = resp.get('pids')
        self.assertEqual(len(processes1), 1)

        truncate_file(self.test_file)  # clean slate
        self.cli.call(make_message("reload"))
        self.assertTrue(poll_for(self.test_file, 'START'))  # restarted

        make_message("list", name="test")
        resp = self.cli.call(msg1)

        processes2 = resp.get('pids')
        self.assertEqual(len(processes2), 1)
        self.assertNotEqual(processes1[0], processes2[0])

    def test_stop_watchers(self):
        resp = self.cli.call(make_message("stop"))
        self.assertEqual(resp.get("status"), "ok")

    def test_stop_watchers1(self):
        self.cli.call(make_message("stop"))
        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get("status"), "stopped")

    def test_stop_watchers2(self):
        self.cli.call(make_message("stop", name="test"))
        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get('status'), "stopped")

    def test_stop_watchers3(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args,
                           options=self._get_options())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("start", name="test1"))
        self.assertEqual(resp.get("status"), "ok")

        self.cli.call(make_message("stop", name="test1"))
        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get('status'), "stopped")

        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get('status'), "active")

    def test_plugins(self):
        # killing the setUp runner
        self._stop_runners()
        self.cli.stop()

        fd, datafile = mkstemp()
        os.close(fd)

        # setting up a circusd with a plugin
        dummy_process = 'circus.tests.support.run_process'
        plugin = 'circus.tests.test_arbiter.Plugin'
        plugins = [{'use': plugin, 'file': datafile}]
        self._run_circus(dummy_process, plugins=plugins)

        # doing a few operations
        def nb_processes():
            return len(cli.send_message('list', name='test').get('pids'))

        def incr_processes():
            return cli.send_message('incr', name='test')

        # wait for the plugin to be started
        self.assertTrue(poll_for(datafile, 'PLUGIN STARTED'))

        cli = CircusClient()
        self.assertEqual(nb_processes(), 1)
        incr_processes()
        self.assertEqual(nb_processes(), 2)
        # wait for the plugin to receive the signal
        self.assertTrue(poll_for(datafile, 'test:spawn'))
        truncate_file(datafile)
        incr_processes()
        self.assertEqual(nb_processes(), 3)
        # wait for the plugin to receive the signal
        self.assertTrue(poll_for(datafile, 'test:spawn'))

    def test_singleton(self):
        self._stop_runners()

        dummy_process = 'circus.tests.support.run_process'
        self._run_circus(dummy_process, singleton=True)
        cli = CircusClient()

        # adding more than one process should fail
        res = cli.send_message('incr', name='test')
        self.assertEqual(res['numprocesses'], 1)
Exemple #33
0
class TestCircus(unittest.TestCase):

    arbiter_factory = get_arbiter

    def setUp(self):
        self.arbiters = []
        self.files = []
        self.dirs = []
        self.tmpfiles = []
        self.cli = CircusClient()

    def tearDown(self):
        self._stop_runners()
        for file in self.files + self.tmpfiles:
            if os.path.exists(file):
                os.remove(file)

        for dir in self.dirs:
            shutil.rmtree(dir)

        self.cli.stop()

    def get_tmpdir(self):
        dir_ = mkdtemp()
        self.dirs.append(dir_)
        return dir_

    def get_tmpfile(self, content=None):
        fd, file = mkstemp()
        os.close(fd)
        self.tmpfiles.append(file)
        if content is not None:
            with open(file, 'w') as f:
                f.write(content)
        return file

    @classmethod
    def _create_circus(cls, callable, plugins=None, stats=False, **kw):
        resolve_name(callable)   # used to check the callable
        fd, testfile = mkstemp()
        os.close(fd)
        wdir = os.path.dirname(__file__)
        args = ['generic.py', callable, testfile]
        worker = {'cmd': _CMD, 'args': args, 'working_dir': wdir,
                  'name': 'test', 'graceful_timeout': 2}
        worker.update(kw)
        debug = kw.get('debug', False)

        fact = cls.arbiter_factory
        if stats:
            arbiter = fact([worker], background=True, plugins=plugins,
                           stats_endpoint=DEFAULT_ENDPOINT_STATS,
                           statsd=True,
                           debug=debug, statsd_close_outputs=not debug)
        else:
            arbiter = fact([worker], background=True, plugins=plugins,
                           debug=debug)
        arbiter.start()
        return testfile, arbiter

    def _run_circus(self, callable, plugins=None, stats=False, **kw):

        testfile, arbiter = TestCircus._create_circus(callable, plugins, stats,
                                                      **kw)
        self.arbiters.append(arbiter)
        self.files.append(testfile)
        return testfile

    def _stop_runners(self):
        for arbiter in self.arbiters:
            arbiter.stop()
        self.arbiters = []

    def call(self, cmd, **props):
        msg = make_message(cmd, **props)
        return self.cli.call(msg)
class LiveClient(object):
    def __init__(self, endpoint, ssh_server=None):
        self.endpoint = str(endpoint)
        self.stats_endpoint = None
        self.client = CircusClient(endpoint=self.endpoint,
                                   ssh_server=ssh_server)
        self.connected = False
        self.watchers = []
        self.plugins = []
        self.stats = defaultdict(list)
        self.dstats = []
        self.sockets = None
        self.use_sockets = False
        self.embed_httpd = False

    def stop(self):
        self.client.stop()

    def update_watchers(self):
        """Calls circus and initialize the list of watchers.

        If circus is not connected raises an error.
        """
        self.watchers = []
        self.plugins = []

        # trying to list the watchers
        try:
            self.connected = True
            for watcher in self.client.send_message('list')['watchers']:
                if watcher in ('circusd-stats', 'circushttpd'):
                    if watcher == 'circushttpd':
                        self.embed_httpd = True
                    continue

                options = self.client.send_message('options',
                                                   name=watcher)['options']
                self.watchers.append((watcher, options))
                if watcher.startswith('plugin:'):
                    self.plugins.append(watcher)

                if not self.use_sockets and options.get('use_sockets', False):
                    self.use_sockets = True

            self.watchers.sort()
            self.stats_endpoint = self.get_global_options()['stats_endpoint']
            if self.endpoint.startswith('tcp://'):
                # In case of multi interface binding i.e: tcp://0.0.0.0:5557
                anyaddr = '0.0.0.0'
                ip = self.endpoint.lstrip('tcp://').split(':')[0]
                self.stats_endpoint = self.stats_endpoint.replace(anyaddr, ip)
        except CallError:
            self.connected = False

    def killproc(self, name, pid):
        # killing a proc and its children
        res = self.client.send_message('signal', name=name, pid=int(pid),
                                       signum=9, recursive=True)
        self.update_watchers()  # will do better later
        return res

    def get_option(self, name, option):
        watchers = dict(self.watchers)
        return watchers[name][option]

    def get_global_options(self):
        return self.client.send_message('globaloptions')['options']

    def get_options(self, name):
        watchers = dict(self.watchers)
        return watchers[name].items()

    def incrproc(self, name):
        res = self.client.send_message('incr', name=name)
        self.update_watchers()  # will do better later
        return res

    def decrproc(self, name):
        res = self.client.send_message('decr', name=name)
        self.update_watchers()  # will do better later
        return res

    def get_stats(self, name, start=0, end=-1):
        return self.stats[name][start:end]

    def get_dstats(self, field, start=0, end=-1):
        stats = self.dstats[start:end]
        res = []
        for stat in stats:
            res.append(stat[field])
        return res

    def get_pids(self, name):
        res = self.client.send_message('list', name=name)
        return res['pids']

    def get_sockets(self, force_reload=False):
        if not self.sockets or force_reload:
            res = self.client.send_message('listsockets')
            self.sockets = res['sockets']
        return self.sockets

    def get_series(self, name, pid, field, start=0, end=-1):
        stats = self.get_stats(name, start, end)
        res = []
        for stat in stats:
            pids = stat['pid']
            if isinstance(pids, list):
                continue
            if str(pid) == str(stat['pid']):
                res.append(stat[field])
        return res

    def get_status(self, name):
        return self.client.send_message('status', name=name)['status']

    def switch_status(self, name):
        msg = cmds['status'].make_message(name=name)
        res = self.client.call(msg)
        status = res['status']
        if status == 'active':
            # stopping the watcher
            msg = cmds['stop'].make_message(name=name)
        else:
            msg = cmds['start'].make_message(name=name)
        res = self.client.call(msg)
        return res

    def add_watcher(self, name, cmd, **kw):
        res = self.client.send_message('add', name=name, cmd=cmd)
        if res['status'] == 'ok':
            # now configuring the options
            options = {}
            options['numprocesses'] = int(kw.get('numprocesses', '5'))
            options['working_dir'] = kw.get('working_dir')
            options['shell'] = kw.get('shell', 'off') == 'on'
            res = self.client.send_message('set', name=name, options=options)
            self.update_watchers()  # will do better later
        return res
Exemple #35
0
class TestTrainer(TestCircus):
    def setUp(self):
        super(TestTrainer, self).setUp()
        dummy_process = "circus.tests.test_arbiter.run_dummy"
        self.test_file = self._run_circus(dummy_process)
        self.cli = CircusClient()

    def tearDown(self):
        super(TestTrainer, self).tearDown()
        self.cli.stop()

    def test_numwatchers(self):
        msg = make_message("numwatchers")
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("numwatchers"), 1)

    def test_numprocesses(self):
        msg = make_message("numprocesses")
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("numprocesses"), 1)

    def test_processes(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        self.assertEqual(resp.get("processes"), [1])

        msg2 = make_message("incr", name="test")
        self.cli.call(msg2)

        resp = self.cli.call(msg1)
        self.assertEqual(resp.get("processes"), [1, 2])

    def test_watchers(self):
        resp = self.cli.call(make_message("list"))
        self.assertEqual(resp.get("watchers"), ["test"])

    def _get_cmd(self):
        fd, testfile = mkstemp()
        os.close(fd)
        cmd = "%s generic.py %s %s" % (sys.executable, "circus.tests.test_arbiter.run_dummy", testfile)

        return cmd

    def _get_cmd_args(self):
        cmd = sys.executable
        args = ["generic.py", "circus.tests.test_arbiter.run_dummy1"]
        return cmd, args

    def test_add_watcher(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

    def test_add_watcher1(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        resp = self.cli.call(make_message("list"))
        self.assertEqual(resp.get("watchers"), ["test", "test1"])

    def test_add_watcher2(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        resp = self.cli.call(make_message("numwatchers"))
        self.assertEqual(resp.get("numwatchers"), 2)

    def test_add_watcher3(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        resp = self.cli.call(msg)
        self.assertTrue(resp.get("status"), "error")

    def test_add_watcher4(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

    def test_add_watcher5(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("start", name="test1"))
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

    def test_add_watcher6(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args, start=True)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

    def test_add_watcher7(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args, start=True, options={"flapping_window": 100})
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

        resp = self.cli.call(make_message("options", name="test1"))
        options = resp.get("options", {})
        self.assertEqual(options.get("flapping_window"), 100)

    def test_rm_watcher(self):
        msg = make_message("add", name="test1", cmd=self._get_cmd())
        self.cli.call(msg)
        msg = make_message("rm", name="test1")
        self.cli.call(msg)
        resp = self.cli.call(make_message("numwatchers"))
        self.assertEqual(resp.get("numwatchers"), 1)

    def test_stop(self):
        resp = self.cli.call(make_message("quit"))
        self.assertEqual(resp.get("status"), "ok")
        self.assertRaises(CallError, self.cli.call, make_message("list"))

    def test_reload(self):
        resp = self.cli.call(make_message("reload"))
        self.assertEqual(resp.get("status"), "ok")

    def test_reload1(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        processes1 = resp.get("processes")

        self.cli.call(make_message("reload"))
        time.sleep(0.5)

        msg2 = make_message("list", name="test")
        resp = self.cli.call(msg2)
        processes2 = resp.get("processes")

        self.assertNotEqual(processes1, processes2)

    def test_reload2(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        processes1 = resp.get("processes")
        self.assertEqual(processes1, [1])

        self.cli.call(make_message("reload"))
        time.sleep(0.5)

        make_message("list", name="test")
        resp = self.cli.call(msg1)

        processes2 = resp.get("processes")
        self.assertEqual(processes2, [2])

    def test_stop_watchers(self):
        resp = self.cli.call(make_message("stop"))
        self.assertEqual(resp.get("status"), "ok")

    def test_stop_watchers1(self):
        self.cli.call(make_message("stop"))
        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get("status"), "stopped")

    def test_stop_watchers2(self):
        self.cli.call(make_message("stop", name="test"))
        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get("status"), "stopped")

    def test_stop_watchers3(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add", name="test1", cmd=cmd, args=args)
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("start", name="test1"))
        self.assertEqual(resp.get("status"), "ok")

        self.cli.call(make_message("stop", name="test1"))
        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "stopped")

        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get("status"), "active")

    def test_plugins(self):
        # killing the setUp runner
        self._stop_runners()
        self.cli.stop()

        fd, datafile = mkstemp()
        os.close(fd)

        # setting up a circusd with a plugin
        dummy_process = "circus.tests.test_arbiter.run_dummy"
        plugin = "circus.tests.test_arbiter.Plugin"
        plugins = [{"use": plugin, "file": datafile}]
        self._run_circus(dummy_process, plugins=plugins)

        # doing a few operations
        cli = CircusClient()
        msg1 = make_message("list", name="test")
        resp = cli.call(msg1)
        self.assertEqual(resp.get("processes"), [1])
        msg2 = make_message("incr", name="test")
        cli.call(msg2)
        resp = cli.call(msg1)
        self.assertEqual(resp.get("processes"), [1, 2])
        cli.call(msg2)
        resp = cli.call(msg1)
        self.assertEqual(resp.get("processes"), [1, 2, 3])

        # wait a bit
        time.sleep(0.2)

        # checking what the plugin did
        with open(datafile) as f:
            data = [line for line in f.read().split("\n") if line != ""]

        wanted = ["test:spawn", "test:spawn"]
        self.assertEqual(data, wanted)

    def test_singleton(self):
        self._stop_runners()

        dummy_process = "circus.tests.test_arbiter.run_dummy"
        self._run_circus(dummy_process, singleton=True)
        cli = CircusClient()

        # adding more than one process should fail
        res = cli.send_message("incr", name="test")
        self.assertEqual(res["numprocesses"], 1)
Exemple #36
0
class LiveClient(object):
    def __init__(self, endpoint):
        self.endpoint = str(endpoint)
        self.stats_endpoint = None
        self.client = CircusClient(endpoint=self.endpoint)
        self.connected = False
        self.watchers = []
        self.plugins = []
        self.stats = defaultdict(list)
        self.dstats = []
        self.sockets = None
        self.use_sockets = False
        self.embed_httpd = False

    def stop(self):
        self.client.stop()

    def update_watchers(self):
        """Calls circus and initialize the list of watchers.

        If circus is not connected raises an error.
        """
        self.watchers = []
        # trying to list the watchers
        try:
            self.connected = True
            for watcher in self.client.send_message('list')['watchers']:
                if watcher in ('circusd-stats', 'circushttpd'):
                    if watcher == 'circushttpd':
                        self.embed_httpd = True
                    continue

                options = self.client.send_message('options',
                                                   name=watcher)['options']
                self.watchers.append((watcher, options))
                if watcher.startswith('plugin:'):
                    self.plugins.append(watcher)

                if not self.use_sockets and options.get('use_sockets', False):
                    self.use_sockets = True

            self.watchers.sort()
            self.stats_endpoint = self.get_global_options()['stats_endpoint']
        except CallError:
            self.connected = False

    def killproc(self, name, pid):
        res = self.client.send_message('signal', name=name, pid=int(pid),
                                       signum=9, children=True)
        self.update_watchers()  # will do better later
        return res

    def get_option(self, name, option):
        watchers = dict(self.watchers)
        return watchers[name][option]

    def get_global_options(self):
        return self.client.send_message('globaloptions')['options']

    def get_options(self, name):
        watchers = dict(self.watchers)
        return watchers[name].items()

    def incrproc(self, name):
        res = self.client.send_message('incr', name=name)
        self.update_watchers()  # will do better later
        return res

    def decrproc(self, name):
        res = self.client.send_message('decr', name=name)
        self.update_watchers()  # will do better later
        return res

    def get_stats(self, name, start=0, end=-1):
        return self.stats[name][start:end]

    def get_dstats(self, field, start=0, end=-1):
        stats = self.dstats[start:end]
        res = []
        for stat in stats:
            res.append(stat[field])
        return res

    def get_pids(self, name):
        res = self.client.send_message('list', name=name)
        return res['pids']

    def get_sockets(self, force_reload=False):
        if not self.sockets or force_reload:
            res = self.client.send_message('listsockets')
            self.sockets = res['sockets']
        return self.sockets

    def get_series(self, name, pid, field, start=0, end=-1):
        stats = self.get_stats(name, start, end)
        res = []
        for stat in stats:
            pids = stat['pid']
            if isinstance(pids, list):
                continue
            if str(pid) == str(stat['pid']):
                res.append(stat[field])
        return res

    def get_status(self, name):
        return self.client.send_message('status', name=name)['status']

    def switch_status(self, name):
        msg = cmds['status'].make_message(name=name)
        res = self.client.call(msg)
        status = res['status']
        if status == 'active':
            # stopping the watcher
            msg = cmds['stop'].make_message(name=name)
        else:
            msg = cmds['start'].make_message(name=name)
        res = self.client.call(msg)
        return res

    def add_watcher(self, name, cmd, **kw):
        res = self.client.send_message('add', name=name, cmd=cmd)
        if res['status'] == 'ok':
            # now configuring the options
            options = {}
            options['numprocesses'] = int(kw.get('numprocesses', '5'))
            options['working_dir'] = kw.get('working_dir')
            options['shell'] = kw.get('shell', 'off') == 'on'
            res = self.client.send_message('set', name=name, options=options)
            self.update_watchers()  # will do better later
        return res
Exemple #37
0
class TestTrainer(TestCircus):
    def setUp(self):
        super(TestTrainer, self).setUp()
        dummy_process = 'circus.tests.test_arbiter.run_dummy'
        self.test_file = self._run_circus(dummy_process)
        self.cli = CircusClient()

    def tearDown(self):
        super(TestTrainer, self).tearDown()
        self.cli.stop()

    def test_numwatchers(self):
        msg = make_message("numwatchers")
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("numwatchers"), 1)

    def test_numprocesses(self):
        msg = make_message("numprocesses")
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("numprocesses"), 1)

    def test_processes(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        self.assertEqual(len(resp.get('pids')), 1)

        msg2 = make_message("incr", name="test")
        self.cli.call(msg2)

        resp = self.cli.call(msg1)
        self.assertEqual(len(resp.get('pids')), 2)

        self.cli.send_message("incr", name="test", nb=2)
        resp = self.cli.call(msg1)
        self.assertEqual(len(resp.get('pids')), 4)

    def test_watchers(self):
        resp = self.cli.call(make_message("list"))
        self.assertEqual(resp.get('watchers'), ["test"])

    def _get_cmd(self):
        fd, testfile = mkstemp()
        os.close(fd)
        cmd = '%s generic.py %s %s' % (
            sys.executable, 'circus.tests.test_arbiter.run_dummy', testfile)

        return cmd

    def _get_cmd_args(self):
        cmd = sys.executable
        args = ['generic.py', 'circus.tests.test_arbiter.run_dummy1']
        return cmd, args

    def _get_options(self, **kwargs):
        if 'graceful_timeout' not in kwargs:
            kwargs['graceful_timeout'] = 4
        return kwargs

    def test_add_watcher(self):
        msg = make_message("add",
                           name="test1",
                           cmd=self._get_cmd(),
                           options=self._get_options())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

    def test_add_watcher1(self):
        msg = make_message("add",
                           name="test1",
                           cmd=self._get_cmd(),
                           options=self._get_options())
        self.cli.call(msg)
        resp = self.cli.call(make_message("list"))
        self.assertEqual(resp.get('watchers'), ["test", "test1"])

    def test_add_watcher2(self):
        msg = make_message("add",
                           name="test1",
                           cmd=self._get_cmd(),
                           options=self._get_options())
        self.cli.call(msg)
        resp = self.cli.call(make_message("numwatchers"))
        self.assertEqual(resp.get("numwatchers"), 2)

    def test_add_watcher3(self):
        msg = make_message("add",
                           name="test1",
                           cmd=self._get_cmd(),
                           options=self._get_options())
        self.cli.call(msg)
        resp = self.cli.call(msg)
        self.assertTrue(resp.get('status'), 'error')

    def test_add_watcher4(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add",
                           name="test1",
                           cmd=cmd,
                           args=args,
                           options=self._get_options())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

    def test_add_watcher5(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add",
                           name="test1",
                           cmd=cmd,
                           args=args,
                           options=self._get_options())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("start", name="test1"))
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

    def test_add_watcher6(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add",
                           name="test1",
                           cmd=cmd,
                           args=args,
                           start=True,
                           options=self._get_options())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

    def test_add_watcher7(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add",
                           name="test1",
                           cmd=cmd,
                           args=args,
                           start=True,
                           options=self._get_options(flapping_window=100))
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")

        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get("status"), "active")

        resp = self.cli.call(make_message("options", name="test1"))
        options = resp.get('options', {})
        self.assertEqual(options.get("flapping_window"), 100)

    def test_rm_watcher(self):
        msg = make_message("add",
                           name="test1",
                           cmd=self._get_cmd(),
                           options=self._get_options())
        self.cli.call(msg)
        msg = make_message("rm", name="test1")
        self.cli.call(msg)
        resp = self.cli.call(make_message("numwatchers"))
        self.assertEqual(resp.get("numwatchers"), 1)

    def test_stop(self):
        resp = self.cli.call(make_message("quit"))
        self.assertEqual(resp.get("status"), "ok")
        self.assertRaises(CallError, self.cli.call, make_message("list"))

    def test_reload(self):
        resp = self.cli.call(make_message("reload"))
        self.assertEqual(resp.get("status"), "ok")

    def test_reload1(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        processes1 = resp.get('pids')

        self.cli.call(make_message("reload"))
        time.sleep(0.5)

        msg2 = make_message("list", name="test")
        resp = self.cli.call(msg2)
        processes2 = resp.get('pids')

        self.assertNotEqual(processes1, processes2)

    def test_reload2(self):
        msg1 = make_message("list", name="test")
        resp = self.cli.call(msg1)
        processes1 = resp.get('pids')
        self.assertEqual(len(processes1), 1)

        self.cli.call(make_message("reload"))
        time.sleep(0.5)

        make_message("list", name="test")
        resp = self.cli.call(msg1)

        processes2 = resp.get('pids')
        self.assertEqual(len(processes2), 1)
        self.assertNotEqual(processes1[0], processes2[0])

    def test_stop_watchers(self):
        resp = self.cli.call(make_message("stop"))
        self.assertEqual(resp.get("status"), "ok")

    def test_stop_watchers1(self):
        self.cli.call(make_message("stop"))
        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get("status"), "stopped")

    def test_stop_watchers2(self):
        self.cli.call(make_message("stop", name="test"))
        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get('status'), "stopped")

    def test_stop_watchers3(self):
        cmd, args = self._get_cmd_args()
        msg = make_message("add",
                           name="test1",
                           cmd=cmd,
                           args=args,
                           options=self._get_options())
        resp = self.cli.call(msg)
        self.assertEqual(resp.get("status"), "ok")
        resp = self.cli.call(make_message("start", name="test1"))
        self.assertEqual(resp.get("status"), "ok")

        self.cli.call(make_message("stop", name="test1"))
        resp = self.cli.call(make_message("status", name="test1"))
        self.assertEqual(resp.get('status'), "stopped")

        resp = self.cli.call(make_message("status", name="test"))
        self.assertEqual(resp.get('status'), "active")

    def test_plugins(self):
        # killing the setUp runner
        self._stop_runners()
        self.cli.stop()

        fd, datafile = mkstemp()
        os.close(fd)

        # setting up a circusd with a plugin
        dummy_process = 'circus.tests.test_arbiter.run_dummy'
        plugin = 'circus.tests.test_arbiter.Plugin'
        plugins = [{'use': plugin, 'file': datafile}]
        self._run_circus(dummy_process, plugins=plugins)

        # doing a few operations
        def nb_processes():
            return len(cli.send_message('list', name='test').get('pids'))

        def incr_processes():
            return cli.send_message('incr', name='test')

        cli = CircusClient()
        self.assertEqual(nb_processes(), 1)
        incr_processes()
        self.assertEqual(nb_processes(), 2)
        incr_processes()
        self.assertEqual(nb_processes(), 3)

        # wait a bit
        time.sleep(.2)

        # checking what the plugin did
        with open(datafile) as f:
            data = [line for line in f.read().split('\n') if line != '']

        wanted = ['test:spawn', 'test:spawn']
        self.assertEqual(data, wanted)

    def test_singleton(self):
        self._stop_runners()

        dummy_process = 'circus.tests.test_arbiter.run_dummy'
        self._run_circus(dummy_process, singleton=True)
        cli = CircusClient()

        # adding more than one process should fail
        res = cli.send_message('incr', name='test')
        self.assertEqual(res['numprocesses'], 1)
Exemple #38
0
class DaemonTamer(object):
    _DAEMON_MAP_FILE = 'daemon_map.yaml'
    _ENDPOINT_TPL = '{host}:{port}'

    def __init__(self, profile):
        self.profile = profile
        self.daemon_name = get_daemon_name(profile)
        self.config = self.get_update_profile()
        self._client = CircusClient()  # endpoint=self.endpoint)

    def generate_new_portnum(self, config=None):
        port = 6000
        used_ports = [profile['port'] for profile in config.values()]
        while port in used_ports:
            port += 2
        return port

    def read_config(self):
        if not path.isfile(self._DAEMON_MAP_FILE):
            return {}
        with open(self._DAEMON_MAP_FILE, 'r') as daemon_map_fo:
            config = yaml.load(daemon_map_fo) or {}
        return config

    def write_config(self, config):
        with open(self._DAEMON_MAP_FILE, 'w') as daemon_map_fo:
            yaml.dump(config, daemon_map_fo)

    def get_update_profile(self):
        config = self.read_config()
        profile_config = config.get(self.profile, {})
        profile_config['uuid'] = get_profile_uuid(self.profile)
        profile_config['host'] = profile_config.get('host', 'tcp://127.0.0.1')
        profile_config['port'] = profile_config.get('port', self.generate_new_portnum(config))
        config[self.profile] = profile_config
        self.write_config(config)
        return config

    @property
    def profile_config(self):
        return self.config[self.profile]

    @property
    def endpoint(self):
        return self._ENDPOINT_TPL.format(host=self.profile_config['host'], port=self.profile_config['port'])

    @property
    def pubsub_endpoint(self):
        return self._ENDPOINT_TPL.format(host=self.profile_config['host'], port=self.profile_config['port'] + 1)

    @property
    def stats_endpoint(self):
        return self._ENDPOINT_TPL.format(host=self.profile_config['host'], port=self.profile_config['port'] + 2)

    @property
    def arbiter_config(self):
        return {
            'logoutput': 'aiida-circus.log',
            'loglevel': 'INFO',
            'debug': False,
            'statsd': True,
            # ~ 'controller': self.endpoint,
            # ~ 'pubsub_endpoint': self.pubsub_endpoint,
            # ~ 'stats_endpoint': self.stats_endpoint
        }

    @property
    def watcher_config(self):
        return get_daemon_properties(self.profile)

    def make_arbiter(self):
        print self.arbiter_config
        print self.watcher_config
        return get_arbiter([self.watcher_config], **self.arbiter_config)

    def pause_daemon(self):
        self._client.stop()

    def unpause_daemon(self):
        self._client.call({
            'command': 'start',
            'properties': {}
        })

    def status(self):
        response = self._client.call({
            'command': 'status',
            'properties': {
                'name': self.daemon_name
            }
        })
        if response.get('status', None):
            return str(response['status'])

    def quit(self):
        try:
            self._client.call({
                'command': 'quit',
                'properties': {}
            })
        except CallError:
            pass