Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/meteor/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Asp.net mvc 在数据库表中存储用户筛选的查询参数的最佳方法是什么?_Asp.net Mvc_Database Design_Query String_Database Schema - Fatal编程技术网

Asp.net mvc 在数据库表中存储用户筛选的查询参数的最佳方法是什么?

Asp.net mvc 在数据库表中存储用户筛选的查询参数的最佳方法是什么?,asp.net-mvc,database-design,query-string,database-schema,Asp.net Mvc,Database Design,Query String,Database Schema,我有一个ASP.NETMVC网站。在我的后端,我有一个名为People的表,其中包含以下列: 身份证 名字 年龄 位置 。。。(许多其他COL) 我有一个通用网页,它使用模型绑定来查询这些数据。以下是我的控制器操作: public ActionResult GetData(FilterParams filterParams) { return View(_dataAccess.Retrieve(filterParams.Name, filterParams.Age, filterPa

我有一个ASP.NETMVC网站。在我的后端,我有一个名为
People
的表,其中包含以下列:

  • 身份证
  • 名字
  • 年龄
  • 位置
  • 。。。(许多其他COL)
  • 我有一个通用网页,它使用模型绑定来查询这些数据。以下是我的控制器操作:

    public ActionResult GetData(FilterParams filterParams)
    {
          return View(_dataAccess.Retrieve(filterParams.Name, filterParams.Age, filterParams.location, . . .)
    }
    
    它映射到如下内容:

     http://www.mysite.com/MyController/GetData?Name=Bill .. . 
    
    dataAccess层只需检查每个参数,查看其是否已填充以添加到db where子句中。这很有效

    现在,我希望能够存储用户的过滤查询,并试图找出存储特定过滤器的最佳方法。由于一些过滤器在queryString中只有一个参数,而另一些过滤器中有10多个字段,因此我无法找出将此查询“filter info”存储到数据库中的最优雅的方法

    我能想到的选择是:

  • 有一个表的完整复制(带有一些额外的列),但称之为PeopleFilterQueries,在每个记录中填充一个FilterName,并在每个字段(名称等)中输入筛选器的值

  • 存储一个仅包含FilterName和字符串的表,其中存储实际的querystring Name=Bill&Location=NewYork。这样,如果过滤器发生更改或增长,我就不必继续添加新列


  • 这种情况下的最佳实践是什么?

    我将把
    FilterParams
    对象序列化为JSON/XML,而不是存储查询字符串,并将结果存储在数据库中

    下面是我经常使用的JSON序列化程序:

    using System.IO;
    using System.Runtime.Serialization.Json;
    using System.Text;
    
    namespace Fabrik.Abstractions.Serialization
    {
        public class JsonSerializer : ISerializer<string>
        {
            public string Serialize<TObject>(TObject @object) {
                var dc = new DataContractJsonSerializer(typeof(TObject));
                using (var ms = new MemoryStream())
                {
                    dc.WriteObject(ms, @object);
                    return Encoding.UTF8.GetString(ms.ToArray());
                }
            }
    
            public TObject Deserialize<TObject>(string serialized) {
                var dc = new DataContractJsonSerializer(typeof(TObject));
                using (var ms = new MemoryStream(Encoding.UTF8.GetBytes(serialized)))
                {
                    return (TObject)dc.ReadObject(ms);
                }
            }
        }
    }
    
    使用System.IO;
    使用System.Runtime.Serialization.Json;
    使用系统文本;
    命名空间Fabrik.Abstractions.Serialization
    {
    公共类JsonSerializer:ISerializer
    {
    公共字符串序列化(TObject@object){
    var dc=新的数据契约JSONSerializer(typeof(TObject));
    使用(var ms=new MemoryStream())
    {
    dc.WriteObject(ms,@object);
    返回Encoding.UTF8.GetString(ms.ToArray());
    }
    }
    公共对象反序列化(字符串序列化){
    var dc=新的数据契约JSONSerializer(typeof(TObject));
    使用(var ms=new MemoryStream(Encoding.UTF8.GetBytes(序列化)))
    {
    返回(TObject)dc.ReadObject(ms);
    }
    }
    }
    }
    

    然后,您可以按照上面的示例对对象进行反序列化,并将数据访问代码传递给它。

    如果目的是保存最近使用的过滤器列表,我会在模型绑定发生后将完整的FilterParams对象序列化到XML字段/列中。通过将其保存到XML字段中,您还可以在以后需要更注重性能的信息查询时灵活地使用XQuery和DML

        public ActionResult GetData(FilterParams filterParams)
        {
              // Peform action to get the information from your data access layer here
              var someData = _dataAccess.Retrieve(filterParams.Name, filterParams.Age, filterParams.location, . . .);
    
              // Save the search that was used to retrieve later here
              _dataAccess.SaveFilter(filterParams);
              return View(someData);
        }
    
    然后在DataAccess类中,您需要两个方法,一个用于保存,一个用于检索筛选器:

    public void SaveFilter(FilterParams filterParams){
        var ser = new System.Xml.Serialization.XmlSerializer(typeof(FilterParams));
        using (var stream = new StringWriter())
               {
                  // serialise to the stream
                  ser.Serialize(stream, filterParams);
               }
      //Add new database entry here, with a serialised string created from the FilterParams obj
      someDBClass.SaveFilterToDB(stream.ToString());
    }
    
    然后,当您想要检索已保存的筛选器时,可能是通过Id:

    public FilterParams GetFilter(int filterId){
    
          //Get the XML blob from your database as a string
          string filter = someDBClass.GetFilterAsString(filterId);
    
          var ser = new System.Xml.Serialization.XmlSerializer(typeof(FilterParams));
    
          using (var sr = new StringReader(filterParams))
          {
              return (FilterParams)ser.Deserialize(sr);
          }
    }
    
    请记住,您的FilterParams类必须有一个默认(即无参数)构造函数,并且您可以使用
    [XmlIgnore]
    属性来防止在需要时将属性序列化到数据库中

    public class FilterParams{
       public string Name {get;set;}
       public string Age {get;set;}
    
       [XmlIgnore]
       public string PropertyYouDontWantToSerialise {get;set;}
    }
    

    注意:SaveFilter返回Void,为简洁起见,没有错误处理

    假设像这样的nosql/对象数据库是不可能的,我肯定会选择选项1。您迟早会发现以下要求或其他要求:

  • 允许人们保存他们的过滤器、标签、标签、搜索并通过书签、推文或其他方式共享
  • 更改参数的含义或作用,这将要求您对过滤器进行版本设置以实现向后兼容性
  • 通过过滤器提供自动完成功能,可能使用用户的过滤器历史记录通知自动完成
  • 如果您执行任何类型的二进制/字符串序列化,其中需要解析结果,然后对其进行处理,那么上述内容将更难满足


    如果您可以使用NoSql DB,那么您将获得sql存储的所有好处,并且能够很好地对“任意数量的键/值对”进行建模。

    已经考虑过使用配置文件。这是存储用户特定信息的内置机制。从你对你的问题的描述来看,这似乎是合适的


    我不得不承认,M$的实现有点过时,但这种方法基本上没有什么错。如果您想自己开发,他们的API中有很多好的想法。

    您没有提到存储过滤器的确切目的

    若您坚持将过滤器保存到数据库表中,我将有以下表的结构

    • 过滤器
    • 字段值
    一个示例表可能是

    FilterId Field    FieldValue
    1        Name     Tom
    1        Age      24
    1        Location IL       
    3        Name     Mike
    ...
    

    答案比你所说的要简单得多:

    基本上,您应该将原始查询存储在它自己的表中,并将其与您的People表相关联。不要费心存储单个过滤器选项

    决定要存储的值(2个选项)

  • 存储URL查询字符串

    如果您喜欢开放式API风格的应用程序,并且希望能够在不进行转换的情况下将某些东西从客户端顺利地来回传递到服务器并重新使用,那么此id将非常有用

        public ActionResult GetData(FilterParams filterParams)
        {
              // Peform action to get the information from your data access layer here
              var someData = _dataAccess.Retrieve(filterParams.Name, filterParams.Age, filterParams.location, . . .);
    
              // Save the search that was used to retrieve later here
              _dataAccess.SaveFilter(filterParams);
              return View(someData);
        }
    
  • 将筛选器对象序列化为字符串

    如果存储这些过滤器的目的仍然完全是服务器端的,并且希望使数据更接近类对象,那么这是一种非常好的方法

  • 将您的
    人员
    表与您的
    查询筛选器表关联

    这里的最佳策略取决于您的意图和性能需求。以下是一些建议:

    • 简单过滤(例如2-3个过滤器,每个3-4个选项)

      使用多对多,因为数字