-
Notifications
You must be signed in to change notification settings - Fork 44
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Exposing new constructor to blob_client. #54
base: master
Are you sure you want to change the base?
Changes from 3 commits
11ccadb
3ce274e
f80fd9e
9abb3b9
971ba3b
39ed702
72a7b46
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -78,27 +78,39 @@ namespace azure { namespace storage_lite { | |
class retry_policy final : public retry_policy_base | ||
{ | ||
public: | ||
|
||
retry_policy(const int maximum_retries = 3, const std::chrono::seconds base_timeout = std::chrono::seconds{10}) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Please make the There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Done, please re-check |
||
: m_maximum_retries(maximum_retries), | ||
m_base_timeout(base_timeout) | ||
{ | ||
} | ||
|
||
retry_info evaluate(const retry_context &context) const override | ||
{ | ||
if (context.numbers() == 0) | ||
{ | ||
return retry_info(true, std::chrono::seconds(0)); | ||
} | ||
else if (context.numbers() < 26 && can_retry(context.result())) | ||
if (context.numbers() >= m_maximum_retries || | ||
!can_retry(context.result())) | ||
{ | ||
double delay = (pow(1.2, context.numbers()-1)-1); | ||
delay = std::min(delay, 60.0); // Maximum backoff delay of 1 minute | ||
delay *= (((double)rand())/RAND_MAX)/2 + 0.75; | ||
return retry_info(true, std::chrono::seconds((int)delay)); | ||
return retry_info(false, std::chrono::seconds(0)); | ||
} | ||
return retry_info(false, std::chrono::seconds(0)); | ||
|
||
return retry_info(true, calculate_new_delay(context)); | ||
} | ||
|
||
private: | ||
bool can_retry(http_base::http_code code) const | ||
{ | ||
return retryable(code); | ||
} | ||
|
||
std::chrono::seconds calculate_new_delay(const retry_context &context) const | ||
{ | ||
// (1 << N) == 2^N | ||
return ((context.numbers() == 0) ? std::chrono::seconds(0) | ||
: (m_base_timeout * (1 << context.numbers()))); | ||
} | ||
|
||
const int m_maximum_retries; | ||
const std::chrono::seconds m_base_timeout; | ||
}; | ||
|
||
}} // azure::storage_lite | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -75,7 +75,7 @@ storage_outcome<chunk_property> blob_client::get_chunk_to_stream_sync(const std: | |
property.etag = http->get_response_header(constants::header_etag); | ||
property.totalSize = get_length_from_content_range(http->get_response_header(constants::header_content_range)); | ||
std::istringstream(http->get_response_header(constants::header_content_length)) >> property.size; | ||
property.last_modified = curl_getdate(http->get_response_header(constants::header_last_modified).c_str(), NULL); | ||
property.last_modified = curl_getdate(http->get_response_header(constants::header_last_modified).c_str(), nullptr); | ||
return storage_outcome<chunk_property>(property); | ||
} | ||
return storage_outcome<chunk_property>(storage_error(response.error())); | ||
|
@@ -196,12 +196,13 @@ std::future<storage_outcome<container_property>> blob_client::get_container_prop | |
container_property properties(true); | ||
properties.etag = http->get_response_header(constants::header_etag); | ||
|
||
auto& headers = http->get_response_headers(); | ||
for (auto iter = headers.begin(); iter != headers.end(); ++iter) | ||
const auto& headers = http->get_response_headers(); | ||
properties.metadata.reserve(headers.size()); | ||
for (const auto& header : headers) | ||
{ | ||
if (iter->first.find(constants::header_ms_meta_prefix) == 0) | ||
if (header.first.find(constants::header_ms_meta_prefix) == 0) | ||
{ | ||
properties.metadata.push_back(std::make_pair(iter->first.substr(constants::header_ms_meta_prefix_size), iter->second)); | ||
properties.metadata.emplace_back(header.first.substr(constants::header_ms_meta_prefix_size), header.second); | ||
} | ||
} | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This code is duplicated with There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @katmsft I'm not sure I agree with you. Since this piece of code is processing properties and metadata. Properties for file/blob container/blob might be different. So I think it's also okay to leave it as it is. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The best solution for this is to use a transform_if algorithm, but it is not in the STL. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @JinmingHu-MSFT You are absolutely right about the properties being different. What I was suggesting was the logic of extracting metadata from the headers. This is universal for blob/container/file/share/directory, potentially there will be 5 places that shares the same code logic. |
||
return storage_outcome<container_property>(properties); | ||
|
@@ -275,21 +276,22 @@ std::future<storage_outcome<blob_property>> blob_client::get_blob_properties(con | |
properties.content_type = http->get_response_header(constants::header_content_type); | ||
properties.etag = http->get_response_header(constants::header_etag); | ||
properties.copy_status = http->get_response_header(constants::header_ms_copy_status); | ||
properties.last_modified = curl_getdate(http->get_response_header(constants::header_last_modified).c_str(), NULL); | ||
properties.last_modified = curl_getdate(http->get_response_header(constants::header_last_modified).c_str(), nullptr); | ||
std::string::size_type sz = 0; | ||
std::string contentLength = http->get_response_header(constants::header_content_length); | ||
if (contentLength.length() > 0) | ||
{ | ||
properties.size = std::stoull(contentLength, &sz, 0); | ||
} | ||
|
||
auto& headers = http->get_response_headers(); | ||
for (auto iter = headers.begin(); iter != headers.end(); ++iter) | ||
const auto& headers = http->get_response_headers(); | ||
properties.metadata.reserve(headers.size()); | ||
for (const auto& header : headers) | ||
{ | ||
if (iter->first.find(constants::header_ms_meta_prefix) == 0) | ||
if (header.first.find(constants::header_ms_meta_prefix) == 0) | ||
{ | ||
// We need to strip ten characters from the front of the key to account for "x-ms-meta-". | ||
properties.metadata.push_back(std::make_pair(iter->first.substr(constants::header_ms_meta_prefix_size), iter->second)); | ||
properties.metadata.emplace_back(header.first.substr(constants::header_ms_meta_prefix_size), header.second); | ||
} | ||
} | ||
return storage_outcome<blob_property>(properties); | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
client
should be internal logic that is not exposed to customers. Please make the 3rd argumentint max_concurrency
instead.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I left the ctor with client for future tests and to join all the ctor logics in to one flow, however it is private so the customer will not use it.
Please recheck and share your thoughts.