Esempio n. 1
0
async def test_continues_polling_when_resource_not_found():
    class _command:
        calls = 0
        operation_complete = False

    async def command():
        """Simulate service responding 404 a few times before 2xx"""

        assert not _command.operation_complete, "polling method shouldn't invoke the command after completion"

        if _command.calls < 3:
            _command.calls += 1
            raise ResourceNotFoundError()

        _command.operation_complete = True

    polling_method = AsyncDeleteRecoverPollingMethod(command,
                                                     final_resource=None,
                                                     finished=False)

    sleep = mock.Mock(return_value=get_completed_future())
    with mock.patch(SLEEP, sleep):
        await polling_method.run()

    assert sleep.call_count == _command.calls
Esempio n. 2
0
async def test_initialization_get_key_successful():
    """If the client is able to get key material, it shouldn't do so again"""

    key_id = "https://localhost/fake/key/version"
    mock_key = mock.Mock()
    mock_key.key.kid = key_id
    mock_client = mock.Mock()
    mock_client.get_key.return_value = get_completed_future(mock_key)

    client = CryptographyClient(key_id, mock.Mock())
    client._client = mock_client

    assert mock_client.get_key.call_count == 0
    with mock.patch(CryptographyClient.__module__ +
                    ".get_local_cryptography_provider") as get_provider:
        await client.verify(SignatureAlgorithm.rs256, b"...", b"...")

    args, _ = get_provider.call_args
    assert len(args) == 1 and isinstance(args[0],
                                         JsonWebKey) and args[0].kid == key_id

    for _ in range(3):
        assert mock_client.get_key.call_count == 1
        assert get_provider.call_count == 1
        await client.verify(SignatureAlgorithm.rs256, b"...", b"...")
async def test_continuation_token():
    """Methods returning pollers should accept continuation tokens"""

    expected_token = "token"

    mock_generated_client = mock.Mock()
    mock_methods = [
        getattr(mock_generated_client, method_name) for method_name in (
            "begin_full_backup",
            "begin_full_restore_operation",
            "begin_selective_key_restore_operation",
        )
    ]
    for method in mock_methods:
        # the mock client's methods must return awaitables, and we don't have AsyncMock before 3.8
        method.return_value = get_completed_future()

    backup_client = KeyVaultBackupClient("vault-url", object())
    backup_client._client = mock_generated_client
    await backup_client.begin_restore("storage uri",
                                      "sas",
                                      continuation_token=expected_token)
    await backup_client.begin_backup("storage uri",
                                     "sas",
                                     continuation_token=expected_token)
    await backup_client.begin_selective_restore(
        "storage uri", "sas", "key", continuation_token=expected_token)

    for method in mock_methods:
        assert method.call_count == 1
        _, kwargs = method.call_args
        assert kwargs["continuation_token"] == expected_token
Esempio n. 4
0
async def test_initialization_transient_failure_getting_key():
    """If the client is not forbidden to get key material, it should retry after failing to do so"""

    mock_client = mock.Mock()
    mock_client.get_key.side_effect = HttpResponseError(response=mock.Mock(status_code=500))
    mock_client.verify.return_value = get_completed_future(mock.Mock())
    client = CryptographyClient("https://localhost/fake/key/version", mock.Mock())
    client._client = mock_client

    for i in range(3):
        assert mock_client.get_key.call_count == i
        await client.verify(SignatureAlgorithm.rs256, b"...", b"...")
Esempio n. 5
0
async def test_initialization_forbidden_to_get_key():
    """If the client is forbidden to get key material, it should try to do so exactly once"""

    mock_client = mock.Mock()
    mock_client.get_key.side_effect = HttpResponseError(response=mock.Mock(status_code=403))
    mock_client.verify.return_value = get_completed_future(mock.Mock())
    client = CryptographyClient("https://localhost/fake/key/version", mock.Mock())
    client._client = mock_client

    assert mock_client.get_key.call_count == 0
    for _ in range(3):
        await client.verify(SignatureAlgorithm.rs256, b"...", b"...")
        assert mock_client.get_key.call_count == 1
Esempio n. 6
0
async def test_initialization_given_key():
    """If the client is given key material, it should not attempt to get this from the vault"""

    mock_client = mock.Mock()
    key = mock.Mock(spec=KeyVaultKey, id="https://localhost/fake/key/version")
    client = CryptographyClient(key, mock.Mock())
    client._client = mock_client
    mock_client.get_key.return_value = get_completed_future()

    with mock.patch(CryptographyClient.__module__ + ".get_local_cryptography_provider") as get_provider:
        await client.verify(SignatureAlgorithm.rs256, b"...", b"...")
    get_provider.assert_called_once_with(key)
    assert mock_client.get_key.call_count == 0
Esempio n. 7
0
async def test_terminal_first_response():
    """The polling method shouldn't sleep when Key Vault's first response indicates the operation is complete"""

    command = mock.Mock(return_value=get_completed_future())
    polling_method = AsyncDeleteRecoverPollingMethod(command,
                                                     final_resource=None,
                                                     finished=False)

    with mock.patch(
            SLEEP,
            raise_exception(
                "polling method shouldn't sleep after the operation completes")
    ):
        await polling_method.run()

    assert command.call_count == 1
    assert polling_method.finished()
Esempio n. 8
0
async def test_run_idempotence():
    """After the polling method completes, calling 'run' again shouldn't change state or invoke the command"""

    max_calls = 3

    class _command:
        calls = 0
        operation_complete = False

    async def command():
        """Simulate service responding 404 a few times before 2xx"""

        assert not _command.operation_complete, "polling method shouldn't invoke the command after completion"

        if _command.calls < max_calls:
            _command.calls += 1
            raise ResourceNotFoundError()

        _command.operation_complete = True

    resource = object()
    polling_method = AsyncDeleteRecoverPollingMethod(command,
                                                     final_resource=resource,
                                                     finished=False)
    assert not polling_method.finished()

    sleep = mock.Mock(return_value=get_completed_future())
    with mock.patch(SLEEP, sleep):
        # when run is first called, the polling method should invoke the command until it indicates completion
        await polling_method.run()
    assert _command.calls == max_calls
    assert sleep.call_count == _command.calls

    # invoking run again should not change the resource or finished status, invoke the command, or sleep
    with mock.patch(
            SLEEP,
            raise_exception(
                "polling method shouldn't sleep when 'run' is called after completion"
            )):
        for _ in range(4):
            assert polling_method.resource() is resource
            assert polling_method.finished()
            await polling_method.run()
Esempio n. 9
0
async def test_initialization_get_key_successful():
    """If the client is able to get key material, it shouldn't do so again"""

    mock_client = mock.Mock()
    mock_client.get_key.return_value = mock.Mock(spec=KeyVaultKey)
    client = CryptographyClient("https://localhost/fake/key/version",
                                mock.Mock())
    client._client = mock_client
    mock_key = mock.Mock()
    mock_client.get_key.return_value = get_completed_future(mock_key)

    assert mock_client.get_key.call_count == 0
    with mock.patch(CryptographyClient.__module__ +
                    ".get_local_cryptography_provider") as get_provider:
        await client.verify(SignatureAlgorithm.rs256, b"...", b"...")
    get_provider.assert_called_once_with(mock_key)

    for _ in range(3):
        assert mock_client.get_key.call_count == 1
        assert get_provider.call_count == 1
        await client.verify(SignatureAlgorithm.rs256, b"...", b"...")