Триггеры и эквивалентные процедуры Access 2007?

хорошо, у кого-нибудь есть хорошие ресурсы для функций Access 2007 относительно триггеров или хранимых процедур? Может ли он вообще сделать их или что-то подобное им? Каждый ресурс, который я нашел в справке Microsoft, ссылается на Access 2003, а также на многие справочные руководства в интернете. Все перемещается в 2007 году, поэтому немного сложно перевести старые справочные руководства. Я действительно хотел использовать ms sql, но был вынужден сделать этот небольшой проект в access, поэтому любые ресурсы быть полезным.

круто, все ответы до сих пор были полезны. Просто хотел подтвердить много разрозненных знаний о доступе, которые у меня есть. Я думаю, что смогу сделать это для этого проекта. О, и я не могу использовать SQL из-за много...волокита.

6 ответов


хранимых процедур

компонент Access database engine в режиме запросов ANSI-92 поддерживает CREATE PROCEDURE (SQL DDL) синтаксис например

CREATE PROCEDURE GetCompanies
(
 :company_type VARCHAR(30) = NULL
)
AS
SELECT company_registered_number, organisation_name, company_type
  FROM Companies 
 WHERE company_type = IIF(:company_type IS NULL, company_type, :company_type);

следовательно, результирующий объект является PROCEDURE и хранится в файле базы данных вместе с таблицами. Акцент здесь делается на слове "хранимый" (а не "процедура"), т. е. он "близок к данным". Использование этих объектов способствует хорошему отделению передней части (FE) от задней части (BE), и я имею в виду логическое например, код SQL, хранящийся в коде VBA или в свойствах элемента управления формами доступа, не "близок к данным" и смешивает задний "слой" с передним "слоем" и затрудняет обслуживание кода SQL, например, если вам нужно переименовать столбец в таблице, задание легко, если все, что вам нужно сделать, это просмотреть PROCEDUREs и VIEWs.

еще одно преимущество использования PROCEDURE является (или, скорее, был), что в сочетании с безопасностью уровня пользователя (ULS) это может помочь "юзабилити". Чтобы использовать пример, часто спрашивают, Как добавить столбец created_date в таблицу и сохранить его значение. Добавление DEFAULT текущей метки времени получает вас только часть пути туда, например

CREATE TABLE Entities (
   entity_ID CHAR(8) WITH COMPRESSION NOT NULL UNIQUE, 
   CONSTRAINT entity_ID__pattern 
      CHECK (entity_ID NOT ALIKE '%[!0-9]%'), 
   entity_name VARCHAR(20) NOT NULL, 
   CONSTRAINT entity_name__whitespace
      CHECK (
             entity_name NOT ALIKE ' %'
             AND entity_name NOT ALIKE '% '
             AND entity_name NOT ALIKE '%  %'
             AND LEN(entity_name) > 0
            ), 
   created_date DATETIME DEFAULT NOW() NOT NULL
);

но это не предотвращает явное значение, которое не является текущей меткой времени. Мы могли бы конечно добавить CHECK ограничение или правило проверки для обеспечения этого:

ALTER TABLE Entities ADD
   CONSTRAINT entity_created_date__must_be_current_timestamp
      CHECK (created_date = NOW());

проблема здесь в том, что CHECK ограничение и проверка Правила проверяются на уровне строк, т. е. если вы когда-либо пытались изменить другой столбец, ограничение будет кусаться. Не хорошо, так:

ALTER TABLE Entities DROP
   CONSTRAINT entity_created_date__must_be_current_timestamp;

что делать? Ну, один из подходов-удалить привилегии из таблицы, чтобы конечные пользователи (и приложения в этом контексте тоже пользователи) не могли INSERT или UPDATE данные таблицы непосредственно, а затем создать PROCEDUREs, чтобы данные могли быть изменены и вместо этого предоставить соответствующие привилегии PROCEDUREs например

