Distributed consensus with Singleton class

32 views Asked by At

I'm developing a singleton calss in Python to keep one node at time as primary node using the PySyncObj library:

class PhiRaft():
    __instance = None

    def __new__(
            cls,
            logger: PhiLogger = None,
            node: str = None,
            nodes: list = None,
            timeout: float = None
    ):
        if cls.__instance is None:
            cls.__instance = super(PhiRaft, cls).__new__(cls)
            if logger and node and nodes and timeout:
                cls._init_singleton(cls, logger, node, nodes, timeout)
        return cls.__instance

    def _init_singleton(self, logger: PhiLogger, node: str, nodes: list, timeout: float):
        self.__log = logger

        lock_manager = ReplLockManager(autoUnlockTime=timeout)
        sync_obj = SyncObj(node, nodes, consumers=[lock_manager])

        self.__lockThread = LockThread(logger, lock_manager, sync_obj)
        self.__lockThread.start()

    def is_node_primary(self):
        return self.__lockThread.getLockStatus()


class LockThread(threading.Thread):
    def __init__(self, logger: PhiLogger, lock_manager: ReplLockManager, sync_obj: SyncObj):
        self.__log = logger
        self.__lock_manager = lock_manager
        self.__sync_obj = sync_obj
        self.__callbacks = []
        self.__lockAcquired = False
        threading.Thread.__init__(self)

    def run(self):
        while True:
            try:
                self.__lockAcquired = self.__lock_manager.tryAcquire('leader', sync=True, timeout=1)
            except Exception as e:
                self.__log.info(f'Error lock: {vars(e)}')
            self.__log.info(f'lockAcquired: {self.__lock_manager.isAcquired("leader")}, amILeader: {self.__sync_obj._isLeader()}, leader: {self.__sync_obj._getLeader()}')
            time.sleep(3)

So with that only one node at time can be the primary node and in every place of my code I can check if I'm the primary node. I'm testing this code and it works with 4+ nodes cluster but with 3 nodes only I'm facing a problem. If the raft-leader node crashes the remaing two doesn't start an election and they won't be able to acquire the lock. The tryAcquire method also throws an Exception of "Timeout". Maybe I'm not implementing it in the righ way, can anyone help me?

0

There are 0 answers