Exemple #1
0
    def __init__(self, dbpath: str, config: Dict[str, Any]):
        """
        Initialize a database-backed cookiestore. Example configuration:

        .. code-block:: json

            {
                "type": "database",
                "path": ".cookies",
                "purge_on_startup": false,
                "maxsize": 1048576,
                "readonly": false,
                "sync": true
            }

        :param dbpath: Filesystem path to database.
        :param config: Database cookie store configuration.
        """
        self.log.info(
            '{func}: initializing database-backed cookiestore with config=\n{config}',
            func=hltype(CookieStoreDatabaseBacked.__init__),
            config=pformat(config))
        CookieStore.__init__(self, config)

        maxsize = config['store'].get('maxsize', 1024 * 2**20)
        assert type(maxsize) == int, "maxsize must be an int, was {}".format(
            type(maxsize))
        # allow maxsize 128kiB to 128GiB
        assert maxsize >= 128 * 1024 and maxsize <= 128 * 2**30, "maxsize must be >=128kiB and <=128GiB, was {}".format(
            maxsize)

        readonly = config['store'].get('readonly', False)
        assert type(
            readonly) == bool, "readonly must be a bool, was {}".format(
                type(readonly))

        sync = config['store'].get('sync', True)
        assert type(sync) == bool, "sync must be a bool, was {}".format(
            type(sync))

        if config['store'].get('purge_on_startup', False):
            zlmdb.Database.scratch(dbpath)
            self.log.warn(
                '{func}: scratched embedded database (purge_on_startup is enabled)!',
                func=hltype(CookieStoreDatabaseBacked.__init__))

        self._db = zlmdb.Database(dbpath=dbpath,
                                  maxsize=maxsize,
                                  readonly=readonly,
                                  sync=sync)
        # self._db.__enter__()
        self._schema = cookiestore.CookieStoreSchema.attach(self._db)

        dbstats = self._db.stats(include_slots=True)

        self.log.info(
            '{func}: database-backed cookiestore opened from dbpath="{dbpath}" - dbstats=\n{dbstats}',
            func=hltype(CookieStoreDatabaseBacked.__init__),
            dbpath=hlval(dbpath),
            dbstats=pformat(dbstats))
Exemple #2
0
    def delAuth(self, cbtid: str) -> bool:
        """
        Delete an existing cookie (if any), including any authentication info and the cookie itself.

        :param cbtid: Cookie value (ID)  of cookie to delete.
        :return: Flag indicating an existing cookie was deleted.
        """
        was_existing = False
        with self._db.begin(write=True) as txn:
            cookie_oid = self._schema.idx_cookies_by_value[txn, cbtid]
            if cookie_oid:
                del self._schema.cookies[txn, cookie_oid]
                was_existing = True

        if was_existing:
            self.log.info(
                '{func} cookie with cbtid="{cbtid}" did exist and was deleted',
                func=hltype(self.delAuth),
                cbtid=hlid(cbtid))
        else:
            self.log.info('{func} no cookie with cbtid="{cbtid}" exists',
                          func=hltype(self.delAuth),
                          cbtid=hlid(cbtid))

        return was_existing
Exemple #3
0
    def detach(self, session=None) -> List[int]:
        self.log.debug('{func}(session={session})',
                       func=hltype(self.detach),
                       session=session)

        detached_session_ids = []
        if session is None:
            # detach all sessions from router
            for session in list(self._session_id_to_session.values()):
                self._detach(session)
                detached_session_ids.append(session._session_id)
        else:
            # detach single session from router
            self._detach(session)
            detached_session_ids.append(session._session_id)

        self.log.info(
            '{func} router session detached from realm "{realm}" (session={session}, '
            'detached_session_ids={detached_session_ids}, authid="{authid}", authrole="{authrole}", '
            'authmethod="{authmethod}", authprovider="{authprovider}")',
            func=hltype(self.detach),
            session=hlid(session._session_id) if session else '',
            authid=hlid(session._authid),
            authrole=hlid(session._authrole),
            authmethod=hlval(session._authmethod),
            authprovider=hlval(session._authprovider),
            detached_session_ids=hlval(len(detached_session_ids)),
            realm=hlid(session._realm))

        return detached_session_ids
