Adjust WidevineEncryptionKeySource to handle timeout
Change-Id: Iac4a86acae2e522c6cfc84ce02ae7ec1dd30c47e
This commit is contained in:
parent
419d463eaa
commit
1927109818
|
@ -40,6 +40,7 @@ const int kFirstRetryDelayMilliseconds = 1000;
|
||||||
// key rotation enabled request.
|
// key rotation enabled request.
|
||||||
const int kDefaultCryptoPeriodCount = 10;
|
const int kDefaultCryptoPeriodCount = 10;
|
||||||
const int kGetKeyTimeoutInSeconds = 5 * 60; // 5 minutes.
|
const int kGetKeyTimeoutInSeconds = 5 * 60; // 5 minutes.
|
||||||
|
const int kHttpTimeoutInSeconds = 60; // 1 minute.
|
||||||
|
|
||||||
bool Base64StringToBytes(const std::string& base64_string,
|
bool Base64StringToBytes(const std::string& base64_string,
|
||||||
std::vector<uint8>* bytes) {
|
std::vector<uint8>* bytes) {
|
||||||
|
@ -129,7 +130,7 @@ WidevineEncryptionKeySource::WidevineEncryptionKeySource(
|
||||||
const std::string& policy,
|
const std::string& policy,
|
||||||
scoped_ptr<RequestSigner> signer,
|
scoped_ptr<RequestSigner> signer,
|
||||||
int first_crypto_period_index)
|
int first_crypto_period_index)
|
||||||
: http_fetcher_(new SimpleHttpFetcher()),
|
: http_fetcher_(new SimpleHttpFetcher(kHttpTimeoutInSeconds)),
|
||||||
server_url_(server_url),
|
server_url_(server_url),
|
||||||
content_id_(content_id),
|
content_id_(content_id),
|
||||||
policy_(policy),
|
policy_(policy),
|
||||||
|
@ -243,24 +244,26 @@ Status WidevineEncryptionKeySource::FetchKeys(
|
||||||
// server limitation.
|
// server limitation.
|
||||||
for (int i = 0; i < kNumTransientErrorRetries; ++i) {
|
for (int i = 0; i < kNumTransientErrorRetries; ++i) {
|
||||||
status = http_fetcher_->Post(server_url_, message, &raw_response);
|
status = http_fetcher_->Post(server_url_, message, &raw_response);
|
||||||
if (!status.ok())
|
if (status.ok()) {
|
||||||
|
VLOG(1) << "Retry [" << i << "] Response:" << raw_response;
|
||||||
|
|
||||||
|
std::string response;
|
||||||
|
if (!DecodeResponse(raw_response, &response)) {
|
||||||
|
return Status(error::SERVER_ERROR,
|
||||||
|
"Failed to decode response '" + raw_response + "'.");
|
||||||
|
}
|
||||||
|
|
||||||
|
bool transient_error = false;
|
||||||
|
if (ExtractEncryptionKey(response, &transient_error))
|
||||||
|
return Status::OK;
|
||||||
|
|
||||||
|
if (!transient_error) {
|
||||||
|
return Status(
|
||||||
|
error::SERVER_ERROR,
|
||||||
|
"Failed to extract encryption key from '" + response + "'.");
|
||||||
|
}
|
||||||
|
} else if (status.error_code() != error::TIME_OUT) {
|
||||||
return status;
|
return status;
|
||||||
VLOG(1) << "Retry [" << i << "] Response:" << raw_response;
|
|
||||||
|
|
||||||
std::string response;
|
|
||||||
if (!DecodeResponse(raw_response, &response)) {
|
|
||||||
return Status(error::SERVER_ERROR,
|
|
||||||
"Failed to decode response '" + raw_response + "'.");
|
|
||||||
}
|
|
||||||
|
|
||||||
bool transient_error = false;
|
|
||||||
if (ExtractEncryptionKey(response, &transient_error))
|
|
||||||
return Status::OK;
|
|
||||||
|
|
||||||
if (!transient_error) {
|
|
||||||
return Status(
|
|
||||||
error::SERVER_ERROR,
|
|
||||||
"Failed to extract encryption key from '" + response + "'.");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Exponential backoff.
|
// Exponential backoff.
|
||||||
|
|
|
@ -143,6 +143,20 @@ class WidevineEncryptionKeySourceTest : public ::testing::Test {
|
||||||
mock_http_fetcher_.PassAs<HttpFetcher>());
|
mock_http_fetcher_.PassAs<HttpFetcher>());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void VerifyKeys() {
|
||||||
|
EncryptionKey encryption_key;
|
||||||
|
const std::string kTrackTypes[] = {"SD", "HD", "AUDIO"};
|
||||||
|
for (size_t i = 0; i < arraysize(kTrackTypes); ++i) {
|
||||||
|
ASSERT_OK(widevine_encryption_key_source_->GetKey(
|
||||||
|
EncryptionKeySource::GetTrackTypeFromString(kTrackTypes[i]),
|
||||||
|
&encryption_key));
|
||||||
|
EXPECT_EQ(GetMockKeyId(kTrackTypes[i]), ToString(encryption_key.key_id));
|
||||||
|
EXPECT_EQ(GetMockKey(kTrackTypes[i]), ToString(encryption_key.key));
|
||||||
|
EXPECT_EQ(GetMockPsshData(kTrackTypes[i]),
|
||||||
|
GetPsshDataFromPsshBox(ToString(encryption_key.pssh)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
scoped_ptr<MockRequestSigner> mock_request_signer_;
|
scoped_ptr<MockRequestSigner> mock_request_signer_;
|
||||||
scoped_ptr<MockHttpFetcher> mock_http_fetcher_;
|
scoped_ptr<MockHttpFetcher> mock_http_fetcher_;
|
||||||
scoped_ptr<WidevineEncryptionKeySource> widevine_encryption_key_source_;
|
scoped_ptr<WidevineEncryptionKeySource> widevine_encryption_key_source_;
|
||||||
|
@ -217,18 +231,24 @@ TEST_F(WidevineEncryptionKeySourceTest, LicenseStatusOK) {
|
||||||
|
|
||||||
CreateWidevineEncryptionKeySource(kDisableKeyRotation);
|
CreateWidevineEncryptionKeySource(kDisableKeyRotation);
|
||||||
ASSERT_OK(widevine_encryption_key_source_->Initialize());
|
ASSERT_OK(widevine_encryption_key_source_->Initialize());
|
||||||
|
VerifyKeys();
|
||||||
|
}
|
||||||
|
|
||||||
EncryptionKey encryption_key;
|
TEST_F(WidevineEncryptionKeySourceTest, RetryOnHttpTimeout) {
|
||||||
const std::string kTrackTypes[] = {"SD", "HD", "AUDIO"};
|
EXPECT_CALL(*mock_request_signer_, GenerateSignature(_, _))
|
||||||
for (size_t i = 0; i < 3; ++i) {
|
.WillOnce(Return(true));
|
||||||
ASSERT_OK(widevine_encryption_key_source_->GetKey(
|
|
||||||
EncryptionKeySource::GetTrackTypeFromString(kTrackTypes[i]),
|
std::string mock_response = base::StringPrintf(
|
||||||
&encryption_key));
|
kHttpResponseFormat, Base64Encode(GenerateMockLicenseResponse()).c_str());
|
||||||
EXPECT_EQ(GetMockKeyId(kTrackTypes[i]), ToString(encryption_key.key_id));
|
|
||||||
EXPECT_EQ(GetMockKey(kTrackTypes[i]), ToString(encryption_key.key));
|
// Retry is expected on HTTP timeout.
|
||||||
EXPECT_EQ(GetMockPsshData(kTrackTypes[i]),
|
EXPECT_CALL(*mock_http_fetcher_, Post(_, _, _))
|
||||||
GetPsshDataFromPsshBox(ToString(encryption_key.pssh)));
|
.WillOnce(Return(Status(error::TIME_OUT, "")))
|
||||||
}
|
.WillOnce(DoAll(SetArgPointee<2>(mock_response), Return(Status::OK)));
|
||||||
|
|
||||||
|
CreateWidevineEncryptionKeySource(kDisableKeyRotation);
|
||||||
|
ASSERT_OK(widevine_encryption_key_source_->Initialize());
|
||||||
|
VerifyKeys();
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_F(WidevineEncryptionKeySourceTest, RetryOnTransientError) {
|
TEST_F(WidevineEncryptionKeySourceTest, RetryOnTransientError) {
|
||||||
|
@ -251,14 +271,7 @@ TEST_F(WidevineEncryptionKeySourceTest, RetryOnTransientError) {
|
||||||
|
|
||||||
CreateWidevineEncryptionKeySource(kDisableKeyRotation);
|
CreateWidevineEncryptionKeySource(kDisableKeyRotation);
|
||||||
ASSERT_OK(widevine_encryption_key_source_->Initialize());
|
ASSERT_OK(widevine_encryption_key_source_->Initialize());
|
||||||
|
VerifyKeys();
|
||||||
EncryptionKey encryption_key;
|
|
||||||
ASSERT_OK(widevine_encryption_key_source_->GetKey(
|
|
||||||
EncryptionKeySource::TRACK_TYPE_SD, &encryption_key));
|
|
||||||
EXPECT_EQ(GetMockKeyId("SD"), ToString(encryption_key.key_id));
|
|
||||||
EXPECT_EQ(GetMockKey("SD"), ToString(encryption_key.key));
|
|
||||||
EXPECT_EQ(GetMockPsshData("SD"),
|
|
||||||
GetPsshDataFromPsshBox(ToString(encryption_key.pssh)));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_F(WidevineEncryptionKeySourceTest, NoRetryOnUnknownError) {
|
TEST_F(WidevineEncryptionKeySourceTest, NoRetryOnUnknownError) {
|
||||||
|
|
Loading…
Reference in New Issue