sql >> Databáze >  >> NoSQL >> MongoDB

Ovladač Mongodb C# vrací pouze odpovídající dílčí dokumenty v poli

K filtrování vnořeného pole obvykle potřebujete použít $filter v Aggregation Framework. Existuje však jednodušší způsob, jak toho dosáhnout pomocí ovladače MongoDB .NET Driver a IQueryable rozhraní.

S ohledem na nejjednodušší model:

public class MyModel
{
    public string _id { get; set; }
    public IEnumerable<MyNestedModel> myArray { get; set; }
}

public class MyNestedModel
{
    public string other { get; set; }
}

a následující údaje:

var m = new MyModel()
{
    _id = "1",
    myArray = new List<MyNestedModel>() {
        new MyNestedModel() {  other = "stuff" },
        new MyNestedModel() { other = "stuff" },
        new MyNestedModel() { other = "stuff2" } }
};

Col.InsertOne(m);

můžete jednoduše zavolat .AsQueryable() na vaši sbírku a poté můžete napsat dotaz LINQ, který bude přeložen ovladačem MongoDB do $filter , zkuste:

var query = from doc in Col.AsQueryable()
            where doc._id == "1"
            select new MyModel()
            {
                _id = doc._id,
                myArray = doc.myArray.Where(x => x.other == "stuff")
            };

var result = query.ToList();

EDIT:

Případně můžete napsat $filter část jako nezpracovaný řetězec a poté použijte .Aggregate() metoda. Pomocí tohoto přístupu nemusíte „mapovat“ všechny vlastnosti, nevýhodou však je, že ztrácíte bezpečnost typu, protože se jedná pouze o řetězec, zkuste:

var addFields = BsonDocument.Parse("{ \"$addFields\": { myArray: { $filter: { input: \"$myArray\", as: \"m\", cond: { $eq: [ \"$$m.other\", \"stuff\" ] } }  } } }");

var query = Col.Aggregate()
               .Match(x => x._id == "1")
               .AppendStage<MyModel>(addFields);

$addFields se zde používá k přepsání existujícího pole.




  1. Kdy Redis? Kdy MongoDB?

  2. Redis filtrovat podle rozsahu, seřadit a vrátit nejprve 10

  3. MongoDB:agregační rámec:$match mezi poli

  4. Vraťte poslední skutečnou hodnotu pro každou skupinu