C# 在 ASP.NET 中转换/访问 QueryString 值

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/604480/
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-04 10:01:18  来源:igfitidea点击:

Converting/accessing QueryString values in ASP.NET

c#.netasp.net

提问by Nick

I'm curious what everyone does for handling/abstracting the QueryString in ASP.NET. In some of our web apps I see a lot of this all over the site:

我很好奇每个人都在处理/抽象 ASP.NET 中的 QueryString 时做了什么。在我们的一些网络应用程序中,我在整个网站上看到了很多这样的内容:

int val = 0;
if(Request.QueryString["someKey"] != null)
{
val = Convert.ToInt32(Request.QueryString["someKey"]);
}

What are some better ways to handle this grossness?

有什么更好的方法来处理这种粗俗?

采纳答案by 7wp

I tend to like the idea of abstracting them as properties. For example:

我倾向于将它们抽象为属性的想法。例如:

        public int age { 
        get
        {
            if (Request.QueryString["Age"] == null)
                return 0;
            else
                return int.Parse(Request.QueryString["Age"]);                                    
        }
    }

You could add more validation if you wanted to. But I tend to like wrapping all of my query string variables this way.

如果您愿意,可以添加更多验证。但我倾向于以这种方式包装我所有的查询字符串变量。

EDIT: --- Also as another poster pointed out that you have to create these properties on every page. My answer is no you do not. You can create these properties in a single class that you can call "QueryStrings" or something. Then you can instantiate this class in every page where you want to access your query strings, then you can simply do something like

编辑: --- 也正如另一位海报指出的那样,您必须在每个页面上创建这些属性。我的回答是不,你没有。您可以在单个类中创建这些属性,您可以将其称为“QueryStrings”或其他东西。然后,您可以在要访问查询字符串的每个页面中实例化此类,然后您可以简单地执行以下操作

var queryStrings = new QueryStrings();
var age = queryStrings.age;

This way you can encapsulate all of the logic for accessing and handling each type of query variable in a single maintainable location.

通过这种方式,您可以将用于访问和处理每种类型的查询变量的所有逻辑封装在一个可维护的位置。

EDIT2: --- And because it is an instance of the class, you could also use dependency injection to inject the QueryStrings class in every place you are using it. StructureMapdoes a good job of that. This also allows you to mock up the QueryStrings class and inject that if you wanted to do automated unit testing. It is much easier to mock this up than ASP.Net's Request object.

EDIT2: --- 因为它是类的一个实例,你也可以使用依赖注入在你使用它的每个地方注入 QueryStrings 类。 StructureMap在这方面做得很好。这也允许您模拟 QueryStrings 类并在您想要进行自动化单元测试时注入它。模拟这个比 ASP.Net 的 Request 对象容易得多。

回答by Ian Suttle

One thing is you're not capturing blank values here. You might have a url like "http://example.com?someKey=&anotherKey=12345" and in this case the "someKey" param value is "" (empty). You can use string.IsNullOrEmpty() to check for both null and empty states.

一件事是您没有在这里捕获空白值。您可能有一个类似“ http://example.com?someKey=&anotherKey=12345”的网址,在这种情况下,“someKey”参数值为“”(空)。您可以使用 string.IsNullOrEmpty() 来检查空状态和空状态。

I'd also change "someKey" to be stored in a variable. That way you're not repeating literal strings in multiple places. It makes this easier to maintain.

我还将更改“someKey”以存储在变量中。这样你就不会在多个地方重复文字字符串。它使这更易于维护。

int val = 0;
string myKey = "someKey";
if (!string.IsNullOrEmpty(Request.QueryString[myKey]))
{
    val = int.Parse(Request.QueryString[myKey]);
}

I hope that helps!

我希望这有帮助!

Ian

伊恩

回答by Charlino

Write some sort of a helper method (library) to handle it...

编写某种辅助方法(库)来处理它...

public static void GetInt(this NameValueCollection nvCol, string key, out int keyValue, int defaultValue)
{
    if (string.IsNullOrEmpty(nvCol[key]) || !int.TryParse(nvCol[key], out keyValue))
        keyValue = defaultValue;
}

Or something along those lines...

或类似的规定...

回答by eduncan911

We've been using constants to keep all of these "loose" keys in a central location:

我们一直在使用常量来将所有这些“松散”的键保存在一个中心位置:

public class Constants
{
  public class QueryString
  {
    public const string PostID = "pid";
    public const string PostKey = "key";
  }
  public class Cookie
  {
    public const string UserID = "mydomain.com-userid";
  }
  public class Cache
  {
    public const string PagedPostList = "PagedPostList-{0}-{1}";
  }
  public class Context
  {
    public const string PostID = "PostID";
  }
  public class Security
  {
    public const RoleAdministrator = "Administrator";
  }
}

