(1) Пролог
Когда набор данных содержит обе первичные/подтаблицы (таблицы первичного ключа/таблицы внешнего ключа), иногда ограничения отношений являются слишком строгими:
Например, правила целостности реляционной базы данных:
1. Целостность объекта. Первичный ключ в таблице первичных ключей не может быть пустым.
2. Ссылочная целостность. Значение внешнего ключа в таблице внешних ключей должно соответствовать первичному ключу в таблице первичных ключей.
Либо пусто, либо значение первичного ключа в таблице первичных ключей.
3. Настройте целостность.
Если ограничения отношений между несколькими таблицами, определенные в таблице DataSet, слишком строгие, используйте метод Update напрямую.
При совместной отправке нескольких таблиц в наборе данных правила целостности могут не соблюдаться и может возникнуть ошибка.
Причина: например, настройте две таблицы: CompanyMain (основная таблица компании) и CompanySon (подтаблица компании).
CompanyMain (основная таблица компании) в основном хранит основную информацию о компании, CompanySon (подтаблица компании)
В основном он хранит информацию о некоторых клиентах этой компании И (ID) в основной таблице компании и (BelongID) в подтаблице.
Установите связь, то есть связь первичного и внешнего ключей; одна компания соответствует нескольким клиентам, то есть связь ID:BelongID = 1:n.
Идентификатор основной таблицы — это автоматически сгенерированный номер.
Так:
При совместной отправке нового интерфейса компании система не будет соблюдать «правила целостности базы данных» для обновления базы данных.
Если сначала обновляется подтаблица, а затем обновляется основная таблица, может быть сообщено об ошибке. Причина в том, что информация о компании в основной таблице еще не была вставлена.
Для таблицы в базе данных номер компании: ID не генерируется, и при обновлении подтаблицы не будет соответствующего BelongID.
В это время, если установлено правило целостности «Внешний ключ в таблице внешних ключей не равен нулю», будет выдано исключение.
Это всего лишь вероятность ошибки, возможностей ошибки больше, и такие ошибки чаще возникают в распределенном дизайне
(2). Решение
обычно следует следующим правилам, что позволяет избежать большого количества ошибок
1
.Правило Перед обновлением набора данных выполните разделенную отправку с помощью <table> и <атрибута RowState таблицы>
I. Выполнение разделенной отправки с помощью <table> означает:
таблицы в наборе данных не отправляются вместе, а отправляются по одной. Таблица, отправка несколько раз
II. Разделение отправки в соответствии с <атрибутом RowState таблицы> означает:
разделить одну таблицу в наборе данных в соответствии с атрибутом RowState,
отправить один и тот же RowState один раз и отправить несколько раз.
2.
На основе правила
.1, сначала обновите статус <новый> и <модифицированный>, а затем обновите <удаленный
>. То есть: сначала обновите значение DataRowState: добавлено и изменено, а затем обновите: удалено
3.
На основе правила 1 и правила
.2, если DataRowState добавлен и изменен, сначала обновляется основная таблица, а затем обновляется подтаблица. На основании правила
1 и правила 2, если DataRowState удален, сначала обновляется подтаблица, а затем подтаблица
.подтаблица обновлена. Обновите основную таблицу.
(3) Обобщите три вышеуказанных правила следующим образом:
1. Разделите таблицу в DataSet, сгруппируйте каждую запись таблицы в соответствии с RowState и сохраните ее в разных наборах данных
// Так и должно быть. хранится в DataSet. Это связано с тем, что: Update принимает параметры DataSet, а WebService поддерживает только
//DataSet.Пример кода
для операции сериализации
:Предположим, что обновляемый набор данных: dsCompany (который включает в себя две таблицы, основную таблицу). и подтаблицу) и хранит
данные для обновления)
//dtCompanyMain хранит информацию основной таблицы компании, dtCompanySon хранит информацию подтаблицы компании
DataTable dtCompanyMail = ds.Tables["dtCompanyMain"].Clone(); //Отделяем данные основной таблицы
и сохраняем другой объект
DataTable dtCompanySon = ds.Talbes[ "dtCompanySon"].Clone(); // Отделяем данные подтаблицы
и сохраняем другой объект
DataSet dsAdded = new DataSet(); // Сохраняем вновь добавленные данные основной таблицы
DataSet dsMidified = new DataSet(); Сохранение записи редактируемой строки основной таблицы
DataSet dsDeleted = new DataSet(); //Сохранение записи удаленной строки основной таблицы
dsAdded = dtCompanyMain.GetChanges(DataRowState.Added); //Получение новой
записи строки, установленной
в основной таблицеdsMidified = dtCompanyMain.GetChanges(DataRowState.Modified); //Получить набор записей строк
, отредактированный
в основной таблице dsDeleted = dtCompanyMain.GetChanges(DataRowState.Deleted); //Получитьнабор записей строк
, удаленный в основной таблице
2. Обновить статус DataRowState; основной таблицы: Добавлены и изменены записи.
SqlDataAdapter.Update(dsAdded,"dtCompanyMain"); //Обновляем добавленный набор записей в базу данных
SqlDataAdapter.Update(dsModified,"dtCompanyMain"); //Обновляем измененный набор записей. в
базу данных
3. Обновить статус DataRowState подтаблицы: Добавлены и изменены записи
... //Код опущен, аналогично 2 обновлению основной таблицы.
4. Обновить статус DataRowState подтаблицы: Удаленные записи
. .... // Код опущен, аналогично коду 5 ниже
5. Обновите статус DataRowState основной таблицы до: Удаленные записи
SqlDataAdapter.Update(dsDeleted, "dtCompanyMain" // Обновляем измененный набор записей в базе данных);
Спасибо за чтение!