Exemple #4
0
    async def authenticate(realm, authid, details):
        """
        this is our dynamic authenticator procedure that will be called by Crossbar.io
        when a session is authenticating
        """
        log.info(
            'authenticate(realm="{realm}", authid="{authid}", details={details}) {func}',
            realm=hl(realm),
            authid=hl(authid),
            details=details,
            func=hltype(create_rlink_authenticator),
        )

        assert ('authmethod' in details)
        assert (details['authmethod'] == 'cryptosign')
        assert ('authextra' in details)
        assert ('pubkey' in details['authextra'])

        pubkey = details['authextra']['pubkey']
        log.info(
            'authenticating session using realm="{realm}", pubkey={pubkey} .. {func}',
            realm=hl(realm),
            pubkey=hl(pubkey),
            func=hltype(create_rlink_authenticator),
        )

        if pubkey in pubkey_to_principals:
            principal = pubkey_to_principals[pubkey]
            auth = {
                'pubkey': pubkey,
                'realm': principal['realm'],
                'authid': principal['authid'],
                'role': principal['role'],
                'extra': principal['extra'],
                'cache': True
            }

            # Note: with WAMP-cryptosign, even though a client may or may not request a `realm`, but in any case, the
            # effective realm the client is authenticated will be returned in the principal `auth['role']` (!)
            effective_realm = auth['realm']

            log.info(
                'found valid principal authid="{authid}", authrole="{authrole}", realm="{realm}" matching given client public key {func}',
                func=hltype(create_rlink_authenticator),
                authid=hl(auth['authid']),
                authrole=hl(auth['role']),
                realm=hl(effective_realm),
            )

            # only now that we know the effective realm a client is to be joined to (see above), maybe active (start)
            # the desired application realm to let the client join to subsequently
            # await _maybe_activate_realm(controller, effective_realm)

            return auth
        else:
            msg = 'no principal with matching public key 0x{}'.format(pubkey)
            log.warn(msg)
            raise ApplicationError('com.example.no_such_user', msg)
Exemple #5
0
    def onConnect(self):
        self.log.info('{func}() ...', func=hltype(self.onConnect))

        authid = self.config.extra.get('authid', None)
        authrole = self.config.extra.get('authrole', None)
        authextra = self.config.extra.get('authextra', {})

        # FIXME: use cryptosign-proxy
        authmethods = ['cryptosign']

        # use WorkerController.get_public_key to call node controller
        # FIXME: the following does _not_ work with onConnect (?!)
        # _public_key = await self._router_controller.get_public_key()

        def actually_join(_public_key):
            authextra.update({
                # forward the client pubkey: this allows us to omit authid as
                # the router can identify us with the pubkey already
                'pubkey': _public_key,

                # not yet implemented. a public key the router should provide
                # a trustchain for its public key. the trustroot can eg be
                # hard-coded in the client, or come from a command line option.
                'trustroot': None,

                # not yet implemented. for authenticating the router, this
                # challenge will need to be signed by the router and send back
                # in AUTHENTICATE for client to verify. A string with a hex
                # encoded 32 bytes random value.
                'challenge': None,

                # https://tools.ietf.org/html/rfc5929
                'channel_binding': 'tls-unique'
            })

            self.log.info(
                '{func} joining with realm="{realm}", authmethods={authmethods}, authid="{authid}", authrole="{authrole}", authextra={authextra}',
                func=hltype(self.onConnect),
                realm=hlval(self.config.realm),
                authmethods=hlval(authmethods),
                authid=hlval(authid),
                authrole=hlval(authrole),
                authextra=authextra)

            self.join(self.config.realm,
                      authmethods=authmethods,
                      authid=authid,
                      authrole=authrole,
                      authextra=authextra)

        res = self._rlink_manager._controller.get_public_key()
        res.addCallback(actually_join)
        self.log.info('{func}() done (res={res}).',
                      func=hltype(self.onConnect),
                      res=res)
        return res
Exemple #6
0
    def start(self):
        """
        Implements :meth:`crossbar._interfaces.IInventory.start`
        """
        if self._running:
            raise RuntimeError('inventory is already running')
        else:
            self.log.info('{func} starting realm inventory',
                          func=hltype(self.start))

        self._running = True
        self.log.info('{func} realm inventory ready!', func=hltype(self.start))
