MongoDB: автоматически генерируемые идентификаторы являются нулями
Я использую MongoDB и официальный драйвер С# 0.9
Я просто проверяю, как работает внедрение простых документов.
Есть 2 простых класса:
public class User
{
public ObjectId _id { get; set; }
public string Name { get; set; }
public IEnumerable<Address> Addresses { get;set; }
}
public class Address
{
public ObjectId _id { get; set; }
public string Street { get; set; }
public string House { get; set; }
}
Я создаю нового пользователя:
var user = new User
{
Name = "Sam",
Addresses = (new Address[] { new Address { House = "BIGHOUSE", Street = "BIGSTREET" } })
};
collection.Insert(user.ToBsonDocument());
Пользователь успешно сохранен, так же как и его адрес.
После ввода
db.users.find()
в оболочке MongoDB, я получил следующий результат:
{ "_id" : ObjectId("4e572f2a3a6c471d3868b81d"), "Name" : "Sam", "Addresses" : [
{
"_id" : ObjectId("000000000000000000000000"),
"Street" : "BIGSTREET",
"House" : "BIGHOUSE"
}
] }
Почему адрес 'id объекта 0?
Выполнение запросов с адресом работает, хотя:
collection.FindOne(Query.EQ("Addresses.Street", streetName));
Он возвращает пользователя "Сэм".
Ответы
Ответ 1
Использовать атрибут BsonId:
public class Address
{
[BsonId]
public string _id { get; set; }
public string Street { get; set; }
public string House { get; set; }
}
Идентификация поля или свойства идентификатора
Чтобы определить, какое поле или свойство класс - это идентификатор, который вы можете написать:
public class MyClass {
[BsonId]
public string SomeProperty { get; set; }
}
Учебник по драйверам
Edit
На самом деле он не работает. Позже я уточню, почему.
Если вам нужно получить его работу, используйте следующую команду:
[Test]
public void Test()
{
var collection = Read.Database.GetCollection("test");
var user = new User
{
Name = "Sam",
Addresses = (new Address[] { new Address { House = "BIGHOUSE", Street = "BIGSTREET", _id = ObjectId.GenerateNewId().ToString() } })
};
collection.Insert(user.ToBsonDocument());
}
Ответ 2
Это не столько ошибка, сколько случай неудовлетворенных ожиданий. Только верхнему уровню _id автоматически присваивается значение. Любые внедренные _ids должны быть назначены значениями кода клиента (используйте ObjectId.GenerateNewId). Также возможно, что вам даже не нужен ObjectId в классе Address (какова его цель?).
Ответ 3
Получить коллекцию как тип пользователя:
var collection = db.GetCollection<User>("users");
Инициализируйте поле _id следующим образом:
var user = new User
{
_id = ObjectId.Empty,
Name = "Sam",
Addresses = (new Address[] { new Address { House = "BIGHOUSE", Street = "BIGSTREET" } })
};
Затем вы вставляете объект:
collection.InsertOne(user);
Поле _id будет автоматически сгенерировано.
В этой ссылке вы найдете альтернативные способы создания настроенных автогенерированных идентификаторов.