LINQ InsertOnSubmit: исключение NullReferenceException
У меня есть этот код:
using DC = MV6DataContext;
using MV6; // Business Logic Layer
// ...
public DC.MV6DataContext dc = new DC.MV6DataContext(ConnectionString);
IP ip = new IP(Request.UserHostAddress);
dc.IPs.InsertOnSubmit(ip);
dc.SubmitChanges();
// in Business Logic layer:
public class IP : DC.IP {
public IP(string address) { ... }
}
При попытке InsertOnSubmit (ip) я получаю исключение NullReferenceException (ссылка объекта не установлена в экземпляр объекта). dc не равен нулю; ip и все свойства ip не равны нулю; хотя некоторые из них пусты.
VS2008 не позволит мне входить в InsertOnSubmit, поэтому я не могу понять, что конкретно является нулевым при оценке. Что дает?
Примечание. Я проверил, и все Linq.EntitySets, созданные отношениями FK, присутствуют и не являются нулевыми.
Ответы
Ответ 1
Получил это.
Вместо создания класса, который наследуется от класса DataContext, я расширяю класс DC с частичным классом на уровне Business Logic. Оттуда я могу добавить любые конструкторы и методы, которые я желаю.
В этом случае необходимо скопировать код из существующего (автоматически сгенерированного) конструктора:
public IP(string address) {
Address = address;
Domain = "";
Notes = "";
FirstAccess = DateTime.Now;
LastAccess = DateTime.Now;
this._Sessions = new EntitySet<Session>(new Action<Session>(this.attach_Sessions), new Action<Session>(this.detach_Sessions));
OnCreated(); }
Не уверен, что в этом обработчике OnCreated, но, похоже, он делает работу, которая меня кость раньше. Хорошо работает сейчас:)
Ответ 2
На самом деле лучше добавить вызов к вашему конструктору, который также вызывает общий конструктор, например:
public IP(string address) : this() {
...
}
Ответ 3
Так как конструктор по умолчанию уже инициализирует base(), this._Sessions и запускает метод OnCreated, все, что вам нужно сделать в вашем расширенном конструкторе, это:
public IP(string address) : this()
{
Address = address;
Domain = "";
Notes = "";
FirstAccess = DateTime.Now;
LastAccess = DateTime.Now;
}
Ответ 4
Является ли это создателем конструктора DataContext или вашим собственным ручным. Я подозреваю, что таблица IPs не может быть создана при попытке использовать InsertOnSubmit()
. Я не вижу, как это произойдет с созданным конструктором DataContext, но я, как известно, забыл инициализировать мои коллекции время от времени в моем собственном коде.
Ответ 5
Вы можете попытаться понять, что происходит, какие изменения будут сделаны, если вы поместите точку останова непосредственно перед SubmitChanges и быстро просмотрите dc. GetChangeSet().
Ответ 6
У меня была немного отличная ситуация, чем у меня, но по той же причине получила ту же ошибку. Я написал новые конструкторы в частичном классе для своих сущностей базы данных, а затем попытался использовать результирующие объекты в вызовах InsertOnSubmit
.
Ни один из этих ответов не помог мне напрямую, но я смог выяснить, что они получают, прочитав все из них.
Автоматически сгенерированный конструктор без параметров для объекта делает вещи, которые должны произойти для InsertOnSubmit
, чтобы работать, поэтому, если вы перегружаете конструктор - например, me - или наследуете от класса - как и спрашиваете - вы нужно вызвать базовый конструктор из вашего нового конструктора, например:
public partial class Entity {
public Entity( Type parameter ) : this() {
// do things with the parameter
}
}
или
public class SubEntity: Entity {
public SubEntity( Type parameter ) : base() {
// do things with the parameter
}
}