Skip to content

Commit 4ae783b

Browse files
fix lob failures, retry on any unknown curl error
1 parent 10f4db4 commit 4ae783b

File tree

2 files changed

+53
-40
lines changed

2 files changed

+53
-40
lines changed

lib/http_perform.c

Lines changed: 52 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -512,28 +512,58 @@ sf_bool STDCALL http_perform(CURL *curl,
512512
if (curl_error_buffer[0] != '\0') {
513513
log_error("curl error buffer: %s", curl_error_buffer);
514514
}
515-
if (res == CURLE_COULDNT_CONNECT && curl_retry_ctx.retry_count <
516-
(unsigned)retry_on_curle_couldnt_connect_count)
515+
if (res == CURLE_COULDNT_CONNECT &&
516+
curl_retry_ctx.retry_count < (unsigned)retry_on_curle_couldnt_connect_count)
517+
{
518+
retry = SF_BOOLEAN_TRUE;
519+
uint32 next_sleep_in_secs = retry_ctx_next_sleep(&curl_retry_ctx);
520+
log_error(
521+
"curl_easy_perform() failed connecting to server on attempt %d, "
522+
"will retry after %d second",
523+
curl_retry_ctx.retry_count,
524+
next_sleep_in_secs);
525+
sf_sleep_ms(next_sleep_in_secs*1000);
526+
} else if ((res == CURLE_OPERATION_TIMEDOUT) &&
527+
((renew_timeout > 0) && (curl_timeout == renew_timeout)))
528+
// retry directly without backoff when timeout is triggered by renew
529+
{
530+
retry = SF_BOOLEAN_TRUE;
531+
}
532+
// retry with backoff on any other curl error except particular non-retryable ones
533+
else {
534+
char msg[1024];
535+
if (res == CURLE_SSL_CACERT_BADFILE) {
536+
sf_sprintf(msg, sizeof(msg), "curl_easy_perform() failed. err: %s, CA Cert file: %s",
537+
curl_easy_strerror(res), CA_BUNDLE_FILE ? CA_BUNDLE_FILE : "Not Specified");
538+
msg[sizeof(msg) - 1] = (char)0;
539+
log_error(msg);
540+
SET_SNOWFLAKE_ERROR(error, SF_STATUS_ERROR_CURL,
541+
msg,
542+
SF_SQLSTATE_UNABLE_TO_CONNECT);
543+
}
544+
else if (res == CURLE_SSL_INVALIDCERTSTATUS) {
545+
log_error("Detected CURLE_SSL_INVALIDCERTSTATUS (91) - likely OCSP/CRL validation failure.");
546+
SET_SNOWFLAKE_ERROR(error, SF_STATUS_ERROR_CURL,
547+
msg,
548+
SF_SQLSTATE_UNABLE_TO_CONNECT);
549+
}
550+
else if (res == CURLE_PEER_FAILED_VERIFICATION)
517551
{
518-
retry = SF_BOOLEAN_TRUE;
519-
uint32 next_sleep_in_secs = retry_ctx_next_sleep(&curl_retry_ctx);
520-
log_error(
521-
"curl_easy_perform() failed connecting to server on attempt %d, "
522-
"will retry after %d second",
523-
curl_retry_ctx.retry_count,
524-
next_sleep_in_secs);
525-
sf_sleep_ms(next_sleep_in_secs*1000);
526-
} else if ((res == CURLE_OPERATION_TIMEDOUT) ||
527-
(res == CURLE_PARTIAL_FILE)) {
528-
// retry directly without backoff when timeout is triggered by renew
529-
if ((res == CURLE_OPERATION_TIMEDOUT) &&
530-
(renew_timeout > 0) && (curl_timeout == renew_timeout))
531-
{
532-
retry = SF_BOOLEAN_TRUE;
533-
}
534-
// otherwise retry with backoff
535-
else if (((uint64)(time(NULL) - elapsedRetryTime) < curl_retry_ctx.retry_timeout) &&
536-
((retry_max_count <= 0) || (curl_retry_ctx.retry_count < (unsigned)retry_max_count)))
552+
sf_sprintf(msg, sizeof(msg), "curl_easy_perform() failed: %s", curl_easy_strerror(res));
553+
msg[sizeof(msg) - 1] = (char)0;
554+
log_error(msg);
555+
SET_SNOWFLAKE_ERROR(error, SF_STATUS_ERROR_CURL,
556+
msg,
557+
SF_SQLSTATE_UNABLE_TO_CONNECT);
558+
}
559+
// otherwise retry with backoff
560+
else {
561+
sf_sprintf(msg, sizeof(msg), "curl_easy_perform() failed: %s", curl_easy_strerror(res));
562+
msg[sizeof(msg) - 1] = (char)0;
563+
log_warn(msg);
564+
565+
if (((uint64)(time(NULL) - elapsedRetryTime) < curl_retry_ctx.retry_timeout) &&
566+
((retry_max_count <= 0) || (curl_retry_ctx.retry_count < (unsigned)retry_max_count)))
537567
{
538568
uint32 next_sleep_in_secs = retry_ctx_next_sleep(&curl_retry_ctx);
539569
log_debug(
@@ -553,24 +583,7 @@ sf_bool STDCALL http_perform(CURL *curl,
553583
SF_SQLSTATE_UNABLE_TO_CONNECT);
554584
}
555585
}
556-
else {
557-
char msg[1024];
558-
if (res == CURLE_SSL_CACERT_BADFILE) {
559-
sf_sprintf(msg, sizeof(msg), "curl_easy_perform() failed. err: %s, CA Cert file: %s",
560-
curl_easy_strerror(res), CA_BUNDLE_FILE ? CA_BUNDLE_FILE : "Not Specified");
561-
}
562-
else {
563-
sf_sprintf(msg, sizeof(msg), "curl_easy_perform() failed: %s", curl_easy_strerror(res));
564-
}
565-
msg[sizeof(msg)-1] = (char)0;
566-
log_error(msg);
567-
if (res == CURLE_SSL_INVALIDCERTSTATUS) {
568-
log_error("Detected CURLE_SSL_INVALIDCERTSTATUS (91) - likely OCSP/CRL validation failure.");
569-
}
570-
SET_SNOWFLAKE_ERROR(error, SF_STATUS_ERROR_CURL,
571-
msg,
572-
SF_SQLSTATE_UNABLE_TO_CONNECT);
573-
}
586+
}
574587
} else {
575588
if (curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &http_code) !=
576589
CURLE_OK) {

tests/test_simple_put.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -123,7 +123,7 @@ void test_simple_put_core(const char * fileName,
123123
if (!connection) {
124124
sf = setup_snowflake_connection();
125125
// extend timeout to fix possible timeout failure
126-
int64 timeout = 600;
126+
int64 timeout = 1200;
127127
snowflake_set_attribute(sf, SF_CON_NETWORK_TIMEOUT, &timeout);
128128
snowflake_set_attribute(sf, SF_CON_RETRY_TIMEOUT, &timeout);
129129
status = snowflake_connect(sf);

0 commit comments

Comments
 (0)