2010-03-03 5 views
6

Я использую Linq to SQL для доступа к моей базе данных. Я хочу иметь функцию «удалить учетную запись», которая в основном избавляется от всех записей во всех таблицах, принадлежащих данному пользователю. Какой был бы самый эффективный способ сделать это?Удалить из нескольких таблиц (linq to sql)

Удаление должно происходить в определенном порядке, в противном случае ошибки целостности внешнего ключа. Я могу сделать это вручную из базы данных, и я бы предпочел просто подражать этому в L2S, например. (Псевдокод)

var tb1del = From Table1 Where userId == userIdToDelete; 
mydatacontext.Table1.deleteonsubmit(tb1del); 

var tb1de2 = From Table1 Where userId == userIdToDelete; 
mydatacontext.Table2.deleteonsubmit(tb1de2); 
... 

Однако, я уверен, что это не самый эффективный способ удаления записей.

+0

Если у меня возникли вопросы. Почему это от linq-to-sql вместо SP или что-то подобное в самом db? Таким образом, вы можете управлять порядком, предоставлять другие функции и т. Д. Кажется, это громоздко сделать с помощью l2s вместо использования встроенных функций db. – GrayWizardx

+0

Я никогда не использовал SQL напрямую, поэтому я думал, что Linq будет проще. Тем не менее, я не против использования SQL с некоторыми предложениями :) –

ответ

6

Простым решением является создание ограничения FOREIGN KEY с ON DELETE CASCADE в базе данных. Таким образом, вам не нужно беспокоиться о порядке удаления или о чем-либо еще. Просто удалите запись учетной записи, и все готово.

2

Если есть несколько таблиц, а данных, принадлежащих пользователю, не так много, вы можете выдавать команды в LINQ to SQL. Под «не так много» я ​​имею в виду несколько записей, которые едва могут измениться, например, информация для входа, информация о адресе и предпочтения. В идеале вы хотели бы объединить всю эту логику, чтобы гарантировать, что шаги всегда выполняются в заданном порядке. Даже если это так, можно использовать хранимую процедуру.

С другой стороны, если ожидается, что данных будет много, например, пользователь форума, который имеет несколько сообщений, комментариев, избранных, закладок и т. Д., Тогда я рекомендую использовать хранимую процедуру, которая принимает идентификатор пользователя и делает все остальное по мере необходимости. Вызывает беспокойство то, что для каждого выдается одна заявка на удаление . Это приводит к более низкой производительности, чем инструкция delete, которая удаляет все записи, связанные с идентификатором пользователя, в одном выражении.

Вариант № 1: Использование хранимой процедуры

можно сопоставить хранимую процедуру для вашего DataContext, который дает вам возможность использовать его в качестве dc.DeleteUserAccount(userId). У Скотта Гу есть отличное сообщение в блоге, которое поможет вам начать: LINQ to SQL (Part 6 - Retrieving Data Using Stored Procedures).

Вариант № 2: Пакетное Используйте Терри ANEY Дополнение Код

Терри ANEY имеет большой пост в блоге, который обсуждает свой опыт развития способности к партии обновления и удаления с помощью LINQ к SQL эффективным образом. Вместо того, чтобы генерировать единую инструкцию update/delete для каждой соответствующей записи, код будет генерировать единый оператор для всех записей, как мы их обычно будем писать. Сообщение и код можно найти здесь: Batch Updates and Deletes with LINQ to SQL.

Вариант № 3: Использование метода DataContext.ExecuteCommand

DataContext.ExecuteCommand method может быть использована для выполнения SQL непосредственно, например:

int affectedRecords = 
    dc.ExecuteCommand("Update Person SET FirstName = {0} WHERE FirstName = {1}", "Foo", "Bar"); 

Обратите внимание на использование {0} и {1}, которые позволяют ввод для параметризации. Используйте это вместо конкатенации, чтобы предотвратить атаки SQL-инъекций.

Если вы собираетесь использовать это, вы можете пойти с опцией №1.

+0

Спасибо за ответ! На данный момент информация пользователя немного, но со временем она может увеличиться. Я рассмотрю вопрос о сохранении формата proc. –

2

Aaronaught правильный, но для тех из вас, кто задается вопросом, как это сделать в Microsoft SQL Server Management Studio, я добавил скриншот, который описывает, где это сделать.

Щелкните правой кнопкой по вашей нужной таблице, нажмите на кнопку Relationships, нажмите на одну из связей и раздвиньте INSERT And UPDATE Spesification под Table designer.

Затем выберите Delete rule = Cascade и все готово. Каждый раз, когда вы удаляете запись из этой таблицы, все элементы внешнего ключа, которые вы выбрали, каскадируются, также будут удалены.

alt text

Смежные вопросы