That way, you easily access the constants you need with:

这样,您可以通过以下方式轻松访问所需的常量:

public void Index()
{
  if (Request[Constants.QueryString.PostKey] == "eduncan911")
  {
    // do something
  }
}

public object GetPostsFromCache(int postID, int userID)
{
  String cacheKey = String.Format(
      Constants.Cache.PagedPostList
      , userID
      , postID);
  return Cache[cacheKey] as IList<Post>;
}

回答by x4000

I'm with the poster who suggested the helper methods (I would comment on his, but can't yet). Someone else disagreed with him in favor of creating properties, but my answer to that is that it doesn't gracefully handle the issue of checking for nulls or invalid formatting, etc. If you have helper methods, all that logic can be written once and centralized.

我和建议使用辅助方法的海报在一起(我会评论他的,但还不能)。其他人不同意他创建属性,但我的回答是它不能优雅地处理检查空值或无效格式等问题。如果你有辅助方法,所有这些逻辑都可以写一次集中。

If you have a lot of pages, adding properties for each might be more time consuming than it is worth. But that's obviously just a preference, so to each his/her own.

如果您有很多页面,则为每个页面添加属性可能会比实际花费的时间更长。但这显然只是一种偏好,所以每个人都有自己的偏好。

One cool thing you could improve on the other poster's helper method is to make the out parameter a reference parameter instead (change out to ref). That way you can set a default value for the property, in case it is not passed. Sometimes you might want optional parameters, for instance -- then you can have it start with some default value for those cases where the optional parameter is not explicitly passed (easier than having a default value passed separately in). You can even add an IsRequired boolean parameter at the end, and have it throw an exception if the bool is set to true and the parameter is not passed. That can be helpful in many cases.

您可以在其他海报的辅助方法上改进的一件很酷的事情是将 out 参数改为参考参数(将 out 更改为 ref)。这样你就可以为属性设置一个默认值,以防它没有被传递。有时您可能需要可选参数,例如——然后您可以让它以一些默认值开始,用于那些未显式传递可选参数的情况(比单独传递默认值更容易)。您甚至可以在最后添加一个 IsRequired 布尔参数,如果 bool 设置为 true 并且未传递该参数,则它会抛出异常。这在许多情况下会很有帮助。

回答by Dan Diplo

Here's what I came up with. It uses generics to return a strongly-typed value from the QueryString or an optional default value if the parameter isn't in the QueryString:

这是我想出的。如果参数不在 QueryString 中,它使用泛型从 QueryString 或可选的默认值返回强类型值:

/// <summary>
    /// Gets the given querystring parameter as a the specified value <see cref="Type"/>
    /// </summary>
    /// <typeparam name="T">The type to convert the querystring value to</typeparam>
    /// <param name="name">Querystring parameter name</param>
    /// <param name="defaultValue">Default value to return if parameter not found</param>
    /// <returns>The value as the specified <see cref="Type"/>, or the default value if not found</returns>
    public static T GetValueFromQueryString<T>(string name, T defaultValue) where T : struct
    {
        if (String.IsNullOrEmpty(name) || HttpContext.Current == null || HttpContext.Current.Request == null)
            return defaultValue;

        try
        {
            return (T)Convert.ChangeType(HttpContext.Current.Request.QueryString[name], typeof(T));
        }
        catch
        {
            return defaultValue;
        }
    }

    /// <summary>
    /// Gets the given querystring parameter as a the specified value <see cref="Type"/>
    /// </summary>
    /// <typeparam name="T">The type to convert the querystring value to</typeparam>
    /// <param name="name">Querystring parameter name</param>
    /// <returns>The value as the specified <see cref="Type"/>, or the types default value if not found</returns>
    public static T GetValueFromQueryString<T>(string name) where T : struct
    {
        return GetValueFromQueryString(name, default(T));
    }

Since writing this post I've written a very small class library for manipulating querystring values - see https://github.com/DanDiplo/QueryString-Helper

自从写这篇文章以来,我编写了一个非常小的类库来操作查询字符串值 - 请参阅https://github.com/DanDiplo/QueryString-Helper

回答by Zain Shaikh

According to me, The best way to get querystring value is like following:
If the querystring is not found then the value of valwill be 0.

据我得到的查询字符串值,最好的办法是像如下:
如果没有找到查询字符串,然后值val0

int val = 0;
int.TryParse(Request.QueryString["someKey"], out val);