Проблема с объектом Entity Framework

Я получаю "Объект нельзя удалить, потому что он не найден в ObjectStateManager". при удалении объекта.

здесь коды;

//first i am filling listview control.
 private void Form1_Load(object sender, EventArgs e)
    {
        FirebirdEntity asa = new FirebirdEntity();

        ObjectQuery<NEW_TABLE> sorgu = asa.NEW_TABLE;

        foreach (var item in sorgu)
        {
            ListViewItem list = new ListViewItem();
            list.Text = item.AD;
            list.SubItems.Add(item.SOYAD);
            list.Tag = item;
            listView1.Items.Add(list);

        }
//than getting New_table entity from listview tag property.
 private void button3_Click(object sender, EventArgs e)
    {

            using (FirebirdEntity arama = new FirebirdEntity())
            {

               NEW_TABLE del = (NEW_TABLE)listView1.SelectedItems[0].Tag;
               arama.DeleteObject(del);
               arama.SaveChanges();


            }}

Ответы

Ответ 1

Вам нужно attach объект в ObjectContext. Попробуйте:

NEW_TABLE del = (NEW_TABLE)listView1.SelectedItems[0].Tag;
arama.Attach(del);
arama.DeleteObject(del);
arama.SaveChanges();

Прикрепленные объекты отслеживаются с помощью ObjectContext. Это необходимо для выполнения удалений и обновлений. Вы можете больше узнать о прикреплении объектов к MSDN.

Изменить, чтобы уточнить прикрепление/отсоединение:

private void Form1_Load(object sender, EventArgs e) {
    FirebirdEntity asa = new FirebirdEntity();

    ObjectQuery<NEW_TABLE> sorgu = asa.NEW_TABLE;
    foreach (var item in sorgu) {
        asa.Detach(item);
        // add to listView1
    }
}

Кроме того, вы должны обернуть использование ObjectContext в блоках using.

Ответ 2

В вашем методе Form1_Load вы создаете FIRST-экземпляр вашего контекста "FirebirdEntity", заполните ListViewItem сущностями, выбранными из этого контекста.

В вашем методе "button3_Click" вы создаете новый, второй экземпляр вашего контекста "FirebirdEntity". Затем вы пытаетесь удалить объект в этом SECOND-контексте, который был выбран в FIRST-контексте.

Используйте один и тот же экземпляр вашего контекста в обоих ваших методах, и все будет работать нормально.

(В качестве альтернативы вы можете выбрать объект, который хотите удалить a из своего SECOND-контекста, а затем удалить этот объект вместо исходного)

Ответ 3

Я запустил linq-запрос в своих методах DomainService и затем удалил из результата, поэтому, в то время как первый фрагмент ниже с ошибкой "Объект не может быть удален, потому что он не был найден в ObjectStateManager", второй фрагмент работал.

public void DeleteSharedDoc(SharedDocs shareddoc)
{
       this.ObjectContext.SharedDocs.DeleteObject(shareddoc);
}

Это сработало:

public void DeleteSharedDoc(SharedDocs shareddoc)
{
var query = (from w in this.ObjectContext.SharedDocs
            where w.UserShareName == shareddoc.UserShareName
            && w.UserShareUsersEmail == shareddoc.UserShareUsersEmail
            && w.DocumentId == shareddoc.DocumentId
            select w).First();
this.ObjectContext.SharedDocs.DeleteObject(query);
}

Ответ 4

обычно для удаления в базе данных я использую этот тип запроса linq, всегда работает, если вы не получили ограничение внешнего ключа:

int id = convert.toint32(some text field from the page);
entity data = new entity();
var del = (from record in data.records 
          where record.id == id
          select record).FirstOrDefault();
data.deleteObject(del);
data.saveChanges();

Надеюсь, что это поможет.

Ответ 5

Предположим, у меня есть объект, называемый Департамент, с суррогатной клавишей DepartmentUUID

DDL выглядит следующим образом:

CREATE TABLE [dbo].[Department] 
    ( 
          DepartmentUUID [UNIQUEIDENTIFIER] NOT NULL 
        , DepartmentName varchar(24) not null
        , CreateDate smalldatetime not null 
    )
GO


ALTER TABLE [dbo].[Department] ADD CONSTRAINT PK_Department PRIMARY KEY NONCLUSTERED (DepartmentUUID) 
GO

ALTER TABLE [dbo].[Department] ADD CONSTRAINT CK_DepartmentName_Unique UNIQUE (DepartmentName) 
GO

ALTER TABLE [dbo].[Department] ADD CONSTRAINT [DF_Department_DepartmentUUID] DEFAULT ( NEWSEQUENTIALID() ) FOR DepartmentUUID
GO

ALTER TABLE [dbo].[Department] ADD CONSTRAINT [DF_Department_CreateDate] DEFAULT ( CURRENT_TIMESTAMP ) FOR CreateDate
GO

Теперь для кода платформы Entity. Важными частями являются: 1. Использование метода AttachTo. 2. Создание временного объекта и установка его первичного ключа. (суррогатный ключ).

public int DeleteDepartment(Guid departmentUUID)
{

    int returnValue = 0;

    Department holder = new Department();
    holder.DepartmentUUID = departmentUUID; // DepartmentUUID is the primary key of this object (entity in the db)

    using (MyContectObject context = new MyContectObject())
    {
        context.AttachTo("Departments", holder);

        context.DeleteObject(holder);

        int numOfObjectsAffected = context.SaveChanges();
        returnValue = numOfObjectsAffected;

        context.Dispose();
    }

    return returnValue;

}

Ответ 6

Отвратительно ужасный хак, который я использовал, таков:

var attachedObject = _repository.GetObjectByKey(detachedObject.EntityKey);

Работает для многих из этих проблем. Я надеялся найти более элегантное решение этой проблемы, придя сюда. Это похоже на трюк.