J'ai une collection MongoDB "foos" contenant des éléments qui ont chacun un tableau de "barres". C'est-à-dire que "foo" a le schéma suivant:
{
"id": UUID
"name": string
...
"bars": [
"id": UUID
"key": string
...
]
}
Je dois créer un index sur name et bar.key à l'aide du pilote MongoDB C # .NET Mongo.
J'ai supposé que je pourrais utiliser une fonction Linq Select pour le faire comme suit:
Indexes.Add(Context.Collection<FooDocument>().Indexes.CreateOne(
Builders<FooDocument>.IndexKeys
.Descending(x => x.Bars.Select(y => y.Key))));
Toutefois, cela entraîne une exception InvalidOperationException:
System.InvalidOperationException: 'Impossible de déterminer les informations de sérialisation pour x => x.Bars.Select (y => y.Id).'
La documentation Mongo sur les index MultiKey montre comment créer un tel index en utilisant la notation simple par points, c.-à-d.
db.foos.createIndex( { "name": 1, "bars.key": 1 } )
Cependant, la documentation du pilote MongoDB } semble suggérer que l’utilisation d’une fonction Linq comme je le fais est correcte.
Comment créer un index multikey sur ma collection à l'aide du pilote MongoDB .NET, de préférence à l'aide d'une fonction Linq?
Ceci est un exemple comment faire avec C #
var indexDefinition = Builders<FooDocument>.IndexKeys.Combine(
Builders<FooDocument>.IndexKeys.Ascending(f => f.Key1),
Builders<FooDocument>.IndexKeys.Ascending(f => f.Key2));
await collection.Indexes.CreateOneAsync(indexDefinition);
UPDATE
En ce qui concerne l'index dans le tableau, ce que j'ai pu trouver est d'utiliser "-1" comme index lorsque vous construisez votre clé d'index. Comme je comprends de github, le code source est une option valide dans le cas de requêtes de construction.
var indexDefinition = Builders<FooDocument>.IndexKeys.Combine(
Builders<FooDocument>.IndexKeys.Ascending(f => f.Key1),
Builders<FooDocument>.IndexKeys.Ascending(f => f.Key2[-1].Key));
await collection.Indexes.CreateOneAsync(indexDefinition);
"-1" est une constante codée en dur dans les pilotes mongodb C # qui signifie "$" ( proof ). Donc, ce code essaierait de créer un index:
{ "Key1": 1, "Key2.$.Key": 1 }
ce qui est bien pour interroger des informations depuis la base de données, mais pas autorisé (une exception "La clé d'index contient un nom de champ non autorisé: le nom de champ commence par '$'") à utiliser dans les index. Je suppose donc que cela devrait être changé dans les pilotes mongodb pour que cela fonctionne. Quelque chose comme "-2" signifie un opérateur vide. Dans ce cas, nous pourrions utiliser
var indexDefinition = Builders<FooDocument>.IndexKeys.Combine(
Builders<FooDocument>.IndexKeys.Ascending(f => f.Key1),
Builders<FooDocument>.IndexKeys.Ascending(f => f.Key2[-2].Key));
await collection.Indexes.CreateOneAsync(indexDefinition);
qui générerait un index comme:
{ "Key1": 1, "Key2.Key": 1 }
Donc en gros, je ne pense pas qu'il soit possible pour le moment de construire l'index que vous voulez avec Linq pur sans changer les drivers mongo C #.
Je pense donc que votre seule option est la même, toujours en C # mais sans Linq
await collection.Indexes.CreateOneAsync(new BsonDocument {{"name", 1}, {"bars.key", 1}});
Vous pouvez créer un index de chaîne et utiliser nameof()
en C # 6:
Indexes.Add(Context.Collection<FooDocument>().Indexes.CreateOne($"{nameof(FooDocument.Bars)}.{nameof(Bars.Key)}"));
Cela semble être une fonctionnalité demandée pour le pilote C # }, bien qu'il n'ait pas vu de progrès ces derniers temps. Cela dit, quelqu'un a soumis une solution simple sur le thread JIRA, alors peut-être que cela fera le travail pour vous.