Windows Azure Storage 之 Retry Policy (用来处理短暂性错误-Transient Fault)
在使用Windows Azure Storage Service 的时候, 通常会遇到各种各样的问题。
例如网络连接不稳定,导致请求没有发出去。删除一个Blob Container 之后又立刻创建同名的Container。
这些情况都有可能使得你的代码抛出异常。这种异常我们通常叫他:Transient Fault 翻译成中文就是短暂性异常。
处理这种异常最简单有效的途径就是过几秒钟之后再重新发送请求。
Retry Policy就是用来帮助我们完成这样一项工作的。
Retry Policy中自带三个已经封装好了可以直接使用的类,分别有着不同的重试策略。
1.LinearRetry
这个类提供一个平行线式的重试策略
![]()
上图展示了LinearRetry的重试策略。它一共重试了五次,每一次的时间间隔都是5秒,第六次由于已经超过了预设定的重试次数,所以就放弃了。
使用LinearRetry的方法如下。
static string accountName = "<storage account name>";
static string accountKey = "<storage account key>";
static void Main(string[] args)
{
var storageAccount = new CloudStorageAccount(new StorageCredentials(accountName, accountKey), true);
string blobContainerName = "temp-" + DateTime.UtcNow.Ticks;
CloudBlobClient blobClient = storageAccount.CreateCloudBlobClient();
IRetryPolicy exponentialRetryPolicy = new ExponentialRetry(TimeSpan.FromSeconds(), );
blobClient.RetryPolicy = exponentialRetryPolicy;
CloudBlobContainer blobContainer = blobClient.GetContainerReference(blobContainerName);
blobContainer.Create();
Console.WriteLine("Blob container created.");
Console.ReadLine();
}
2.ExponentialRetry
这个类提供了一个递增式的重试策略

