Example #1
0
    async def _backend_sock_factory(backend, auth_as, freeze_on_transport_error=True):
        async with backend_raw_transport_factory(
            backend, freeze_on_transport_error=freeze_on_transport_error
        ) as transport:
            if auth_as:
                # Handshake
                if isinstance(auth_as, OrganizationID):
                    ch = APIV1_AnonymousClientHandshake(auth_as)
                elif auth_as == "anonymous":
                    # TODO: for legacy test, refactorise this ?
                    ch = APIV1_AnonymousClientHandshake(coolorg.organization_id)
                elif auth_as == "administration":
                    ch = APIV1_AdministrationClientHandshake(backend.config.administration_token)
                else:
                    ch = APIV1_AuthenticatedClientHandshake(
                        auth_as.organization_id,
                        auth_as.device_id,
                        auth_as.signing_key,
                        auth_as.root_verify_key,
                    )
                challenge_req = await transport.recv()
                answer_req = ch.process_challenge_req(challenge_req)
                await transport.send(answer_req)
                result_req = await transport.recv()
                ch.process_result_req(result_req)

            yield transport
Example #2
0
async def test_authenticated_handshake_bad_versions(
    backend, server_factory, alice, mock_api_versions
):
    ch = APIV1_AuthenticatedClientHandshake(
        alice.organization_id, alice.device_id, alice.signing_key, alice.root_verify_key
    )

    async with server_factory(backend.handle_client) as server:
        stream = server.connection_factory()
        transport = await Transport.init_for_client(stream, server.addr.hostname)

        challenge_req = await transport.recv()
        answer_req = ch.process_challenge_req(challenge_req)

        # Alter answer
        answer_dict = unpackb(answer_req)
        answer_dict["client_api_version"] = ApiVersion(3, 22)
        answer_req = packb(answer_dict)

        await transport.send(answer_req)
        result_req = await transport.recv()

        with pytest.raises(InvalidMessageError) as context:
            ch.process_result_req(result_req)
        assert "bad_protocol" in str(context.value)
        assert "{1.22}" in str(context.value)
Example #3
0
async def test_authenticated_handshake_unknown_device(backend, server_factory, mallory):
    ch = APIV1_AuthenticatedClientHandshake(
        mallory.organization_id, mallory.device_id, mallory.signing_key, mallory.root_verify_key
    )
    async with server_factory(backend.handle_client) as server:
        stream = server.connection_factory()
        transport = await Transport.init_for_client(stream, server.addr.hostname)

        challenge_req = await transport.recv()
        answer_req = ch.process_challenge_req(challenge_req)

        await transport.send(answer_req)
        result_req = await transport.recv()
        with pytest.raises(HandshakeBadIdentity):
            ch.process_result_req(result_req)
Example #4
0
async def apiv1_connect(
    addr: Union[BackendAddr, BackendOrganizationBootstrapAddr,
                BackendOrganizationAddr],
    device_id: Optional[DeviceID] = None,
    signing_key: Optional[SigningKey] = None,
    administration_token: Optional[str] = None,
    keepalive: Optional[int] = None,
) -> Transport:
    """
    Raises:
        BackendConnectionError
    """
    handshake: BaseClientHandshake

    if administration_token:
        if not isinstance(addr, BackendAddr):
            raise BackendConnectionError(f"Invalid url format `{addr}`")
        handshake = APIV1_AdministrationClientHandshake(administration_token)

    elif not device_id:
        if isinstance(addr, BackendOrganizationBootstrapAddr):
            handshake = APIV1_AnonymousClientHandshake(addr.organization_id)
        elif isinstance(addr, BackendOrganizationAddr):
            handshake = APIV1_AnonymousClientHandshake(addr.organization_id,
                                                       addr.root_verify_key)
        else:
            raise BackendConnectionError(
                f"Invalid url format `{addr}` "
                "(should be an organization url or organization bootstrap url)"
            )

    else:
        if not isinstance(addr, BackendOrganizationAddr):
            raise BackendConnectionError(
                f"Invalid url format `{addr}` (should be an organization url)")

        if not signing_key:
            raise BackendConnectionError(
                f"Missing signing_key to connect as `{device_id}`")
        handshake = APIV1_AuthenticatedClientHandshake(addr.organization_id,
                                                       device_id, signing_key,
                                                       addr.root_verify_key)

    return await _connect(addr.hostname, addr.port, addr.use_ssl, keepalive,
                          handshake)
Example #5
0
async def test_authenticated_handshake_good(backend, server_factory, alice, mock_api_versions):
    ch = APIV1_AuthenticatedClientHandshake(
        alice.organization_id, alice.device_id, alice.signing_key, alice.root_verify_key
    )

    async with server_factory(backend.handle_client) as server:
        stream = server.connection_factory()
        transport = await Transport.init_for_client(stream, server.addr.hostname)

        challenge_req = await transport.recv()
        answer_req = ch.process_challenge_req(challenge_req)

        await transport.send(answer_req)
        result_req = await transport.recv()
        ch.process_result_req(result_req)

        assert ch.client_api_version == mock_api_versions.default_client_version
        assert ch.backend_api_version == mock_api_versions.default_backend_version
Example #6
0
async def test_authenticated_handshake_expired_organization(
    backend, server_factory, expiredorg, alice
):
    ch = APIV1_AuthenticatedClientHandshake(
        expiredorg.organization_id, alice.device_id, alice.signing_key, expiredorg.root_verify_key
    )

    async with server_factory(backend.handle_client) as server:
        stream = server.connection_factory()
        transport = await Transport.init_for_client(stream, server.addr.hostname)

        challenge_req = await transport.recv()
        answer_req = ch.process_challenge_req(challenge_req)

        await transport.send(answer_req)
        result_req = await transport.recv()
        with pytest.raises(HandshakeOrganizationExpired):
            ch.process_result_req(result_req)
Example #7
0
async def test_handshake_bad_rvk(backend, server_factory, coolorg, alice, otherorg, is_anonymous):
    if is_anonymous:
        ch = APIV1_AnonymousClientHandshake(coolorg.organization_id, otherorg.root_verify_key)
    else:
        ch = APIV1_AuthenticatedClientHandshake(
            alice.organization_id, alice.device_id, alice.signing_key, otherorg.root_verify_key
        )
    async with server_factory(backend.handle_client) as server:
        stream = server.connection_factory()
        transport = await Transport.init_for_client(stream, server.addr.hostname)

        challenge_req = await transport.recv()
        answer_req = ch.process_challenge_req(challenge_req)

        await transport.send(answer_req)
        result_req = await transport.recv()
        with pytest.raises(HandshakeRVKMismatch):
            ch.process_result_req(result_req)
Example #8
0
async def test_handshake_unknown_organization(
    backend, server_factory, organization_factory, alice, type
):
    bad_org = organization_factory()
    if type == "anonymous":
        ch = APIV1_AnonymousClientHandshake(bad_org.organization_id, bad_org.root_verify_key)
    else:  # authenticated
        ch = APIV1_AuthenticatedClientHandshake(
            bad_org.organization_id, alice.device_id, alice.signing_key, bad_org.root_verify_key
        )

    async with server_factory(backend.handle_client) as server:
        stream = server.connection_factory()
        transport = await Transport.init_for_client(stream, server.addr.hostname)

        challenge_req = await transport.recv()
        answer_req = ch.process_challenge_req(challenge_req)

        await transport.send(answer_req)
        result_req = await transport.recv()
        with pytest.raises(HandshakeBadIdentity):
            ch.process_result_req(result_req)