如果你想添加一些在特定条件下才会执行的过滤器,是不是很酷,但是怎么来进行呢?例如,假设你希
望将认证过滤器设置到除了用户登陆的的所有action上,看起来是个好主意吧?
现在让我们把它实现把,如果你添加一个过滤器到ClobalFilters.Filters集合中,他将会设置到所有的action中,这是一种方式,现在我们期望的是把它添加到除了某一个特定action之上时,这就会出问题了。幸运的是,MVC带有一种新的特性,我们可以写一个类来作为action过滤器来使用。本例,我们需要写一个条件动作控制器。
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web.Mvc;
public class ConditionalFilterProvider : IFilterProvider {
private readonly
IEnumerable> _conditions;
public ConditionalFilterProvider(
IEnumerable> conditions)
{
_conditions = conditions;
}
public IEnumerable GetFilters(
ControllerContext controllerContext,
ActionDescriptor actionDescriptor) {
return from condition in _conditions
select condition(controllerContext, actionDescriptor) into filter
where filter != null
select new Filter(filter, FilterScope.Global, null);
}
}
然后我们就可以这样使用:
IEnumerable> conditions = new Func [] { (c, a) => c.Controller.GetType() != typeof(HomeController) ? new MyFilter() : null, (c, a) => a.ActionName.StartsWith("About") ? new SomeFilter() : null }; var provider = new ConditionalFilterProvider(conditions); FilterProviders.Providers.Add(provider);
详细可以看英文原文
其实是自己一直避开的一个技术问题,就像线程一样,但是因为在写比赛项目的手机客户端就不得不面对
这个问题,因为需要使用我们的第三方接口来进行认证用户登陆,而且是需要使用POST进行,在WP7下有两种方式支持网络请求:webclient和webrequest,这里,webclient是比较简单的,但是有一点不太明白就是只知道get方式,而post不知道方法,后来求解得出结论是使用什么什么(忘记名字里,哎,Live writer中没有智能提示呀),而后者又比较麻烦,但是你可以较自由的定制。不管怎样异步是不能少的,估计微软也是为了用户体验的需要,及时你设置了超时,用户也是伤不起的~
这里就说下关于WP7中异步的实现方案:
private void LoadMe()
{
IsolatedStorageSettings setting = IsolatedStorageSettings.ApplicationSettings;
HttpWebRequest req = (HttpWebRequest)WebRequest.Create("http://localhost:13829/client/User/index?id=" + setting["token"]);
req.Method = "POST";
UpdateState State = new UpdateState();
State.AsyncRequest = req;
req.BeginGetResponse(new AsyncCallback(AnaRepUser), State);
}
public class UpdateState
{
public HttpWebRequest AsyncRequest { get; set; }
public HttpWebResponse AsyncResponse { get; set; }
}
private void AnaRep(IAsyncResult asyncResult)
{
UpdateState myState = (UpdateState)asyncResult.AsyncState;
HttpWebRequest myRequest = (HttpWebRequest)myState.AsyncRequest;
//结束异步请求
myState.AsyncResponse = (HttpWebResponse)myRequest.EndGetResponse(asyncResult);
Stream streamResult = myState.AsyncResponse.GetResponseStream();
DoTaskV2.WP7.DoTaskAnalytics ana = new DoTaskAnalytics();
StreamReader sr = new StreamReader(streamResult);
string xx= sr.ReadToEnd();
try
{
DoTaskV2.ClientLibiary.ErrorViewModels err = ana.ErrorMessage(xx);
if (err.id != "00") { this.Dispatcher.BeginInvoke(() => { MessageBox.Show(err.message); }); }
}
catch
{
List err = ana.AnaTask(xx);
this.Dispatcher.BeginInvoke(() =>
{
this.g1.DataContext = err;
});
}
}
这里,其实让自己比较不爽的就是在异步以后,你需要调用当前的dispacher来进行设置,否者就是跨线程调用对象,这是不允许的~这里的匿名方法自然少不了~
问题解决后就开始抱怨:
1 异步执行你不知道结果什么时候返回,以前的过程式编程方式需要进行比较大的修改。
2 异步其实就是多一个线程来执行,这样必然造成异步以后的线程间传递数据问题。
但是异步帮助我们解决了界面假死问题,让程序更流程这是毋庸置疑的~
其实,对异步微软的Asyn发布的CTP貌似做了一些改进,可惜以前同时安装MVC3和Asyn以后VS就会出问题,不知道微软把这个小bug解决没~
额,突然想到了一种异步的解决方式,试下~结果以后告知