C# 我可以修改 Request.Form 变量吗?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/323265/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-03 23:11:38  来源:igfitidea点击:

Can I modify Request.Form variables?

c#request.form

提问by complez

I try Request.Form.Set(k, v)but it's throwing exception

我尝试Request.Form.Set(k, v)但它抛出异常

Collection is read-only

集合是只读的

采纳答案by annakata

This is exactly the same as modifying Request.Querystring. Both are internally complicated by private properties and what could be deemed a bug, however there are two possible solutions I'm aware of (I'll dismiss the response.redirect plan out of hand - that's terrible).

这与修改Request.Querystring. 两者都因私有属性而在内部复杂化,并且可能被视为错误,但是我知道有两种可能的解决方案(我会立即取消 response.redirect 计划 - 这太糟糕了)。

Method one is to use reflection to modify the collection directly:

方法一是直接使用反射修改集合:

NameValueCollection oQuery = Request.QueryString;
oQuery = (NameValueCollection)Request.GetType().GetField("_queryString",BindingFlags.NonPublic | BindingFlags.Instance).GetValue(Request);
PropertyInfo oReadable = oQuery .GetType().GetProperty("IsReadOnly", BindingFlags.NonPublic | BindingFlags.Instance);
oReadable.SetValue(oQuery, false, null);
oQuery["foo"] = "bar";
oReadable.SetValue(oQuery, true, null); 

Plan B, which I think lends itself better to unit testing is to avoid dealing with the collection directly and instead pass it as a NameValueCollectionto any method you want to handle it, shallow copying whatever you need out of it. I've used this myself to mock web requests.

计划 B,我认为更适合单元测试的是避免直接处理集合,而是将其作为 a 传递NameValueCollection给您想要处理它的任何方法,浅复制您需要的任何内容。我自己用它来模拟网络请求。

Edit: Marc Gravell gave more eloquent reasons for plan B

编辑:Marc Gravell 为 B 计划提供了更雄辩的理由

回答by Marc Gravell

The form is a representation of what the client sent in the request. What is it you want to do? Personally, I would try to separate the "read the form" code from the "do something with the values" code - that way, you can do any pre-processing early on (when reading from the form), and none of the later code needs to know about what was actuallysent - it just takes the values given to it (i.e. it never talks to the request directly).

表单是客户端在请求中发送的内容的表示。你想做什么?就我个人而言,我会尝试将“读取表单”代码与“对值执行某些操作”代码分开——这样,您可以在早期(从表单读取时)进行任何预处理,而不会在后期进行任何预处理代码需要知道实际发送的是什么——它只需要给它的值(即它从不直接与请求对话)。

It also means you can test your logic without the need for a form, or even an http-request at all.

这也意味着您可以测试您的逻辑,而无需表单,甚至根本不需要 http 请求。

Actually, ASP.NET MVC will do a lot of this (the above paragraph) for you...

实际上,ASP.NET MVC 会为你做很多这样的事情(上一段)......

Note that you can update the .Items collection - but this is a bit more vague (i.e. it doesn't relate specifically to the form).

请注意,您可以更新 .Items 集合 - 但这有点模糊(即它与表单无关)。