[Keyvault] operation resume token fix (#2093)
Enable resume operations for keyvault
This commit is contained in:
parent
1ea5afa961
commit
ce4b285ddd
@ -10,6 +10,10 @@
|
||||
|
||||
- Removed `Azure::Security::KeyVault::Keys::JsonWebKey::to_json`.
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
- Fix getting a resume token from delete and recover key operations.
|
||||
|
||||
## 4.0.0-beta.1 (2021-04-07)
|
||||
|
||||
### New Features
|
||||
|
||||
@ -75,6 +75,14 @@ namespace Azure { namespace Security { namespace KeyVault { namespace Keys {
|
||||
std::shared_ptr<Azure::Security::KeyVault::_internal::KeyVaultPipeline> keyvaultPipeline,
|
||||
Azure::Response<Azure::Security::KeyVault::Keys::DeletedKey> response);
|
||||
|
||||
DeleteKeyOperation(
|
||||
std::shared_ptr<Azure::Security::KeyVault::_internal::KeyVaultPipeline> keyvaultPipeline,
|
||||
std::string resumeToken)
|
||||
: m_pipeline(keyvaultPipeline), m_value(DeletedKey(resumeToken)),
|
||||
m_continuationToken(std::move(resumeToken))
|
||||
{
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Get the #Azure::Core::Http::RawResponse of the operation request.
|
||||
* @return A reference to an #Azure::Core::Http::RawResponse.
|
||||
|
||||
@ -225,6 +225,18 @@ namespace Azure { namespace Security { namespace KeyVault { namespace Keys {
|
||||
std::string const& name,
|
||||
Azure::Core::Context const& context = Azure::Core::Context()) const;
|
||||
|
||||
/**
|
||||
* @brief Construct a #DeletedKeyOperation from a resume token previously generated by calling
|
||||
* #DeleteKeyOperation::GetResumeToken after a call to #StartDeleteKey().
|
||||
*
|
||||
* @param resumeToken A generated token from a DeletedKeyOperation.
|
||||
* @param context A cancellation token controlling the request lifetime.
|
||||
* @return Azure::Security::KeyVault::Keys::DeleteKeyOperation
|
||||
*/
|
||||
Azure::Security::KeyVault::Keys::DeleteKeyOperation ResumeDeleteKey(
|
||||
std::string const& resumeToken,
|
||||
Azure::Core::Context const& context = Azure::Core::Context()) const;
|
||||
|
||||
/**
|
||||
* @brief Gets the public part of a deleted key.
|
||||
*
|
||||
@ -293,6 +305,19 @@ namespace Azure { namespace Security { namespace KeyVault { namespace Keys {
|
||||
std::string const& name,
|
||||
Azure::Core::Context const& context = Azure::Core::Context()) const;
|
||||
|
||||
/**
|
||||
* @brief Construct a #RecoverDeletedKeyOperation from a resume token previously generated by
|
||||
* calling #RecoverDeletedKeyOperation::GetResumeToken after a call to
|
||||
* #StartRecoverDeletedKey().
|
||||
*
|
||||
* @param resumeToken A generated token from a StartRecoverDeletedKey.
|
||||
* @param context A cancellation token controlling the request lifetime.
|
||||
* @return Azure::Security::KeyVault::Keys::RecoverDeletedKeyOperation
|
||||
*/
|
||||
Azure::Security::KeyVault::Keys::RecoverDeletedKeyOperation ResumeRecoverDeletedKey(
|
||||
std::string const& resumeToken,
|
||||
Azure::Core::Context const& context = Azure::Core::Context()) const;
|
||||
|
||||
/**
|
||||
* @brief The update key operation changes specified attributes of a stored key and can be
|
||||
* applied to any key type and key version stored in Azure Key Vault.
|
||||
|
||||
@ -71,6 +71,14 @@ namespace Azure { namespace Security { namespace KeyVault { namespace Keys {
|
||||
std::shared_ptr<Azure::Security::KeyVault::_internal::KeyVaultPipeline> keyvaultPipeline,
|
||||
Azure::Response<Azure::Security::KeyVault::Keys::KeyVaultKey> response);
|
||||
|
||||
RecoverDeletedKeyOperation(
|
||||
std::shared_ptr<Azure::Security::KeyVault::_internal::KeyVaultPipeline> keyvaultPipeline,
|
||||
std::string resumeToken)
|
||||
: m_pipeline(keyvaultPipeline), m_value(DeletedKey(resumeToken)),
|
||||
m_continuationToken(std::move(resumeToken))
|
||||
{
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Get the #Azure::Core::Http::RawResponse of the operation request.
|
||||
* @return A reference to an #Azure::Core::Http::RawResponse.
|
||||
|
||||
@ -60,11 +60,8 @@ Azure::Security::KeyVault::Keys::DeleteKeyOperation::DeleteKeyOperation(
|
||||
m_value = response.Value;
|
||||
m_rawResponse = std::move(response.RawResponse);
|
||||
|
||||
// Build the full url for continuation token. It is only used in case customers wants to use
|
||||
// it on their own. The Operation uses the KeyVaultPipeline from the client which knows how to
|
||||
// build this url.
|
||||
m_continuationToken = m_pipeline->GetVaultUrl() + "/" + std::string(_detail::DeletedKeysPath)
|
||||
+ "/" + m_value.Name();
|
||||
// The key name is enough to be used as continuation token.
|
||||
m_continuationToken = m_value.Name();
|
||||
|
||||
// The recoveryId is only returned if soft-delete is enabled.
|
||||
// The LRO is considered completed for non soft-delete (key will be eventually removed).
|
||||
|
||||
@ -202,6 +202,28 @@ Azure::Security::KeyVault::Keys::DeleteKeyOperation KeyClient::StartDeleteKey(
|
||||
{_detail::KeysPath, name}));
|
||||
}
|
||||
|
||||
Azure::Security::KeyVault::Keys::DeleteKeyOperation KeyClient::ResumeDeleteKey(
|
||||
std::string const& resumeToken,
|
||||
Azure::Core::Context const& context) const
|
||||
{
|
||||
Azure::Security::KeyVault::Keys::DeleteKeyOperation operation(m_pipeline, resumeToken);
|
||||
// Need to fix this to use context directly. See:
|
||||
// https://github.com/Azure/azure-sdk-for-cpp/issues/2091
|
||||
operation.Poll(context.GetApplicationContext());
|
||||
return operation;
|
||||
}
|
||||
|
||||
Azure::Security::KeyVault::Keys::RecoverDeletedKeyOperation KeyClient::ResumeRecoverDeletedKey(
|
||||
std::string const& resumeToken,
|
||||
Azure::Core::Context const& context) const
|
||||
{
|
||||
Azure::Security::KeyVault::Keys::RecoverDeletedKeyOperation operation(m_pipeline, resumeToken);
|
||||
// Need to fix this to use context directly. See:
|
||||
// https://github.com/Azure/azure-sdk-for-cpp/issues/2091
|
||||
operation.Poll(context.GetApplicationContext());
|
||||
return operation;
|
||||
}
|
||||
|
||||
Azure::Security::KeyVault::Keys::RecoverDeletedKeyOperation KeyClient::StartRecoverDeletedKey(
|
||||
std::string const& name,
|
||||
Azure::Core::Context const& context) const
|
||||
|
||||
@ -62,9 +62,6 @@ Azure::Security::KeyVault::Keys::RecoverDeletedKeyOperation::RecoverDeletedKeyOp
|
||||
m_value = response.Value;
|
||||
m_rawResponse = std::move(response.RawResponse);
|
||||
|
||||
// Build the full url for continuation token. It is only used in case customers wants to use
|
||||
// it on their own. The Operation uses the KeyVaultPipeline from the client which knows how to
|
||||
// build this url.
|
||||
m_continuationToken = m_pipeline->GetVaultUrl() + "/" + std::string(_detail::DeletedKeysPath)
|
||||
+ "/" + m_value.Name();
|
||||
// The key name is enough to resume the operation
|
||||
m_continuationToken = m_value.Name();
|
||||
}
|
||||
|
||||
@ -62,8 +62,7 @@ TEST_F(KeyVaultClientTest, DeleteKey)
|
||||
auto cancelToken = Azure::Core::Context::GetApplicationContext().WithDeadline(duration);
|
||||
|
||||
auto keyResponseLRO = keyClient.StartDeleteKey(keyName);
|
||||
auto expectedStatusToken = m_keyVaultUrl
|
||||
+ std::string(Azure::Security::KeyVault::Keys::_detail::DeletedKeysPath) + "/" + keyName;
|
||||
auto expectedStatusToken = keyName;
|
||||
EXPECT_EQ(keyResponseLRO.GetResumeToken(), expectedStatusToken);
|
||||
// poll each second until key is soft-deleted
|
||||
// Will throw and fail test if test takes more than 3 minutes (token cancelled)
|
||||
@ -320,3 +319,84 @@ TEST_F(KeyVaultClientTest, GetDeletedKey)
|
||||
Azure::Security::KeyVault::Keys::KeyType::KeyTypeToString(deletedKey.Key.KeyType));
|
||||
}
|
||||
}
|
||||
|
||||
TEST_F(KeyVaultClientTest, DeleteOperationResumeToken)
|
||||
{
|
||||
Azure::Security::KeyVault::Keys::KeyClient keyClient(m_keyVaultUrl, m_credential);
|
||||
auto keyName = GetUniqueName();
|
||||
|
||||
{
|
||||
auto keyResponse
|
||||
= keyClient.CreateKey(keyName, Azure::Security::KeyVault::Keys::JsonWebKeyType::Ec);
|
||||
CheckValidResponse(keyResponse);
|
||||
auto keyVaultKey = keyResponse.Value;
|
||||
EXPECT_EQ(keyVaultKey.Name(), keyName);
|
||||
}
|
||||
std::string resumeToken;
|
||||
{
|
||||
auto keyResponseLRO = keyClient.StartDeleteKey(keyName);
|
||||
resumeToken = keyResponseLRO.GetResumeToken();
|
||||
}
|
||||
// Resume operation from token
|
||||
{
|
||||
auto resumeOperation = keyClient.ResumeDeleteKey(resumeToken);
|
||||
resumeOperation.PollUntilDone(std::chrono::milliseconds(500));
|
||||
}
|
||||
{
|
||||
// recover
|
||||
auto recoverOperation = keyClient.StartRecoverDeletedKey(keyName);
|
||||
auto keyResponse = recoverOperation.PollUntilDone(std::chrono::milliseconds(500));
|
||||
auto key = keyResponse.Value;
|
||||
// Delete again for purging
|
||||
auto deleteOp = keyClient.StartDeleteKey(key.Name());
|
||||
deleteOp.PollUntilDone(std::chrono::milliseconds(200));
|
||||
}
|
||||
{
|
||||
// Purge
|
||||
auto response = keyClient.PurgeDeletedKey(keyName);
|
||||
CheckValidResponse(response, Azure::Core::Http::HttpStatusCode::NoContent);
|
||||
}
|
||||
}
|
||||
|
||||
TEST_F(KeyVaultClientTest, RecoverOperationResumeToken)
|
||||
{
|
||||
Azure::Security::KeyVault::Keys::KeyClient keyClient(m_keyVaultUrl, m_credential);
|
||||
auto keyName = GetUniqueName();
|
||||
|
||||
{
|
||||
auto keyResponse
|
||||
= keyClient.CreateKey(keyName, Azure::Security::KeyVault::Keys::JsonWebKeyType::Ec);
|
||||
CheckValidResponse(keyResponse);
|
||||
auto keyVaultKey = keyResponse.Value;
|
||||
EXPECT_EQ(keyVaultKey.Name(), keyName);
|
||||
}
|
||||
std::string resumeToken;
|
||||
{
|
||||
auto keyResponseLRO = keyClient.StartDeleteKey(keyName);
|
||||
resumeToken = keyResponseLRO.GetResumeToken();
|
||||
}
|
||||
// Resume operation from token
|
||||
{
|
||||
auto resumeOperation = keyClient.ResumeDeleteKey(resumeToken);
|
||||
resumeOperation.PollUntilDone(std::chrono::milliseconds(500));
|
||||
}
|
||||
{
|
||||
// recover
|
||||
auto recoverOperation = keyClient.StartRecoverDeletedKey(keyName);
|
||||
resumeToken = recoverOperation.GetResumeToken();
|
||||
}
|
||||
{
|
||||
// resume from token
|
||||
auto resumeRecoveryOp = keyClient.ResumeRecoverDeletedKey(resumeToken);
|
||||
auto keyResponse = resumeRecoveryOp.PollUntilDone(std::chrono::milliseconds(500));
|
||||
auto key = keyResponse.Value;
|
||||
// Delete again for purging
|
||||
auto deleteOp = keyClient.StartDeleteKey(key.Name());
|
||||
deleteOp.PollUntilDone(std::chrono::milliseconds(200));
|
||||
}
|
||||
{
|
||||
// Purge
|
||||
auto response = keyClient.PurgeDeletedKey(keyName);
|
||||
CheckValidResponse(response, Azure::Core::Http::HttpStatusCode::NoContent);
|
||||
}
|
||||
}
|
||||
|
||||
Loading…
Reference in New Issue
Block a user