oq中使用seq和trigger自动增量 - 无效的sql语句

时间:2015-04-04 19:21:01

标签: sql oracle oracle11g

我是oracle的新手,来自MySQL,我试图让自动增量在Oracle中使用序列和触发器工作,这样每次插入时它都会将我的字段增加1。

CREATE SEQUENCE proposals_seq MINVALUE 1 
START WITH 1 INCREMENT BY 1 CACHE 10;

CREATE OR REPLACE TRIGGER proposals_before_insert
BEFORE INSERT
   ON proposals
   FOR EACH ROW
BEGIN
    SELECT proposals_seq.nextval INTO :new.proposal_id FROM dual;
END;

但是当我运行脚本时,我收到错误:

Error code 900, SQL state 42000: ORA-00900: invalid SQL statement

如果我删除&#34 ;;"在select语句之后,我没有得到任何错误,直到我尝试将数据插入表中,然后我收到此错误:

INSERT INTO proposals (target_audience, line_of_business, activity_description, cost, comments, objectives_and_results) 
    VALUES ('test', 'test', 'test', 15, 'test', 'test');

Error code 4098, SQL state 42000: ORA-04098: trigger 'PROPOSALS_BEFORE_INSERT' is invalid and failed re-validation

我正在使用此版本的Oracle: Oracle Database 11g企业版11.2.0.1.0版 - 64位生产

我找到的关于它的所有文章似乎都是这样做的,并在这里回答:How to create id with AUTO_INCREMENT on Oracle?

可能是因为我的Oracle版本?还有另一种方法让我自动增量吗?或者我是否必须手动增加我的sql中的序列?

我的表格如下:

CREATE TABLE proposals (
    proposal_id INT NOT NULL,
    target_audience VARCHAR2(50) NOT NULL,
    line_of_business VARCHAR2(50),
    activity_description VARCHAR2(250) NOT NULL,
    cost DECIMAL(19, 4) NOT NULL,
    comments VARCHAR2(250),
    objectives_and_results VARCHAR2(250),
    PRIMARY KEY (proposal_id)
);

3 个答案:

答案 0 :(得分:4)

我怀疑问题是你的客户端工具正在读取每个分号作为命令的结尾,导致PL / SQL代码(需要分号作为语句终止符)被错误地传输到服务器。

删除分号时,语句会正确发送到服务器,但由于PL / SQL不正确,最终会出现无效对象。

我在SQL Fiddle上复制了你的问题。然后我将语句终止符更改为/而不是;,并将代码更改为使用斜杠执行每个语句,并且它没有错误地工作:

CREATE TABLE proposals (
    proposal_id INT NOT NULL,
    target_audience VARCHAR2(50) NOT NULL,
    line_of_business VARCHAR2(50),
    activity_description VARCHAR2(250) NOT NULL,
    cost NUMBER(19, 4),
    comments VARCHAR2(250),
    objectives_and_results VARCHAR2(250),
    PRIMARY KEY (proposal_id)
)
/

CREATE SEQUENCE proposals_seq MINVALUE 1 
START WITH 1 INCREMENT BY 1 CACHE 10
/

CREATE OR REPLACE TRIGGER proposals_before_insert
BEFORE INSERT ON proposals FOR EACH ROW
BEGIN
    select proposals_seq.nextval into :new.proposal_id from dual;
END;
/

答案 1 :(得分:-1)

这是我用来改编你的桌子的代码。它适用于任何Oracle版本,但没有利用12中的新功能将序列设置为自动增量ID

CREATE OR REPLACE TRIGGER your_schema.proposal_Id_TRG BEFORE INSERT ON your_schema.proposal
FOR EACH ROW
BEGIN
  if inserting and :new.Proposal_Id is NULL then
  SELECT your_schema.proposal_Id_SEQ.nextval into :new.Proposal_Id FROM DUAL;
  end if;

END;
/

并且用法是

INSERT INTO proposals (proposal_id,target_audience, line_of_business, activity_description, cost, comments, objectives_and_results) 
    VALUES (null,'test', 'test', 'test', 15, 'test', 'test');

请注意,我们故意在主键中插入null以启动触发器。

答案 2 :(得分:-1)

我在Oracle中为我的表创建了SEQUENCE和Trigger。

我的实体:

@Entity
@Table(name = "TBL_AUTHENTICATE")
public class UserSession implements Serializable {
    @Id
    @Column(name = "SESSIONID", nullable = false, length = 12)
    private Long sessionId;

    @Column(name = "USER_ID", nullable = false, length = 10)
    private int user_id;

    @Column(name = "TIME_TO_LIVE", nullable = false)
    private Date time_to_live;

: - d
我尝试在此表中插入数据并使用我生成的值设置sessionId,最后我理解了问题。那是我的错。

然后我从表中获取序列和触发器。
我的问题解决了。