Exemple #7
0
    def get_public_key(self):
        """
        Call into node controller (over secure controller-worker pipe) to get the node's public key.

        :return:
        """
        self.log.info('{func}() ...', func=hltype(self.get_public_key))
        result = yield self.call("crossbar.get_public_key")
        self.log.info('{func}(): {result}',
                      func=hltype(self.get_public_key),
                      result=result)
        return result
    def connectionLost(self, reason: Failure = connectionDone):
        # Twisted networking framework entry point, called by Twisted
        # when the connection is lost (either a client or a server)

        was_clean = False
        if isinstance(reason.value, ConnectionDone):
            self.log.debug("Connection to/from {peer} was closed cleanly",
                           peer=self.peer)
            was_clean = True

        elif _is_tls_error(reason.value):
            self.log.error(_maybe_tls_reason(reason.value))

        elif isinstance(reason.value, ConnectionAborted):
            self.log.debug("Connection to/from {peer} was aborted locally",
                           peer=self.peer)

        elif isinstance(reason.value, ConnectionLost):
            message = str(reason.value)
            if hasattr(reason.value, 'message'):
                message = reason.value.message
            self.log.debug(
                "Connection to/from {peer} was lost in a non-clean fashion: {message}",
                peer=self.peer,
                message=message,
            )

        # at least: FileDescriptorOverrun, ConnectionFdescWentAway - but maybe others as well?
        else:
            self.log.debug(
                "Connection to/from {peer} lost ({error_type}): {error})",
                peer=self.peer,
                error_type=type(reason.value),
                error=reason.value)

        # ok, now forward to the networking framework independent code for websocket
        self._connectionLost(reason)

        # ok, done!
        if was_clean:
            self.log.debug(
                '{func} connection lost for peer="{peer}", closed cleanly',
                func=hltype(self.connectionLost),
                peer=hlval(self.peer))
        else:
            self.log.debug(
                '{func} connection lost for peer="{peer}", closed with error {reason}',
                func=hltype(self.connectionLost),
                peer=hlval(self.peer),
                reason=reason)
Exemple #9
0
    def drop_role(self, realm: str, role: str) -> RouterRole:
        """
        Drop a role from a realm.

        :param realm: The name of the realm to drop.
        :param role: The URI of the role (on the realm) to drop.
        :return: The dropped role object.
        """
        self.log.info('{func}: realm="{realm}", role="{role}"',
                      func=hltype(self.drop_role),
                      realm=hlval(realm),
                      role=hlval(role))

        if realm not in self._routers:
            raise RuntimeError(
                'no router started for realm "{}"'.format(realm))

        router = self._routers[realm]

        if role not in router._roles:
            raise RuntimeError(
                'no role "{}" started on router for realm "{}"'.format(
                    role, realm))

        role_obj = router._roles[role]
        router.drop_role(role_obj)
        return role_obj
    def connectionMade(self):
        # Twisted networking framework entry point, called by Twisted
        # when the connection is established (either a client or a server)

        # determine preliminary transport details (what is know at this point)
        self._transport_details = create_transport_details(
            self.transport, self.is_server)
        self._transport_details.channel_framing = TransportDetails.CHANNEL_FRAMING_WEBSOCKET

        # backward compatibility
        self.peer = self._transport_details.peer

        # try to set "Nagle" option for TCP sockets
        try:
            self.transport.setTcpNoDelay(self.tcpNoDelay)
        except:  # don't touch this! does not work: AttributeError, OSError
            # eg Unix Domain sockets throw Errno 22 on this
            pass

        # ok, now forward to the networking framework independent code for websocket
        self._connectionMade()

        # ok, done!
        self.log.debug('{func} connection established for peer="{peer}"',
                       func=hltype(self.connectionMade),
                       peer=hlval(self.peer))
Exemple #11
0
    def dropProto(self, cbtid: str, proto: ISession):
        """
        Remove given WebSocket connection from the set of connections associated
        with the cookie having the given ID. Return the new count of
        connections associated with the cookie.
        """
        self.log.debug('{func} removing proto {proto} from cookie "{cbtid}"',
                       func=hltype(self.dropProto),
                       proto=proto,
                       cbtid=hlid(cbtid))

        if self.exists(cbtid):
            if cbtid in self._connections:
                # remove this WebSocket connection from the set of connections
                # associated with the same cookie
                self._connections[cbtid].discard(proto)
                remaining = len(self._connections[cbtid])
                if remaining:
                    return remaining
                else:
                    del self._connections[cbtid]
        else:
            if cbtid in self._connections:
                del self._connections[cbtid]
        return 0
