Oracle 11g 触发器错误 - ORA-00923:未在预期位置找到 FROM 关键字
Oracle 11g Trigger Error - ORA-00923: FROM keyword not found where expected
我对 Oracle SQL(特别是 Oracle 11g SQL)还是很陌生。我正在尝试编写触发器,但似乎无法解决所有错误。当前,当我尝试执行下面列出的 SQL 时,出现此错误:
Error at line 12: PL/SQL: ORA-00923: FROM keyword not found where expected
1. CREATE OR REPLACE TRIGGER course_assignment_trigger
2. AFTER INSERT ON Assign FOR EACH ROW
3. DECLARE
这是SQL我有:
CREATE OR REPLACE TRIGGER course_assignment_trigger
AFTER INSERT ON Assign FOR EACH ROW
DECLARE
tooManyCourses EXCEPTION;
notQualified EXCEPTION;
assignedBeforeQualified EXCEPTION;
assignedCourseCount int;
qualifiedRowCount int;
PRAGMA EXCEPTION_INIT( tooManyCourses, -20001 );
PRAGMA EXCEPTION_INIT( notQualified, -20001 );
PRAGMA EXCEPTION_INIT( assignedBeforeQualified, -20001 );
BEGIN
SELECT assignedCourseCount = COUNT(*) FROM Assign where Fid = :new.Fid;
IF assignedCourseCount >= 3
THEN
RAISE tooManyCourses;
END IF;
SELECT qualifiedRowCount = COUNT(*) FROM Qualify where Fid = :new.Fid and Cid = :new.Cid;
IF qualifiedRowCount = 0
THEN
RAISE notQualified;
END IF;
IF(:new.assignDate < (select qualifyDate from Qualify where Fid = :new.Fid and Cid = :new.Cid))
THEN
RAISE unacceptedDateOfQualification;
END IF;
EXCEPTION
WHEN tooManyCourses THEN
DBMS_OUTPUT.PUT_LINE('Cannot assign faculty to more than 3 courses.');
WHEN notQualified THEN
DBMS_OUTPUT.PUT_LINE('Faculty is not qualified to teach the course.');
WHEN assignedBeforeQualified THEN
DBMS_OUTPUT.PUT_LINE('Date of qualification must be before date of assignment.');
END;
你快到了。
语法是:
SELECT column_identifier
INTO plsql_variable
FROM table
-- ...
而你 RAISE unacceptedDateOfQualification
当你将异常声明为 assignedBeforeQualified
并且需要给每个异常一个不同的错误号。但是,您几乎肯定不想引发自定义异常并在同一个触发器中捕获它们并输出到控制台,因为它不会阻止 INSERT
的发生;你想要 RAISE_APPLICATION_ERROR
与你的自定义错误消息并想要这样做 BEFORE INSERT
.
像这样:
CREATE OR REPLACE TRIGGER course_assignment_trigger
BEFORE INSERT ON Assign FOR EACH ROW
DECLARE
assignedCourseCount int;
qualifiedRowCount int;
qualifyDt DATE;
BEGIN
SELECT COUNT(*)
INTO assignedCourseCount
FROM Assign
where Fid = :new.Fid;
IF assignedCourseCount >= 3
THEN
RAISE_APPLICATION_ERROR( -20001, 'Cannot assign faculty to more than 3 courses.');
END IF;
SELECT COUNT(*)
INTO qualifiedRowCount
FROM Qualify
where Fid = :new.Fid
and Cid = :new.Cid;
IF qualifiedRowCount = 0
THEN
RAISE_APPLICATION_ERROR( -20002, 'Faculty is not qualified to teach the course.');
END IF;
select MIN(qualifyDate)
INTO qualifyDt
from Qualify
where Fid = :new.Fid
and Cid = :new.Cid;
IF :new.assignDate < qualifyDt
THEN
RAISE_APPLICATION_ERROR( -20003, 'Date of qualification must be before date of assignment.' );
END IF;
END;
/
如果你有表格:
CREATE TABLE assign (
FID number,
CID number,
assignDate DATE
);
CREATE TABLE qualify (
FID number,
CID number,
qualifyDate DATE
);
然后:
INSERT INTO assign VALUES ( 1, 1, DATE '2020-01-01' );
引发异常:
ORA-20002: Faculty is not qualified to teach the course.
ORA-06512: at "FIDDLE_BLJCMOGDEOXTZOEWHDDA.COURSE_ASSIGNMENT_TRIGGER", line 24
ORA-04088: error during execution of trigger 'FIDDLE_BLJCMOGDEOXTZOEWHDDA.COURSE_ASSIGNMENT_TRIGGER'
然后:
INSERT INTO qualify VALUES ( 1, 1, DATE '2020-01-01' );
INSERT INTO assign VALUES ( 1, 1, DATE '2020-01-01' );
有效但是:
INSERT INTO assign VALUES ( 1, 1, DATE '2019-01-01' );
引发异常:
ORA-20003: Date of qualification must be before date of assignment.
ORA-06512: at "FIDDLE_BLJCMOGDEOXTZOEWHDDA.COURSE_ASSIGNMENT_TRIGGER", line 35
ORA-04088: error during execution of trigger 'FIDDLE_BLJCMOGDEOXTZOEWHDDA.COURSE_ASSIGNMENT_TRIGGER'
和:
INSERT INTO assign VALUES ( 1, 1, DATE '2020-01-01' );
INSERT INTO assign VALUES ( 1, 1, DATE '2020-01-01' );
INSERT INTO assign VALUES ( 1, 1, DATE '2020-01-01' );
插入行的第 2 个和第 3 个副本,但第 4 个副本引发异常:
ORA-20001: Cannot assign faculty to more than 3 courses.
ORA-06512: at "FIDDLE_BLJCMOGDEOXTZOEWHDDA.COURSE_ASSIGNMENT_TRIGGER", line 13
ORA-04088: error during execution of trigger 'FIDDLE_BLJCMOGDEOXTZOEWHDDA.COURSE_ASSIGNMENT_TRIGGER'
db<>fiddle here
我对 Oracle SQL(特别是 Oracle 11g SQL)还是很陌生。我正在尝试编写触发器,但似乎无法解决所有错误。当前,当我尝试执行下面列出的 SQL 时,出现此错误:
Error at line 12: PL/SQL: ORA-00923: FROM keyword not found where expected
1. CREATE OR REPLACE TRIGGER course_assignment_trigger
2. AFTER INSERT ON Assign FOR EACH ROW
3. DECLARE
这是SQL我有:
CREATE OR REPLACE TRIGGER course_assignment_trigger
AFTER INSERT ON Assign FOR EACH ROW
DECLARE
tooManyCourses EXCEPTION;
notQualified EXCEPTION;
assignedBeforeQualified EXCEPTION;
assignedCourseCount int;
qualifiedRowCount int;
PRAGMA EXCEPTION_INIT( tooManyCourses, -20001 );
PRAGMA EXCEPTION_INIT( notQualified, -20001 );
PRAGMA EXCEPTION_INIT( assignedBeforeQualified, -20001 );
BEGIN
SELECT assignedCourseCount = COUNT(*) FROM Assign where Fid = :new.Fid;
IF assignedCourseCount >= 3
THEN
RAISE tooManyCourses;
END IF;
SELECT qualifiedRowCount = COUNT(*) FROM Qualify where Fid = :new.Fid and Cid = :new.Cid;
IF qualifiedRowCount = 0
THEN
RAISE notQualified;
END IF;
IF(:new.assignDate < (select qualifyDate from Qualify where Fid = :new.Fid and Cid = :new.Cid))
THEN
RAISE unacceptedDateOfQualification;
END IF;
EXCEPTION
WHEN tooManyCourses THEN
DBMS_OUTPUT.PUT_LINE('Cannot assign faculty to more than 3 courses.');
WHEN notQualified THEN
DBMS_OUTPUT.PUT_LINE('Faculty is not qualified to teach the course.');
WHEN assignedBeforeQualified THEN
DBMS_OUTPUT.PUT_LINE('Date of qualification must be before date of assignment.');
END;
你快到了。
语法是:
SELECT column_identifier
INTO plsql_variable
FROM table
-- ...
而你 RAISE unacceptedDateOfQualification
当你将异常声明为 assignedBeforeQualified
并且需要给每个异常一个不同的错误号。但是,您几乎肯定不想引发自定义异常并在同一个触发器中捕获它们并输出到控制台,因为它不会阻止 INSERT
的发生;你想要 RAISE_APPLICATION_ERROR
与你的自定义错误消息并想要这样做 BEFORE INSERT
.
像这样:
CREATE OR REPLACE TRIGGER course_assignment_trigger
BEFORE INSERT ON Assign FOR EACH ROW
DECLARE
assignedCourseCount int;
qualifiedRowCount int;
qualifyDt DATE;
BEGIN
SELECT COUNT(*)
INTO assignedCourseCount
FROM Assign
where Fid = :new.Fid;
IF assignedCourseCount >= 3
THEN
RAISE_APPLICATION_ERROR( -20001, 'Cannot assign faculty to more than 3 courses.');
END IF;
SELECT COUNT(*)
INTO qualifiedRowCount
FROM Qualify
where Fid = :new.Fid
and Cid = :new.Cid;
IF qualifiedRowCount = 0
THEN
RAISE_APPLICATION_ERROR( -20002, 'Faculty is not qualified to teach the course.');
END IF;
select MIN(qualifyDate)
INTO qualifyDt
from Qualify
where Fid = :new.Fid
and Cid = :new.Cid;
IF :new.assignDate < qualifyDt
THEN
RAISE_APPLICATION_ERROR( -20003, 'Date of qualification must be before date of assignment.' );
END IF;
END;
/
如果你有表格:
CREATE TABLE assign (
FID number,
CID number,
assignDate DATE
);
CREATE TABLE qualify (
FID number,
CID number,
qualifyDate DATE
);
然后:
INSERT INTO assign VALUES ( 1, 1, DATE '2020-01-01' );
引发异常:
ORA-20002: Faculty is not qualified to teach the course.
ORA-06512: at "FIDDLE_BLJCMOGDEOXTZOEWHDDA.COURSE_ASSIGNMENT_TRIGGER", line 24
ORA-04088: error during execution of trigger 'FIDDLE_BLJCMOGDEOXTZOEWHDDA.COURSE_ASSIGNMENT_TRIGGER'
然后:
INSERT INTO qualify VALUES ( 1, 1, DATE '2020-01-01' );
INSERT INTO assign VALUES ( 1, 1, DATE '2020-01-01' );
有效但是:
INSERT INTO assign VALUES ( 1, 1, DATE '2019-01-01' );
引发异常:
ORA-20003: Date of qualification must be before date of assignment.
ORA-06512: at "FIDDLE_BLJCMOGDEOXTZOEWHDDA.COURSE_ASSIGNMENT_TRIGGER", line 35
ORA-04088: error during execution of trigger 'FIDDLE_BLJCMOGDEOXTZOEWHDDA.COURSE_ASSIGNMENT_TRIGGER'
和:
INSERT INTO assign VALUES ( 1, 1, DATE '2020-01-01' );
INSERT INTO assign VALUES ( 1, 1, DATE '2020-01-01' );
INSERT INTO assign VALUES ( 1, 1, DATE '2020-01-01' );
插入行的第 2 个和第 3 个副本,但第 4 个副本引发异常:
ORA-20001: Cannot assign faculty to more than 3 courses.
ORA-06512: at "FIDDLE_BLJCMOGDEOXTZOEWHDDA.COURSE_ASSIGNMENT_TRIGGER", line 13
ORA-04088: error during execution of trigger 'FIDDLE_BLJCMOGDEOXTZOEWHDDA.COURSE_ASSIGNMENT_TRIGGER'
db<>fiddle here