Secure your code as it's written. Use Snyk Code to scan source code in minutes - no build needed - and fix issues immediately.
public async sendRequest(request: WebResource): Promise {
this.tryCount++;
this.requestStartTime = new Date();
if (this.tryCount === 1) {
this.operationStartTime = this.requestStartTime;
}
this.log(HttpPipelineLogLevel.INFO, `==> OUTGOING REQUEST (Try number=${this.tryCount}):`);
this.log(HttpPipelineLogLevel.INFO, ` ${request.method}: ${sanitizeURL(request.url)}`);
try {
const response = await this._nextPolicy.sendRequest(request);
const requestEndTime = new Date();
const requestCompletionTime = requestEndTime.getTime() - this.requestStartTime.getTime();
const operationDuration = requestEndTime.getTime() - this.operationStartTime.getTime();
let currentLevel: HttpPipelineLogLevel = HttpPipelineLogLevel.INFO;
let logMessage: string = "";
if (this.shouldLog(HttpPipelineLogLevel.INFO)) {
// Assume success and default to informational logging.
logMessage = "Successfully Received Response. ";
}
// If the response took too long, we'll upgrade to warning.
this.logf(
HttpPipelineLogLevel.INFO,
`RetryPolicy: Network error ${retriableError} found, will retry.`
);
return true;
}
}
}
// If attempt was against the secondary & it returned a StatusNotFound (404), then
// the resource was not found. This may be due to replication delay. So, in this
// case, we'll never try the secondary again for this operation.
if (response || err) {
const statusCode = response ? response.status : err ? err.statusCode : 0;
if (!isPrimaryRetry && statusCode === 404) {
this.logf(HttpPipelineLogLevel.INFO, `RetryPolicy: Secondary access with 404, will retry.`);
return true;
}
// Server internal error or server timeout
if (statusCode === 503 || statusCode === 500) {
this.logf(
HttpPipelineLogLevel.INFO,
`RetryPolicy: Will retry for status code ${statusCode}.`
);
return true;
}
}
return false;
}
public async sendRequest(request: WebResource): Promise {
this.tryCount++;
this.requestStartTime = new Date();
if (this.tryCount === 1) {
this.operationStartTime = this.requestStartTime;
}
this.log(HttpPipelineLogLevel.INFO, `==> OUTGOING REQUEST (Try number=${this.tryCount}):`);
this.log(HttpPipelineLogLevel.INFO, ` ${request.method}: ${sanitizeURL(request.url)}`);
try {
const response = await this._nextPolicy.sendRequest(request);
const requestEndTime = new Date();
const requestCompletionTime = requestEndTime.getTime() - this.requestStartTime.getTime();
const operationDuration = requestEndTime.getTime() - this.operationStartTime.getTime();
let currentLevel: HttpPipelineLogLevel = HttpPipelineLogLevel.INFO;
let logMessage: string = "";
if (this.shouldLog(HttpPipelineLogLevel.INFO)) {
// Assume success and default to informational logging.
logMessage = "Successfully Received Response. ";
}
const isPrimaryRetry = true; // File doesn't suport secondary endpoint
// Set the server-side timeout query parameter "timeout=[seconds]"
if (this.retryOptions.tryTimeoutInMs) {
newRequest.url = setURLParameter(
newRequest.url,
URLConstants.Parameters.TIMEOUT,
Math.floor(this.retryOptions.tryTimeoutInMs! / 1000).toString()
);
}
let response: HttpOperationResponse | undefined;
try {
this.logf(
HttpPipelineLogLevel.INFO,
`RetryPolicy: =====> Try=${attempt} ${isPrimaryRetry ? "Primary" : "Secondary"}`
);
response = await this._nextPolicy.sendRequest(newRequest);
if (!this.shouldRetry(isPrimaryRetry, attempt, response)) {
return response;
}
secondaryHas404 = secondaryHas404 || (!isPrimaryRetry && response.status === 404);
} catch (err) {
this.logf(
HttpPipelineLogLevel.ERROR,
`RetryPolicy: Caught error, message: ${err.message}, code: ${err.code}`
);
if (!this.shouldRetry(isPrimaryRetry, attempt, response, err)) {
throw err;
}
this.requestStartTime = new Date();
if (this.tryCount === 1) {
this.operationStartTime = this.requestStartTime;
}
this.log(HttpPipelineLogLevel.INFO, `==> OUTGOING REQUEST (Try number=${this.tryCount}):`);
this.log(HttpPipelineLogLevel.INFO, ` ${request.method}: ${sanitizeURL(request.url)}`);
try {
const response = await this._nextPolicy.sendRequest(request);
const requestEndTime = new Date();
const requestCompletionTime = requestEndTime.getTime() - this.requestStartTime.getTime();
const operationDuration = requestEndTime.getTime() - this.operationStartTime.getTime();
let currentLevel: HttpPipelineLogLevel = HttpPipelineLogLevel.INFO;
let logMessage: string = "";
if (this.shouldLog(HttpPipelineLogLevel.INFO)) {
// Assume success and default to informational logging.
logMessage = "Successfully Received Response. ";
}
// If the response took too long, we'll upgrade to warning.
if (requestCompletionTime >= this.loggingOptions.logWarningIfTryOverThreshold) {
// Log a warning if the try duration exceeded the specified threshold.
if (this.shouldLog(HttpPipelineLogLevel.WARNING)) {
currentLevel = HttpPipelineLogLevel.WARNING;
logMessage = `SLOW OPERATION. Duration > ${this.loggingOptions.logWarningIfTryOverThreshold} ms. `;
}
}
if (
protected shouldRetry(
isPrimaryRetry: boolean,
attempt: number,
response?: HttpOperationResponse,
err?: RestError
): boolean {
if (attempt >= this.retryOptions.maxTries!) {
this.logf(
HttpPipelineLogLevel.INFO,
`RetryPolicy: Attempt(s) ${attempt} >= maxTries ${this.retryOptions
.maxTries!}, no further try.`
);
return false;
}
// Handle network failures, you may need to customize the list when you implement
// your own http client
const retriableErrors = [
"ETIMEDOUT",
"ESOCKETTIMEDOUT",
"ECONNREFUSED",
"ECONNRESET",
"ENOENT",
"ENOTFOUND",
"TIMEOUT",
public async sendRequest(request: WebResource): Promise {
this.tryCount++;
this.requestStartTime = new Date();
if (this.tryCount === 1) {
this.operationStartTime = this.requestStartTime;
}
let safeURL: string = request.url;
if (getURLParameter(safeURL, URLConstants.Parameters.SIGNATURE)) {
safeURL = setURLParameter(safeURL, URLConstants.Parameters.SIGNATURE, "*****");
}
this.log(
HttpPipelineLogLevel.INFO,
`'${safeURL}'==> OUTGOING REQUEST (Try number=${this.tryCount}).`
);
try {
const response = await this._nextPolicy.sendRequest(request);
const requestEndTime = new Date();
const requestCompletionTime = requestEndTime.getTime() - this.requestStartTime.getTime();
const operationDuration = requestEndTime.getTime() - this.operationStartTime.getTime();
let currentLevel: HttpPipelineLogLevel = HttpPipelineLogLevel.INFO;
let logMessage: string = "";
if (this.shouldLog(HttpPipelineLogLevel.INFO)) {
// Assume success and default to informational logging.
logMessage = "Successfully Received Response. ";
}
"TIMEOUT",
"REQUEST_SEND_ERROR" // For default xhr based http client provided in ms-rest-js
];
if (err) {
for (const retriableError of retriableErrors) {
if (
err.name.toUpperCase().includes(retriableError) ||
err.message.toUpperCase().includes(retriableError) ||
(err.code &&
err.code
.toString()
.toUpperCase()
.includes(retriableError))
) {
this.logf(
HttpPipelineLogLevel.INFO,
`RetryPolicy: Network error ${retriableError} found, will retry.`
);
return true;
}
}
}
// If attempt was against the secondary & it returned a StatusNotFound (404), then
// the resource was not found. This may be due to replication delay. So, in this
// case, we'll never try the secondary again for this operation.
if (response || err) {
const statusCode = response ? response.status : err ? err.statusCode : 0;
if (!isPrimaryRetry && statusCode === 404) {
this.logf(HttpPipelineLogLevel.INFO, `RetryPolicy: Secondary access with 404, will retry.`);
return true;
}
"TIMEOUT",
"REQUEST_SEND_ERROR" // For default xhr based http client provided in ms-rest-js
];
if (err) {
for (const retriableError of retriableErrors) {
if (
err.name.toUpperCase().includes(retriableError) ||
err.message.toUpperCase().includes(retriableError) ||
(err.code &&
err.code
.toString()
.toUpperCase()
.includes(retriableError))
) {
this.logf(
HttpPipelineLogLevel.INFO,
`RetryPolicy: Network error ${retriableError} found, will retry.`
);
return true;
}
}
}
// If attempt was against the secondary & it returned a StatusNotFound (404), then
// the resource was not found. This may be due to replication delay. So, in this
// case, we'll never try the secondary again for this operation.
if (response || err) {
const statusCode = response ? response.status : err ? err.statusCode : 0;
if (!isPrimaryRetry && statusCode === 404) {
this.logf(HttpPipelineLogLevel.INFO, `RetryPolicy: Secondary access with 404, will retry.`);
return true;
}
switch (this.retryOptions.retryPolicyType) {
case StorageRetryPolicyType.EXPONENTIAL:
delayTimeInMs = Math.min(
(Math.pow(2, attempt - 1) - 1) * this.retryOptions.retryDelayInMs!,
this.retryOptions.maxRetryDelayInMs!
);
break;
case StorageRetryPolicyType.FIXED:
delayTimeInMs = this.retryOptions.retryDelayInMs!;
break;
}
} else {
delayTimeInMs = Math.random() * 1000;
}
this.logf(HttpPipelineLogLevel.INFO, `RetryPolicy: Delay for ${delayTimeInMs}ms`);
return delay(delayTimeInMs, abortSignal, RETRY_ABORT_ERROR);
}
}