CREATE PROCEDURE AddEntity (
   :entity_ID CHAR(8), 
   :entity_name VARCHAR(20)
)
AS 
INSERT INTO Entities (entity_ID, entity_name, created_date) 
VALUES (:entity_ID, :entity_name, NOW());

EXECUTE EXECUTE AddEntity '00000001', 'Black';

я использую прошедшее время, потому что, как вы знаете, команда Открыть (или группы SharePoint? :)) удалены ULS из нового для Access2007 Ace engine. Я не уверен, что могу рекомендовать использовать устаревшую функцию.

теперь плохие новости. Многие (большинство?) народ бы возразил, что такое PROCEDURE не является процедурой, и у них есть хорошая точка зрения, потому что синтаксис SQL Access database engine не поддерживает управление потоком, объявление переменных, даже возможность выполнения более одного оператора SQL. Другими словами, a PROCEDURE не может содержать процессуальный кодекс. Рассмотрим таблицу, которая ссылается на сущности:

CREATE TABLE FlyingEntities (
   entity_ID CHAR(8) WITH COMPRESSION NOT NULL UNIQUE 
      REFERENCES Entities (entity_ID) 
      ON DELETE CASCADE 
      ON UPDATE CASCADE
);

было бы неплохо иметь PROCEDURE это может создать строку в сущностях и при необходимости создать строку в FlyingEntitiesbased на значение параметра, но это просто невозможно в одной инструкции SQL. Таким образом Access Database engine PROCEDURE имеет ограниченное значение, особенно теперь, когда ULS имеет исчез.

триггеры

невозможно обойти тот факт, что компонент Access database engine не имеет и никогда не имел триггеров. Вопрос в том, нужны ли они вам?

хотя я поддерживаю любовь к простоте ядра СУБД Access, правда в том, что много лет назад я перемещаю всю "серьезную" работу в более "промышленную силу" и более SQL-совместимые продукты, в первую очередь SQL Server. Однако в SQL Server я использую триггеры только для двух вещей, обе из которых могут быть сделаны без триггеров (в определенной степени) в ядре базы данных Access.

первым из этих обычаев является справиться с тем, что SQL Server CHECK ограничения не поддерживают подзапросы; другими словами, они могут быть на уровне столбцов и строк, но не на уровне таблицы. Доступ к базе данных двигателя CHECK ограничения, введенные в Jet 4.0 и все еще присутствующие в ACE (2007), всегда являются табличными... ну, они в теории. Есть проблема (подозреваемая ошибка), где они проверяются на уровне строки, когда они должны быть логически проверены на уровне инструкции SQL. Они не поддерживают SQL-92 DEFERRABLE синтаксис, поэтому для этой проблемы нет обходного пути (кстати, SQL Server страдает от той же проблемы при использовании FUNCTION для обхода ограничения нет вложенных запросов). Не все!--13--> ограничения столкнутся с этой проблемой, но ее существование заставляет меня немного опасаться.

второе и окончательное использование для триггеры в SQL Server для меня обусловлены другим ограничением: страшным "внешним ключом"...может вызвать циклы или несколько каскадных путей" при попытке создать два REFERENCEs к тому же ключу, например, это разрешено в Access database engine:

CREATE TABLE Marriages (
   entity_ID_1 CHAR(8) WITH COMPRESSION NOT NULL UNIQUE
      REFERENCES Entities (entity_ID) 
      ON DELETE CASCADE 
      ON UPDATE CASCADE, 
   entity_ID_2 CHAR(8) WITH COMPRESSION NOT NULL UNIQUE
      REFERENCES Entities (entity_ID) 
      ON DELETE CASCADE 
      ON UPDATE CASCADE,
   CONSTRAINT cannot_marry_yourself 
      CHECK (entity_ID_1 <> entity_ID_2)
);

но перенесите это на SQL Server (удалите WITH COMPRESSION etc), и это не допускается. В этом случае cannot_marry_yourself предотвратит циклы, но SQL Server делает простой подсчет и решает, что 1 + 1 = слишком много. Сырой, но эффективный, Я полагаю. Использование триггеров-единственный способ удовлетворительного обхода;CASCADE ссылочные действия-это особая боль с триггерами.

