Как обрабатывать ссылочную целостность для вставок в Access - PullRequest
1 голос
/ 13 сентября 2011

Я работаю над проектом Access, который перенял у коллеги.Существуют три таблицы: rules, overview и relationship.Таблица relationship имеет два поля, каждое из которых является внешним ключом, который ссылается на первичный ключ в двух других таблицах.У меня есть представление таблицы данных rules в форме, где я могу удалить записи без проблем.Однако, когда я пытаюсь вставить запись в таблицу rules, запись будет вставлена ​​в таблицу rules, но в таблицу relationship не будет найдено соответствующей записи.У меня отмечены «Принудительная ссылочная целостность», а также «Связанные поля каскадного обновления» и «Каскадное удаление связанных записей».Я сделал наивное предположение, что это будет обрабатывать вставки, но я явно ошибался.Так что теперь я задаюсь вопросом о лучшем способе справиться с этим - я пишу некоторый VBA для события After Insert формы, которая вставляет запись в таблицу relationship соответственно?

Ответы [ 2 ]

2 голосов
/ 13 сентября 2011

Обычный способ состоит в том, чтобы либо иметь форму для вставки записей в правила, основанную на запросе, который включает в себя таблицу отношений и, скажем, комбо, позволяющий пользователю выбрать соответствующий обзор, либо набор форм / подчиненных формс подходящими основными / дочерними полями.В примере базы данных NorthWind таблица Order Order является примером вашей таблицы Relationship, в ней используется ненавистная антивирусная функция поиска в таблице, но вы можете получить некоторые идеи для дальнейших исследований.

Гораздо более подробное описание варианта 1

Таблицы

Обзор Я БЫобзор

Правила Я БЫправило

Отношения RulesID) ПК, образованный двумя ФКOverviewID)

Отношение

Relations

Данные

data

Предложение 1 Дизайн запроса

Обратите внимание, что оба поля из Отношения включены в запрос.Нет необходимости показывать ID из правил, потому что это поле для автонумерации, но оно включено здесь для простоты.

Если строка удалена, записи из обеих таблиц будут удалены.

Query Design

Вы не можете нарушать ссылочную целостность.Прежде чем это сработает, вам нужно будет создать все обзоры или предоставить другой способ добавления обзоров.

Violate Integrity

Если вы обновите RulesID и OverviewID, записьбудет добавлен в таблицу отношений, но не в правила.

New Relationship record

Если вы обновите OverviewID и Rule, записи будут добавлены как в отношения, так и в правила.

New Rule and Relationship records

Если вы создаете непрерывную форму, вы получаете все вышеперечисленное в гораздо более удобном для пользователя виде с большим контролем.Вы можете использовать комбинированный список, чтобы позволить пользователю выбрать более понятное описание обзора, а не ID, и вы можете воспользоваться событием NotInList для добавления новых обзоров.

continuous Form

Обратите внимание, что до сих пор для этого не требовалось ни одной строки кодаЭто сила доступа.

0 голосов
/ 14 сентября 2011

Если рассматриваемый ключ является автономным номером (IDENTITY) и одна таблица ссылается на другую (через внешний ключ), тогда вы можете создать VIEW, соединяющий две таблицы, вставить в представление, и значение автономного номера получится автоматически копируется в справочную таблицу. Вот короткая демонстрация:

Sub RulesOverview()
  On Error Resume Next
  Kill Environ$("temp") & "\DropMe.mdb"
  On Error GoTo 0

  Dim cat
  Set cat = CreateObject("ADOX.Catalog")

  With cat
    .Create _
    "Provider=Microsoft.Jet.OLEDB.4.0;" & _
    "Data Source=" & _
    Environ$("temp") & "\DropMe.mdb"

    With .ActiveConnection

      Dim Sql As String

      Sql = _
      "CREATE TABLE Rules ( " & _
      " ID INTEGER IDENTITY NOT NULL UNIQUE,  " & _
      " Rule VARCHAR(30) NOT NULL UNIQUE " & _
      ")"

      .Execute Sql

      Sql = _
      "CREATE TABLE Overview ( " & _
      " OverviewID INTEGER IDENTITY NOT NULL UNIQUE, " & _
      " Overview VARCHAR(30) NOT NULL UNIQUE " & _
      ")"

      .Execute Sql

      Sql = _
      "CREATE TABLE Relationship ( " & _
      " RuleID INTEGER NOT NULL " & _
      "    REFERENCES Rules (ID) " & _
      "    ON DELETE CASCADE, " & _
      " OverviewID INTEGER " & _
      "    REFERENCES Overview (OverviewID) " & _
      "    ON DELETE SET NULL, " & _
      " Name VARCHAR(20) NOT NULL, " & _
      " UNIQUE (RuleID, OverviewID) " & _
      ")"

      .Execute Sql

      Sql = _
      "CREATE VIEW RulesRelationship AS " & _
      "SELECT Rules.ID, " & _
      "       Rules.Rule, " & _
      "       Relationship.RuleID, " & _
      "       Relationship.Name " & _
      "  FROM Rules INNER JOIN Relationship " & _
      "          ON Rules.ID = Relationship.RuleID;"

      .Execute Sql

      Sql = _
      "INSERT INTO RulesRelationship (Rule, Name) " & _
      "   VALUES ('Don''t run with scissors', " & _
      "           'Initial scissors');"

      .Execute Sql

      Sql = _
      "SELECT * FROM RulesRelationship;"

      Dim rs
      Set rs = .Execute(Sql)
      MsgBox rs.GetString

    End With
    Set .ActiveConnection = Nothing
  End With
End Sub
...