找不到匹配的创建者

Ant*_*tau 9 c# mongodb aggregation-framework mongodb-.net-driver

最近我已经从mongosharp 1.8迁移到2.0.我遇到的唯一问题是聚合日期字段.让我告诉你如何构造查询:

var aggregateResult = Items.Aggregate()
    .Group(
        g => new {
            // some fields
            Day = g.DateTime.DayOfYear
        },
        z => new {
            MyKey = z.Key
            // agrregation functions
        })
    .Project(
        d => new {
            // projection for other fields
            d.MyKey.Day
        });
Run Code Online (Sandbox Code Playgroud)

我在文档中使用了这个例子.

我得到以下异常:No matching creator found.我已检查生成的查询并手动执行它 - 结果很完美.再现测试代码并与我比较我发现问题是在日期.那么,有人能指出我更正日期的语法/查询规则吗?下面生成的查询证明查询是正确的.

aggregate(
[
    {
        "$group" : {
            "_id" : {
                "Day" : {
                    "$dayOfYear" : "$DateTime"
                }
            },
        }
    },
    {
        "$project" : {
            "Day" : "$_id.Day",
            "_id" : 0
        }
    }
])
Run Code Online (Sandbox Code Playgroud)

解决方法

所以,为了让事情有效,我会做下一个解决方法:

  • create aggregate helper class,它使用Legacy程序集封装对数据库的访问.
  • 实现使用在bson文档上构造的查询的方法
  • 将它注入我的async 2.0服务并用sync替换异步调用

下面是获取集合和执行查询的代码

_collection = new MongoDatabase(new MongoServer( MongoServerSettings.FromUrl(connectionString)), databaseName, new MongoDatabaseSettings()).GetCollection<MyClass>("collection_name"); 
var pipeline = new[] { match, groupBy, project, .... };
_collection.Aggregate(new AggregateArgs { Pipeline = pipeline }).ToList()
Run Code Online (Sandbox Code Playgroud)

R J*_*R J 9

我今天遇到了这个错误。与提出问题的人类似,我从 mongo 查询填充了一个匿名类型。

当您获取的元素在数据库中不存在时,错误似乎发生了。在这种情况下,mongo 驱动程序似乎对生成的匿名类型应该生成为什么“类型”感到困惑。

我将匿名类型更改为具体类型(通过为其声明一个类)并修复了错误。


wei*_*hch 7

对于使用LINQ查询像我这样的人,你也可以考虑使用聚结式(又名??Select所述的具有产生不必要的具体类型忌。

在编写以下示例时使用了 MongoDB.Driver 2.11.2

考虑这个查询:

var query = Collection
    .Where(x => filter.Inject())
    .Select(x => new
    {
        Title = x.Title // Some old entities do not have Title
    });
Run Code Online (Sandbox Code Playgroud)

查询将被翻译为$project

aggregate([{ "$project" : { "Title" : "$title" } }])
Run Code Online (Sandbox Code Playgroud)

当某些项目没有时$title,由于@rj 所述的原因,结果无法映射到匿名类型,并且引发异常:

未找到匹配的创建者。

如果对 应用合并x.Title

new
{
    Title = x.Title ?? null
}
Run Code Online (Sandbox Code Playgroud)

然后查询将被转换为:

aggregate([{ "$project" : { "Title" : { "$ifNull" : ["$title", null] } } }])
Run Code Online (Sandbox Code Playgroud)

以何种方式 aTitle在结果中得到保证。

这种方法的缺点是,如果从 C# 的角度来看,C# 表达式确实看起来有点混乱。如果Title在 C# 中启用可为空的引用类型并且该属性不为空,您将看到一条警告/提示,指出左操作数从不为空。