с другой стороны, компонент Access database engine в этом отношении еще тупее, чем SQL Server, потому что он вообще не пытается обнаружить циклы. Если вы создадите цикл, вы не получите предупреждения, и результатом будет гонка для перезаписи данных и сложная ситуация для отладки.

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

Итак, да, движку базы данных Access не хватает триггеров, но вы можете обнаружить, что вам может быть лучше без них.


О, и не пойми меня. началось в документации по СУБД Access. Он фрагментирован, и многие из этих фрагментов исчезли со временем, и многие из них не существовали в первую очередь, например, я упомянул CHECK ограничения выше, но никогда не было никаких подробностей, выпущенных, просто несколько ошибочных примеров (все, что я знаю о CHECK ограничения, которые я должен был узнать методом проб и ошибок - что существует, что я еще не наткнулся?!) И существующие фрагменты содержат существенные ошибки и ошибок и неточностей... даже ошибочно детализируя функциональность, которая никогда не существовала! например,создать инструкцию таблицы из справки Access2007 упоминаются временные таблицы с именем NOT NULL ограничения и многоколоночные NOT NULL ограничения, все из которых не существуют, но не упоминают DEFAULT или то, что некоторые CONSTRAINTs не реализованы с использованием индексов. Но самым серьезным упущением IMO является ссылка на выражения ядра СУБД Access, например IIF() ведет себя иначе, чем IIf() в VBA, но это, похоже, в настоящее время недокументировано. У справки SQL для Jet 3 был такой список, ни одна версия с тех пор не была, и справка Jet 3 исчезла из MSDN год или два назад. Отсутствие хорошей документации действительно подрывает доверие к ядру базы данных Access.


по данным Википедия:

Microsoft Access-это файловый сервер базы данных. В отличие от клиентского сервера СУБД, Microsoft Access не делает реализовать триггеры базы данных, сохраненные процедуры или ведение журнала транзакций.

были ли ресурсы, которые вы нашли для 2003 talking abour ADP файлов? Я думаю, что они могут быть, и в этом случае могут быть связаны с триггерами/процедурами в бэкэнде SQL Server, для чего они предназначены.


рассмотрите возможность использования Access 2007 в качестве интерфейса для SQL Express. Если ваш проблемный домен-это то, что Access JET может обрабатывать, SQL Express также может обрабатывать его, и вы получаете такие вещи, как триггеры и хранимые процедуры "бесплатно". Самое близкое, что native Access/JET имеет к хранимым процедурам, - это запросы (действие и стандарт), и нет ничего похожего на триггер в native Access / JET.

существует не так много проблем с настройкой Экспресс-выпусков либо, и Access отлично работает как интерфейс для SQL Express. Вы не заметите большой разницы (кроме стиля дизайнеров таблиц и тому подобного) при работе с таким фоном, и вам не придется делать это, когда ваше приложение масштабируется, чтобы нуждаться в реальном сервере базы данных в любом случае.


хранимые процедуры в основном выполняются как запросы в Access. В значительной степени любая документация для 03 будет соответствовать 07, поскольку функциональные различия довольно редки.


в Access, есть нет такой вещи, как триггер. Это относится ко всем версиям.


Что касается триггеров, если вы используете проект данных access, то у вас нет локальных таблиц, и вы даже не используете jet. В этом случае триггеры будут созданы и записаны в SQL server. Имейте в виду, что при построении проекта access data нельзя использовать любой другой сервер баз данных, кроме SQL server. Большинство версий office и access имеют версию SQL server на компакт-диске для этой цели. Это изменилось для 2007, но тем не менее в этом случае вы не можете использовать local таблицы с проектами данных access.

поэтому, если вы решите использовать access ADP, по умолчанию будут доступны триггеры.

Если вы используете стандартный файл mdb или accDB и не используете SQL server, но используете JET (теперь называемый ACE), у вас не будет доступных триггеров.