Exemple #12
0
    def add_role(self, realm: str, config: Dict[str, Any]) -> RouterRole:
        """
        Add a role to a realm.

        :param realm: The name of the realm to add the role to.
        :param config: The role configuration.
        :return: The new role object.
        """
        self.log.info('{func}: realm="{realm}", config=\n{config}',
                      func=hltype(self.add_role),
                      realm=hlval(realm),
                      config=pformat(config))

        if realm not in self._routers:
            raise RuntimeError(
                'no router started for realm "{}"'.format(realm))

        router = self._routers[realm]
        uri = config['name']

        role: RouterRole
        if 'permissions' in config:
            role = RouterRoleStaticAuth(router, uri, config['permissions'])
        elif 'authorizer' in config:
            role = RouterRoleDynamicAuth(router, uri, config['authorizer'])
        else:
            allow_by_default = config.get('allow-by-default', False)
            role = RouterRole(router, uri, allow_by_default=allow_by_default)

        router.add_role(role)
        return role
Exemple #13
0
    def parse(self, headers):
        """
        Parse HTTP request header for cookie. If cookie is found, return cookie ID,
        else return None.
        """
        self.log.debug('{func} parsing cookie from {headers}',
                       func=hltype(self.parse),
                       headers=headers)

        # see if there already is a cookie set in the HTTP request
        if 'cookie' in headers:
            try:
                cookie = http_cookies.SimpleCookie()
                header_cookie = str(headers['cookie'])
                cookie.load(header_cookie)

                if self._cookie_id_field not in cookie and self._cookie_id_field in header_cookie:
                    # Sometimes Python can't parse cookie. So let's parse it manually.
                    header_cookies_as_array = header_cookie.split(";")
                    if len(header_cookies_as_array) != 0:
                        header_cookie_id_indexes = []
                        for cookie_raw in header_cookies_as_array:
                            if (self._cookie_id_field + "=") in cookie_raw:
                                header_cookie_id_indexes.append(
                                    header_cookies_as_array.index(cookie_raw))
                        if len(header_cookie_id_indexes) > 0:
                            cookie.load(header_cookies_as_array[
                                header_cookie_id_indexes[0]])
            except http_cookies.CookieError:
                pass
            else:
                if self._cookie_id_field in cookie:
                    cbtid = cookie[self._cookie_id_field].value
                    return cbtid
        return None
Exemple #14
0
    def start(self):
        """
        Implements :meth:`crossbar._interfaces.IRealmStore.start`
        """
        if self._running:
            raise RuntimeError('store is already running')
        else:
            self.log.info(
                '{func} starting realm store type="{stype}"',
                func=hltype(self.start),
                stype=hlval(self._type),
            )

        # currently nothing to do in stores of type "memory"
        self._running = True
        self.log.info('{func} realm store ready!', func=hltype(self.start))
Exemple #15
0
    def onChallenge(self, challenge):
        self.log.debug('{func}(challenge={challenge})',
                       func=hltype(self.onChallenge),
                       challenge=challenge)

        if challenge.method == 'cryptosign':
            # alright, we've got a challenge from the router.

            # sign the challenge with our private key.
            channel_id_type = 'tls-unique'
            channel_id_map = self._router_controller._transport.transport_details.channel_id
            if channel_id_type in channel_id_map:
                channel_id = channel_id_map[channel_id_type]
            else:
                channel_id = None
                channel_id_type = None

            # use WorkerController.get_public_key to call node controller
            # FIXME: await?
            signed_challenge = self._router_controller.sign_challenge(
                challenge, channel_id, channel_id_type)

            # send back the signed challenge for verification
            return signed_challenge

        else:
            raise Exception(
                'internal error: we asked to authenticate using wamp-cryptosign, but now received a challenge for {}'
                .format(challenge.method))
Exemple #16
0
        def got_authorization(authorization):
            # backward compatibility
            if isinstance(authorization, bool):
                authorization = {'allow': authorization, 'cache': False}
                if action in ['call', 'publish']:
                    authorization['disclose'] = False

            auto_disclose_trusted = True
            if auto_disclose_trusted and authrole == 'trusted' and action in [
                    'call', 'publish'
            ]:
                authorization['disclose'] = True

            if not cached_authorization and authorization.get('cache', False):
                self._authorization_cache[cache_key] = authorization
                self.log.debug(
                    '{func} add authorization cache entry for key {cache_key}:\n{authorization}',
                    func=hltype(got_authorization),
                    cache_key=hlval(cache_key),
                    authorization=pformat(authorization))

            self.log.debug(
                "Authorized action '{action}' for URI '{uri}' by session {session_id} with authid '{authid}' and "
                "authrole '{authrole}' -> authorization: {authorization}",
                session_id=session._session_id,
                uri=uri,
                action=action,
                authid=session._authid,
                authrole=session._authrole,
                authorization=authorization)

            return authorization
