Пример #1
0
class TestAuthViaSentinel(TestCase):
    master_port = 36379
    sentinel_port = 46379

    def setUp(self):
        self.fake_master = FakeAuthenticatedRedisFactory('secret!')
        self.master_listener = reactor.listenTCP(self.master_port,
                                                 self.fake_master)

        self.fake_sentinel = FakeSentinelFactory()
        self.fake_sentinel.master_addr = ("127.0.0.1", self.master_port)
        self.fake_sentinel.slave_addrs = []
        self.fake_sentinel.slave_flags = []
        self.sentinel_listener = reactor.listenTCP(self.sentinel_port,
                                                   self.fake_sentinel)

        self.client = Sentinel([("127.0.0.1", self.sentinel_port)])
        self.client.discovery_timeout = 1

    @defer.inlineCallbacks
    def tearDown(self):
        yield self.client.disconnect()
        self.sentinel_listener.stopListening()
        self.master_listener.stopListening()

    @defer.inlineCallbacks
    def test_auth(self):
        conn = self.client.master_for("test", password='******')
        reply = yield conn.role()
        self.assertEqual(reply[0], "master")
        yield conn.disconnect()
Пример #2
0
class TestAuthViaSentinel(TestCase):
    master_port = 36379
    sentinel_port = 46379

    def setUp(self):
        self.fake_master = FakeAuthenticatedRedisFactory('secret!')
        self.master_listener = reactor.listenTCP(self.master_port, self.fake_master)

        self.fake_sentinel = FakeSentinelFactory()
        self.fake_sentinel.master_addr = ("127.0.0.1", self.master_port)
        self.fake_sentinel.slave_addrs = []
        self.fake_sentinel.slave_flags = []
        self.sentinel_listener = reactor.listenTCP(self.sentinel_port, self.fake_sentinel)

        self.client = Sentinel([("127.0.0.1", self.sentinel_port)])
        self.client.discovery_timeout = 1

    @defer.inlineCallbacks
    def tearDown(self):
        yield self.client.disconnect()
        self.sentinel_listener.stopListening()
        self.master_listener.stopListening()


    @defer.inlineCallbacks
    def test_auth(self):
        conn = self.client.master_for("test", password='******')
        reply = yield conn.role()
        self.assertEqual(reply[0], "master")
        yield conn.disconnect()
Пример #3
0
class TestConnectViaSentinel(TestCase):

    master_port = 36379
    slave_port = 36380
    sentinel_port = 46379

    def setUp(self):
        self.fake_master = FakeRedisFactory()
        self.master_listener = reactor.listenTCP(self.master_port,
                                                 self.fake_master)
        self.fake_slave = FakeRedisFactory()
        self.fake_slave.role = [
            "slave", "127.0.0.1", self.master_port, "connected", 0
        ]
        self.slave_listener = reactor.listenTCP(self.slave_port,
                                                self.fake_slave)

        self.fake_sentinel = FakeSentinelFactory()
        self.fake_sentinel.master_addr = ("127.0.0.1", self.master_port)
        self.fake_sentinel.slave_addrs = [("127.0.0.1", self.slave_port)]
        self.fake_sentinel.slave_flags = ["slave"]
        self.sentinel_listener = reactor.listenTCP(self.sentinel_port,
                                                   self.fake_sentinel)

        self.client = Sentinel([("127.0.0.1", self.sentinel_port)])
        self.client.discovery_timeout = 1

    @defer.inlineCallbacks
    def tearDown(self):
        yield self.client.disconnect()
        self.sentinel_listener.stopListening()
        self.master_listener.stopListening()
        self.slave_listener.stopListening()

    @defer.inlineCallbacks
    def test_master(self):
        conn = self.client.master_for("test")
        reply = yield conn.role()
        self.assertEqual(reply[0], "master")
        yield conn.disconnect()

    @defer.inlineCallbacks
    def test_retry_on_error(self):
        self.client.discover_master = Mock(side_effect=[
            defer.fail(MasterNotFoundError()),
            defer.fail(MasterNotFoundError()),
            defer.succeed(self.fake_sentinel.master_addr)
        ])
        conn = self.client.master_for("test")
        yield conn.role()
        self.assertEqual(self.client.discover_master.call_count, 3)
        yield conn.disconnect()

    @defer.inlineCallbacks
    def test_retry_unexpected_role(self):
        self.fake_master.role = [
            "slave", "127.0.0.1", self.slave_port, "connected", 0
        ]

        def side_effect(*args, **kwargs):
            if self.client.discover_master.call_count > 2:
                self.fake_master.role = FakeRedisFactory.role
            return defer.succeed(self.fake_sentinel.master_addr)

        self.client.discover_master = Mock(side_effect=side_effect)
        conn = self.client.master_for("test")
        reply = yield conn.role()
        self.assertEqual(reply[0], "master")
        self.assertEqual(self.client.discover_master.call_count, 3)
        yield conn.disconnect()

    @defer.inlineCallbacks
    def test_slave(self):
        conn = self.client.slave_for("test")
        reply = yield conn.role()
        self.assertEqual(reply[0], "slave")
        yield conn.disconnect()

    @defer.inlineCallbacks
    def test_fallback_to_master_if_no_slaves(self):
        self.client.discover_slaves = Mock(return_value=defer.succeed([]))
        conn = self.client.slave_for("test")
        reply = yield conn.role()
        self.assertEqual(reply[0], "master")
        yield conn.disconnect()

    @staticmethod
    def _delay(secs):
        d = defer.Deferred()
        reactor.callLater(secs, d.callback, None)
        return d

    @defer.inlineCallbacks
    def test_drop_all_when_master_changes(self):
        # When master address change detected, factory should drop and reestablish
        # all its connections

        conn = self.client.master_for("test", poolsize=3)
        yield conn.role()  # wait for connection

        addrs = [proto.transport.getPeer() for proto in conn._factory.pool]
        self.assertTrue(len(addrs), 3)
        self.assertTrue(all(addr.port == self.master_port for addr in addrs))

        # Change master address at sentinel and change role of the slave to master
        self.fake_sentinel.master_addr = ("127.0.0.1", self.slave_port)
        self.fake_slave.role = ["master", 0, ["127.0.0.1", self.slave_port, 0]]

        # Force reconnection of one connection
        conn._factory.pool[0].transport.loseConnection()

        # After a short time all connections should be to the new master
        yield self._delay(0.2)
        addrs = [proto.transport.getPeer() for proto in conn._factory.pool]
        self.assertTrue(len(addrs), 3)
        self.assertTrue(all(addr.port == self.slave_port for addr in addrs))

        yield conn.disconnect()
