手机版

HttpRequest的查询字符串属性的一点认识

时间:2021-10-07 来源:互联网 编辑:宝哥软件园 浏览:

当然我们一般都是按照提示来把结构版本设置2.0来解决。为什么可以这么解决了,还有没有其它的解决方法了。先让我们看看查询字符串的源代码吧:复制代码代码如下:公共名称值集合查询字符串{ get { if(this ._queryString==null) { this ._查询字符串=new HttpValueCollection();如果(这个_wr!=null) {这个.FillInQueryStringCollection();}这个_queryString .MakeReadOnly();}如果(这个_flags[1]) {这._旗帜.清晰(1);这个ValidateNameValueCollection(此. queryString,RequestValidationSource .查询字符串);}退回这个{ private void FillInQueryStringCollection(){ byte[]queryStringBytes=this .query string bytes if(query string bytes!=null) { if (queryStringBytes .长度!=0) {这个._queryString .fillforencodedbytes(查询字符串字节,这个查询字符串编码);} } else if(!字符串IsNullOrEmpty(这. query string text)){ 0这个_queryString .FillFromString(这个. QueryStringText,真,这个查询字符串编码);} } 先让我们插入一点那就是查询字符串默认已经做了全球资源定位器(统一资源定位符)解码。其中httpalucolecollection的FillFromEncodedBytes方法如下复制代码代码如下:内部void fillforencodedbytes(byte[]字节,Encoding Encoding){ int num=(字节!=null)?字节。长度: 0;for(int I=0;I NuMi){ string str;字符串str2这个throwifmaxhttpcollectionkeysexcluded();int offset=I;int num 4=-1;while(I num){ byte num 5=bytes[I];if(num 5==0x3d){ if(num 4 0){ num 4=I;} } else if(num 5==0x 26){ break;}我;} if(num 4=0){ str=Httputity .UrlDecode(字节,偏移量,num4 -偏移量,编码);str2=HttpUtility .UrlDecode(字节,num 4-1,(i - num4) - 1,编码);} else { str=nullstr2=HttpUtility .UrlDecode(字节、偏移量我偏移量、编码);}基地添加(字符串,字符串2);if ((i==(num - 1))(字节[i]==0x26)) { base .添加(空,字符串。空的);} } } 从这里我们可以看到查询字符串已经为我们做了解码工作,我们不需要写成HttpUtility .超文本标记语言解码(请求QueryString['xxx'])而是直接写成请求查询字符串['xxx']就好的了。现在让我们来看看你查询字符串的验证,在代码中有复制代码代码如下: if(这个_flags[1]) {这._旗帜.清晰(1);这个ValidateNameValueCollection(此. queryString,RequestValidationSource .查询字符串);} 一看这个ValidateNameValueCollection这个方法名称就知道是干什么的了,验证查询字符串数据;那么在什么情况下验证的了?让我们看看这个。_标志[1]在什么地方设置的:复制代码代码如下: public void ValidateInput(){ if(!这个_ flags[0x 8000]){ 0这旗帜.set(0x 8000);这个旗帜.集合(1);这个旗帜.集合(2);这个旗帜.集合(4);这个旗帜.set(0x 40);这个旗帜.set(0x 80);这个旗帜.set(0x 100);这个旗帜.set(0x 200);这个旗帜.集(8);} } 而该方法在ValidateInputIfRequiredByConfig中调用,调用代码复制代码代码如下:内部无效validateinputrequiredbyconfig(){ 0..if (httpRuntime .RequestValidationMode=version util .框架40) {这个ValidateInput();} } 我想现在大家都应该明白为什么错题提示让我们把结构改为2.0了吧。应为在4.0后才验证。

这种解决问题的方法是关闭验证,那么我们是否可以改变默认的验证规则了?让我们看看ValidateNameValueCollection复制代码代码如下: private void ValidateNameValueCollection(名称值集合NVC,请求验证资源请求集合){ int count=NVC .计数;for(int I=0;我数;i ) {字符串键=nvc .GetKey(I);if ((key==null) ||!钥匙以(' _ _ '开头,字符串比较.序数)){字符串str2=nvc .得到(我);if(!字符串IsNullOrEmpty(str2)) {这个.ValidateString(str2,key,请求集合);} } } } private void ValidateString(字符串值,字符串collectionKey,RequestValidationSource请求集合){ int numvalue=RemoveNullCharacters(值);if(!RequestValidator .当前。IsValidRequestString(此。上下文、值、requestCollection、collectionKey、out num)){ string str=collection key '=\ ';int startIndex=num-10;if(startIndex=0){ startIndex=0;} else { str=str '.} int长度=num 20if(长度=值。长度){长度=值。长度;字符串=字符串值。子字符串(startIndex,length-startIndex)" \ ";} else { str=str值。子字符串(开始索引,长度-开始索引).\'';}字符串requestValidationSourceName=GetRequestValidationSourceName(requestCollection);引发新的http requestvalidationexception(SR . GetString(' Dangerous _ input _ detected ',new object[]{ RequestvalidationSourceName,str });} } 哦?原来一切都明白了,验证是在RequestValidator做的。复制代码代码如下:公共类请求验证程序{//字段私有静态请求验证器_自定义验证器;私有静态只读LazyRequestValidator _ customValidatorresolver=new LazyRequestValidator(new Funcrequestvalidator(RequestValidator .getcustomvalidatorfromconfig));//方法私有静态RequestValidator getcustomvalidatorfromconfig(){ Httpruntimesection Httpruntimeconfig=Runtimeconfig .GetAppConfig().HttpRuntime类型用户基本类型=配置1 .GetType(httpRuntime .RequestValidationType,' requestValidationType ',httpRuntime);配置工具CheckBaseType(类型为(RequestValidator),userBaseType,‘RequestValidationType’,HttpRuntime);返回(RequestValidator) HttpRuntime .createpublic实例(UserBasetype);}内部静态void InitializeOnFirstRequest(){ RequestValidator local 1=_ customValidatorResolver .价值;}私有静态bool IsAtoZ(char c){ return(((c=' A ')(c=' Z ')| |((c=' A ')(c=' Z '));}受保护的内部虚拟bool是有效的请求字符串(HttpContext上下文,字符串值,RequestValidationSource RequestValidationSource,字符串集合键,out int validation failure index){ if(RequestValidationSource==RequestValidationSource .headers){ validation failure index=0;返回真;}返回!交叉描述验证.IsDangerousString(值,out validationfailure索引);}//Properties公共静态请求验证程序当前{ get { if(_ custom validator==null){ _ custom validator=_ custom validator resolver .价值;} return _ customValidator}设置{ if(值==null)}抛出新的ArgumentNullException('值');} _ customValidator=value} } }主要的验证方法还是在交叉描述验证.IsDangerousString(值,out validationfailure索引);而交叉站点描述验证是一个内部类,无法修改。

让我们看看交叉站点描述验证类大代码把复制代码代码如下:内部静态类CrossSiteScriptingValidation {//字段私有静态字符[]起始字符=新字符[]{ " "," " };//方法私有静态bool IsAtoZ(char c){ return((c=' A ')(c=' Z ')| |((c=' A ')(c=' Z '));}内部静态bool IsDangerousString(字符串s,out int match index){ match index=0;int startIndex=0;while(true){ int num 2=s . IndexOfAny(起始字符,startIndex);if(num 2 0){ return false;} if(num 2==(s . Length-1)){ return false;} MatchIndex=num 2 char ch=s[num 2];if (ch!=' '){ if((ch==' ')((IsAtoZ(s[num 2 1]))| |(s[num 2 1]=='!'))| |((s[num 21]=='/')| |(s[num 21]=='?')))){返回true } } else if(s[num 2 1]==' # '){ return true;} startIndex=num 2 1;} }内部静态bool IsDangerousUrl(字符串){ if(字符串IsNullOrEmpty(){ return false;} s=s . Trim();整数长度=秒长度;if((((长度4)((S[0]=' H ')| |(S[0]=' H ')((S[1]=' T ')|(S[1]=' T ')((S[2]=' T ')|(S[2]=' T ')|(S[3]=' P ')|(S[3]=' P '))((S[4]=' : ')|(长度5)()} if(s . IndexOf(' : ')==-1){ return false;}返回真}内部静态bool IsValidJavascriptId(字符串id) { if(!字符串IsNullOrEmpty(id)){ 0返回代码生成器is valid language independentifier(id);}返回真实} }结果我们发现!/?[a-zA-z]这些情况验证都是通不过的。所以我们只需要重写RequestValidator就可以了。例如我们现在需要处理我们现在需要过滤查询字符串中k=.的情况复制代码代码如下:公共类CustRequestValidator : RequestValidator { 0受保护的重写bool是有效的requeststring(HttpContext上下文,字符串值,RequestValidationSource RequestValidationSource,字符串集合键out int validation failure index){ validation failure index=0;//我们现在需要过滤查询字符串中k=.的情况if(requestValidationSource==requestValidationSource .查询字符串集合键。等于(' k ')值启动开关(" " {)返回真}返回基地IsValidRequestString(上下文、值、requestValidationSource、collectionKey、out validationfailure索引);} } Httpruntime requestvalidationTYPe=' MVCapp .CustRequestValidator'/个人在这里只是提供一个思想,欢迎大家拍砖!

版权声明:HttpRequest的查询字符串属性的一点认识是由宝哥软件园云端程序自动收集整理而来。如果本文侵犯了你的权益,请联系本站底部QQ或者邮箱删除。