Exemple #17
0
        def actually_join(_public_key):
            authextra.update({
                # forward the client pubkey: this allows us to omit authid as
                # the router can identify us with the pubkey already
                'pubkey': _public_key,

                # not yet implemented. a public key the router should provide
                # a trustchain for its public key. the trustroot can eg be
                # hard-coded in the client, or come from a command line option.
                'trustroot': None,

                # not yet implemented. for authenticating the router, this
                # challenge will need to be signed by the router and send back
                # in AUTHENTICATE for client to verify. A string with a hex
                # encoded 32 bytes random value.
                'challenge': None,

                # https://tools.ietf.org/html/rfc5929
                'channel_binding': 'tls-unique'
            })

            self.log.info(
                '{func} joining with realm="{realm}", authmethods={authmethods}, authid="{authid}", authrole="{authrole}", authextra={authextra}',
                func=hltype(self.onConnect),
                realm=hlval(self.config.realm),
                authmethods=hlval(authmethods),
                authid=hlval(authid),
                authrole=hlval(authrole),
                authextra=authextra)

            self.join(self.config.realm,
                      authmethods=authmethods,
                      authid=authid,
                      authrole=authrole,
                      authextra=authextra)
Exemple #18
0
    def onJoin(self, details):
        assert self.config.extra and 'on_ready' in self.config.extra
        assert self.config.extra and 'other' in self.config.extra

        remote = self.config.extra['other']
        assert isinstance(remote, RLinkRemoteSession)

        self._exclude_authid = self.config.extra.get('exclude_authid', None)
        self._exclude_authrole = self.config.extra.get('exclude_authrole',
                                                       None)

        # setup local->remote event forwarding
        forward_events = self.config.extra.get('forward_events', False)
        if forward_events:
            yield self._setup_event_forwarding(remote)

        # setup local->remote invocation forwarding
        forward_invocations = self.config.extra.get('forward_invocations',
                                                    False)
        if forward_invocations:
            yield self._setup_invocation_forwarding(remote)

        self.log.debug(
            'Router link local session ready (forward_events={forward_events}, forward_invocations={forward_invocations}, realm={realm}, authid={authid}, authrole={authrole}, session={session}) {method}',
            method=hltype(RLinkLocalSession.onJoin),
            forward_events=hluserid(forward_events),
            forward_invocations=hluserid(forward_invocations),
            realm=hluserid(details.realm),
            authid=hluserid(details.authid),
            authrole=hluserid(details.authrole),
            session=hlid(details.session))

        on_ready = self.config.extra.get('on_ready', None)
        if on_ready and not on_ready.called:
            self.config.extra['on_ready'].callback(self)
Exemple #19
0
 def store_session_joined(self, session: ISession, details: SessionDetails):
     """
     Implements :meth:`crossbar._interfaces.IRealmStore.store_session_joined`
     """
     self.log.info('{func} new session joined session={session}, details={details}',
                   func=hltype(self.store_session_joined),
                   session=session,
                   details=details)
Exemple #20
0
 def store_session_left(self, session: ISession, details: CloseDetails):
     """
     Implements :meth:`crossbar._interfaces.IRealmStore.store_session_left`
     """
     self.log.info('{func} session left session={session}, details={details}',
                   func=hltype(self.store_session_left),
                   session=session,
                   details=details)
    def dataReceived(self, data: bytes):
        self.log.debug('{func} received {data_len} bytes for peer="{peer}"',
                       func=hltype(self.dataReceived),
                       peer=hlval(self.peer),
                       data_len=hlval(len(data)))

        # bytes received from Twisted, forward to the networking framework independent code for websocket
        self._dataReceived(data)
Exemple #22
0
    def __init__(self, config: Dict[str, Any]):
        CookieStore.__init__(self, config)

        # transient cookie database
        self._cookies: Dict[str, Dict[str, Any]] = {}

        self.log.info('{func} cookie stored created with config=\n{config}',
                      func=hltype(CookieStoreMemoryBacked.__init__),
                      config=pformat(config))
Exemple #23
0
    def start(self):
        """
        Implements :meth:`crossbar._interfaces.IRealmStore.start`
        """
        if self._running:
            raise RuntimeError('store is already running')
        else:
            self.log.info(
                '{func} starting realm store type="{stype}"',
                func=hltype(self.start),
                stype=hlval(self._type),
            )

        self._buffer = []
        self._log_counter = 0
        self._running = True
        self._process_buffers_thread = yield self._reactor.callInThread(self._process_buffers)
        self.log.info('{func} realm store ready!', func=hltype(self.start))