Пример #4
0
class TestConnectViaSentinel(TestCase):

    master_port = 36379
    slave_port = 36380
    sentinel_port = 46379

    def setUp(self):
        self.fake_master = FakeRedisFactory()
        self.master_listener = reactor.listenTCP(self.master_port, self.fake_master)
        self.fake_slave = FakeRedisFactory()
        self.fake_slave.role = ["slave", "127.0.0.1", self.master_port, "connected", 0]
        self.slave_listener = reactor.listenTCP(self.slave_port, self.fake_slave)

        self.fake_sentinel = FakeSentinelFactory()
        self.fake_sentinel.master_addr = ("127.0.0.1", self.master_port)
        self.fake_sentinel.slave_addrs = [("127.0.0.1", self.slave_port)]
        self.fake_sentinel.slave_flags = ["slave"]
        self.sentinel_listener = reactor.listenTCP(self.sentinel_port, self.fake_sentinel)

        self.client = Sentinel([("127.0.0.1", self.sentinel_port)])
        self.client.discovery_timeout = 1

    @defer.inlineCallbacks
    def tearDown(self):
        yield self.client.disconnect()
        self.sentinel_listener.stopListening()
        self.master_listener.stopListening()
        self.slave_listener.stopListening()

    @defer.inlineCallbacks
    def test_master(self):
        conn = self.client.master_for("test")
        reply = yield conn.role()
        self.assertEqual(reply[0], "master")
        yield conn.disconnect()

    @defer.inlineCallbacks
    def test_retry_on_error(self):
        self.client.discover_master = Mock(side_effect=[defer.fail(MasterNotFoundError()),
                                                        defer.fail(MasterNotFoundError()),
                                                        defer.succeed(self.fake_sentinel.master_addr)])
        conn = self.client.master_for("test")
        yield conn.role()
        self.assertEqual(self.client.discover_master.call_count, 3)
        yield conn.disconnect()

    @defer.inlineCallbacks
    def test_retry_unexpected_role(self):
        self.fake_master.role = ["slave", "127.0.0.1", self.slave_port, "connected", 0]

        def side_effect(*args, **kwargs):
            if self.client.discover_master.call_count > 2:
                self.fake_master.role = FakeRedisFactory.role
            return defer.succeed(self.fake_sentinel.master_addr)

        self.client.discover_master = Mock(side_effect=side_effect)
        conn = self.client.master_for("test")
        reply = yield conn.role()
        self.assertEqual(reply[0], "master")
        self.assertEqual(self.client.discover_master.call_count, 3)
        yield conn.disconnect()

    @defer.inlineCallbacks
    def test_slave(self):
        conn = self.client.slave_for("test")
        reply = yield conn.role()
        self.assertEqual(reply[0], "slave")
        yield conn.disconnect()

    @defer.inlineCallbacks
    def test_fallback_to_master_if_no_slaves(self):
        self.client.discover_slaves = Mock(return_value=defer.succeed([]))
        conn = self.client.slave_for("test")
        reply = yield conn.role()
        self.assertEqual(reply[0], "master")
        yield conn.disconnect()

    @staticmethod
    def _delay(secs):
        d = defer.Deferred()
        reactor.callLater(secs, d.callback, None)
        return d

    @defer.inlineCallbacks
    def test_drop_all_when_master_changes(self):
        # When master address change detected, factory should drop and reestablish
        # all its connections

        conn = self.client.master_for("test", poolsize=3)
        yield conn.role()  # wait for connection

        addrs = [proto.transport.getPeer() for proto in conn._factory.pool]
        self.assertTrue(len(addrs), 3)
        self.assertTrue(all(addr.port == self.master_port for addr in addrs))

        # Change master address at sentinel and change role of the slave to master
        self.fake_sentinel.master_addr = ("127.0.0.1", self.slave_port)
        self.fake_slave.role = ["master", 0, ["127.0.0.1", self.slave_port, 0]]

        # Force reconnection of one connection
        conn._factory.pool[0].transport.loseConnection()

        # After a short time all connections should be to the new master
        yield self._delay(0.2)
        addrs = [proto.transport.getPeer() for proto in conn._factory.pool]
        self.assertTrue(len(addrs), 3)
        self.assertTrue(all(addr.port == self.slave_port for addr in addrs))

        yield conn.disconnect()