很明显这是一个指数级别的重试策略,每一次重试的时间间隔都是之前的2倍。
使用ExponentialRetry方法如下:
static string accountName = "<storage account name>";
static string accountKey = "<storage account key>";
static void Main(string[] args)
{
var storageAccount = new CloudStorageAccount(new StorageCredentials(accountName, accountKey), true);
string blobContainerName = "temp-" + DateTime.UtcNow.Ticks;
CloudBlobClient blobClient = storageAccount.CreateCloudBlobClient();
IRetryPolicy linearRetryPolicy = new LinearRetry(TimeSpan.FromSeconds(), );
blobClient.RetryPolicy = linearRetryPolicy;
CloudBlobContainer blobContainer = blobClient.GetContainerReference(blobContainerName);
IRetryPolicy noRetryPolicy = new NoRetry();
BlobRequestOptions requestOptions = new BlobRequestOptions()
{
RetryPolicy = noRetryPolicy,
};
blobContainer.Create(requestOptions);
Console.WriteLine("Blob container created.");
Console.ReadLine();
}
3.NoRetry
这个类的重试策略就是不重试,这个策略看似矛盾,其实它是用来配合之前两种策略来使用的,当你希望一个Blob Container的所有操作都能应用重试策略,唯独Create Blob不使用重试策略的时候你就需要用到NoRetry了。 代码如下:
static string accountName = "<storage account name>";
static string accountKey = "<storage account key>";
static void Main(string[] args)
{
var storageAccount = new CloudStorageAccount(new StorageCredentials(accountName, accountKey), true);
string blobContainerName = "temp-" + DateTime.UtcNow.Ticks;
CloudBlobClient blobClient = storageAccount.CreateCloudBlobClient();
IRetryPolicy linearRetryPolicy = new LinearRetry(TimeSpan.FromSeconds(), );
blobClient.RetryPolicy = linearRetryPolicy;
CloudBlobContainer blobContainer = blobClient.GetContainerReference(blobContainerName);
IRetryPolicy noRetryPolicy = new NoRetry();
BlobRequestOptions requestOptions = new BlobRequestOptions()
{
RetryPolicy = noRetryPolicy,
};
blobContainer.Create(requestOptions);
Console.WriteLine("Blob container created.");
Console.ReadLine();
}
除了以上三个已经封装好的类以外,我们还可以自己创建自定义的重试策略类, 我们只需要实现IRetryPolicy接口即可。
实现自定义类的一个好处是可以自定义控制在何种特定情况下才进行重试。
下面代码将自定义一个实现了IRetryPolicy接口的 自定义类。
public class ContainerBeingDeletedRetryPolicy : IRetryPolicy
{
int maxRetryAttemps = 10; TimeSpan defaultRetryInterval = TimeSpan.FromSeconds(5); public ContainerBeingDeletedRetryPolicy(TimeSpan deltaBackoff, int retryAttempts)
{
maxRetryAttemps = retryAttempts;
defaultRetryInterval = deltaBackoff;
} public IRetryPolicy CreateInstance()
{
return new ContainerBeingDeletedRetryPolicy(TimeSpan.FromSeconds(2), 5);
} public bool ShouldRetry(int currentRetryCount, int statusCode, Exception lastException, out TimeSpan retryInterval, OperationContext operationContext)
{
retryInterval = defaultRetryInterval;
if (currentRetryCount >= maxRetryAttemps)
{
return false;
}
//Since we're only interested in 409 status code, let's not retry any other operation.
if ((HttpStatusCode)statusCode != HttpStatusCode.Conflict)
{
return false;
}
//We're only interested in storage exceptions so if there's any other exception, let's not retry it.
if (lastException.GetType() != typeof(StorageException))
{
return false;
}
else
{
var storageException = (StorageException)lastException;
string errorCode = storageException.RequestInformation.ExtendedErrorInformation.ErrorCode;
if (errorCode.Equals("ContainerBeingDeleted"))
{
return true;
}
else
{
return false;
}
}
return true;
}
}
使用代码如下:
static string accountName = "<storage account name>";
static string accountKey = "<storage account key>";
static void Main(string[] args)
{
var storageAccount = new CloudStorageAccount(new StorageCredentials(accountName, accountKey), true);
string blobContainerName = "temp-" + DateTime.UtcNow.Ticks;
CloudBlobClient blobClient = storageAccount.CreateCloudBlobClient();
IRetryPolicy linearRetryPolicy = new LinearRetry(TimeSpan.FromSeconds(), );
blobClient.RetryPolicy = linearRetryPolicy;
CloudBlobContainer blobContainer = blobClient.GetContainerReference(blobContainerName);
blobContainer.Create();
Console.WriteLine("Blob container created.");
blobContainer.Delete();
Console.WriteLine("Blob container deleted.");
IRetryPolicy containerBeingDeletedRetryPolicy = new ContainerBeingDeletedRetryPolicy(TimeSpan.FromSeconds(), );
BlobRequestOptions requestOptions = new BlobRequestOptions()
{
RetryPolicy = containerBeingDeletedRetryPolicy,
};
blobContainer.Create(requestOptions);
Console.WriteLine("Blob container created.");
Console.ReadLine();
}
这个类只用于处理返回409错误并且错误信息 "Blob container created." 的错误,其他错误则忽略掉了。
总结:
像上面这种,在一个方法中删除一个container并且重建同名container的情况很容易就产生 Transient Fault。
这时使用RetryPolicy就能够很好的解决这种异常了!
Windows Azure Storage 之 Retry Policy (用来处理短暂性错误-Transient Fault)的更多相关文章
- [New Portal]Windows Azure Storage (14) 使用Azure Blob的PutBlock方法,实现文件的分块、离线上传
<Windows Azure Platform 系列文章目录> 相关内容 Windows Azure Platform (二十二) Windows Azure Storage Servic ...
- [SDK2.2]Windows Azure Storage (15) 使用WCF服务,将本地图片上传至Azure Storage (上) 服务器端代码
<Windows Azure Platform 系列文章目录> 这几天工作上的内容,把项目文件和源代码拿出来给大家分享下. 源代码下载:Part1 Part2 Part3 我们在写WEB服 ...
- Windows Azure Storage (18) 使用HTML5 Portal的Azure CDN服务
<Windows Azure Platform 系列文章目录> Update:2015-04-15 如果读者使用的是国内由世纪互联运维的Azure China服务,请参考笔者的文档:Azu ...
- Windows Azure Storage (19) 再谈Azure Block Blob和Page Blob
<Windows Azure Platform 系列文章目录> 请读者在参考本文之前,预习相关背景知识:Windows Azure Storage (1) Windows Azure St ...
- Windows Azure Storage (21) 使用AzCopy工具,加快Azure Storage传输速度
<Windows Azure Platform 系列文章目录> Update 2016-09-28 想要在Azure云端,使用AzCopy工具,从Azure China 上海数据中心存储账 ...
- Windows Azure Storage (22) Azure Storage如何支持多级目录
<Windows Azure Platform 系列文章目录> 熟悉Azure平台的读者都知道,Azure Blob有三层架构.如下图:(注意blob.core.chinacloudapi ...
- Windows Azure Storage图形界面管理工具
上一篇我们介绍了用PowerShell将Windows Azure的存储服务当网盘来使用.如果感觉还不够简单,那么这次我们来看看还有哪些使用起来更方便的图形界面管理工具吧.当然,这些工具必要支持中国版 ...
- [转]探索 Windows Azure Storage
本文转自:https://msdn.microsoft.com/zh-tw/jj573842 概觀 儲存服務 (Storage services) 在 Windows Azure 運算模擬器中提供了可 ...
- Windows Azure Storage (6) Windows Azure Storage之Table
<Windows Azure Platform 系列文章目录> 最近想了想,还是有必要把Windows Azure Table Storage 给说清楚. 1.概念 Windows Azu ...
随机推荐
- AD Local Domain groups, Global groups and Universal groups
http://ss64.com/nt/syntax-groups.html Rules that govern when a group can be added to another group ( ...
- Chrome F12学习
Chrome实用调试技巧 Chrome调试工具常用功能整理 Google Chrome开发者工具使用(图文教程) 如何更专业的使用Chrome开发者工具
- NGUI 层级关系控制
NGUI元素的遮挡情况是不依赖空间关系,所以在NGUI上添加特效有时候特别蛋疼,特别是美术同学还要依赖空间关系来控制特效效果,那先看看看NGUI的层级是怎么处理的,不过下面的描述都是针对单个相机下的P ...
- frag General URL components
HTTP: The Definitive Guide 2.2.7 Fragments Some resource types, such as HTML, can be divided further ...
- jQuery 一句代码返回顶部
兼容各大主流浏览器,jQuery返回顶部,一句代码搞定 <a class="top" href="javascript:;" style="po ...
- 浅谈iOS开发中方法延迟执行的几种方式
Method1. performSelector方法 Method2. NSTimer定时器 Method3. NSThread线程的sleep Method4. GCD 公用延迟执行方法 - (vo ...
- 为什么要使用CachedRowSetImpl?
很多情况我们使用ResultSet 就会因为这样那样的问题,rs被关闭或数据链接被关闭,导致ResultSet不能使用.其实这个问题我们可以用CachedRowSetImpl来解决.我的理解是这是一个 ...
- "undefined method `root' for nil:NilClass" error when using "pod install" 解决办法
如果pod undate 的时候报错"undefined method `root' for nil:NilClass" error when using "pod in ...
- C++:C++的两种多态形式
// // main.cpp // Test.cpp // // Created by mac on 15/8/11. // Copyright (c) 2015年. All rights reser ...
- Eclipse 的单步调试(转)
1.设置断点在程序里面放置一个断点,也就是双击需要放置断点的程序左边的栏目上.2.调试(1)点击"打开透视图"按钮,选择调试透视图,则打开调试透视图界面,然后先设置断点,按调试按钮 ...