Exemple #24
0
    def __init__(self, personality, factory, config):
        """

        :param personality:
        :param factory:
        :param config: Realm store configuration item.
        """
        from twisted.internet import reactor

        self._reactor = reactor
        self._personality = personality
        self._factory = factory

        dbpath = config.get('path', None)
        assert type(dbpath) == str

        maxsize = config.get('maxsize', 128 * 2**20)
        assert type(maxsize) == int
        # allow maxsize 128kiB to 128GiB
        assert maxsize >= 128 * 1024 and maxsize <= 128 * 2**30

        readonly = config.get('readonly', False)
        assert type(readonly) == bool

        sync = config.get('sync', True)
        assert type(sync) == bool

        self._config = config

        self._type = self._config.get('type', None)
        assert self._type == self.STORE_TYPE

        self._db = zlmdb.Database(dbpath=dbpath, maxsize=maxsize, readonly=readonly, sync=sync)
        self._db.__enter__()
        self._schema = RealmStore.attach(self._db)

        self._running = False
        self._process_buffers_thread = None

        self._max_buffer = config.get('max-buffer', 10000)
        self._buffer_flush = config.get('buffer-flush', 200)
        self._buffer = []
        self._log_counter = 0

        # map: registration.id -> deque( (session, call, registration, authorization) )
        self._queued_calls = {}

        self.log.info(
            '{func} realm store initialized (type="{stype}", dbpath="{dbpath}", maxsize={maxsize}, '
            'readonly={readonly}, sync={sync})',
            func=hltype(self.__init__),
            stype=hlval(self._type),
            dbpath=dbpath,
            maxsize=maxsize,
            readonly=readonly,
            sync=sync)
Exemple #25
0
    def sign_challenge(self,
                       challenge: Challenge,
                       channel_id: Optional[bytes],
                       channel_id_type=Optional[str]):
        """
        Call into node controller (over secure controller-worker pipe) to sign challenge with node key.

        :param challenge:
        :param channel_id:
        :param channel_id_type:
        :return:
        """
        self.log.info('{func}() ...', func=hltype(self.sign_challenge))
        result = yield self.call("crossbar.sign_challenge", challenge.method,
                                 challenge.extra, channel_id, channel_id_type)
        self.log.info('{func}(): {result}',
                      func=hltype(self.sign_challenge),
                      result=result)
        return result
Exemple #26
0
    def _store_session_joined(self, txn: zlmdb.Transaction, ses: cfxdb.realmstore.Session):

        # FIXME: use idx_sessions_by_session_id to check there is no session with (session_id, joined_at) yet

        self._schema.sessions[txn, ses.oid] = ses

        cnt = self._schema.sessions.count(txn)
        self.log.info('{func} database record inserted [total={total}] session={session}',
                      func=hltype(self._store_session_joined),
                      total=hlval(cnt),
                      session=ses)
Exemple #27
0
    def stop(self):
        """
        Implements :meth:`crossbar._interfaces.IRealmStore.stop`
        """
        if not self._running:
            raise RuntimeError('store is not running')
        else:
            self.log.info('{func} stopping realm store', func=hltype(self.start))

        # currently nothing to do in stores of type "memory"
        self._running = False
Exemple #28
0
    def has_role(self, uri):
        """
        Check if a role with given URI exists on this router.

        :returns: bool - `True` if a role under the given URI exists on this router.
        """
        self.log.info('{func}: uri="{uri}", exists={exists}',
                      func=hltype(self.has_role),
                      uri=hlval(uri),
                      exists=(uri in self._roles))
        return uri in self._roles
Exemple #29
0
    def onLeave(self, details):
        self.log.warn(
            'Router link local session down! (realm={realm}, authid={authid}, authrole={authrole}, session={session}, details={details}) {method}',
            method=hltype(RLinkLocalSession.onLeave),
            realm=hluserid(self.config.realm),
            authid=hluserid(self._authid),
            authrole=hluserid(self._authrole),
            details=details,
            session=hlid(self._session_id))

        BridgeSession.onLeave(self, details)
Exemple #30
0
    def stop(self):
        """
        Implements :meth:`crossbar._interfaces.IInventory.stop`
        """
        if not self._running:
            raise RuntimeError('inventory is not running')
        else:
            self.log.info('{func} stopping realm inventory',
                          func=hltype(self.start))

        self._running = False