1 目的
- Oracle 获取
序列(sequence)
的底层代码基本上一样。 - 本文在此记录,方便以后复制、粘贴。
2 源代码
思路:
2.1 序列配置表
CREATE TABLE odsdata.project_sequence_config (
owner VARCHAR(30),
table_name VARCHAR2(30),
column_name VARCHAR2(30),
sequence_name VARCHAR2(30) NOT NULL,
is_valid VARCHAR2(2) DEFAULT 'Y' NOT NULL,
create_user VARCHAR2(30) NOT NULL,
create_date DATE NOT NULL,
update_user VARCHAR2(30) NOT NULL,
update_date DATE NOT NULL
);
COMMENT ON TABLE odsdata.project_sequence_config IS '序列配置表';
COMMENT ON COLUMN odsdata.project_sequence_config.owner IS '属主';
COMMENT ON COLUMN odsdata.project_sequence_config.table_name IS '表名';
COMMENT ON COLUMN odsdata.project_sequence_config.column_name IS '列名';
COMMENT ON COLUMN odsdata.project_sequence_config.sequence_name IS '序列名';
COMMENT ON COLUMN odsdata.project_sequence_config.is_valid IS '是否有效(Y: 有效, N: 无效)';
COMMENT ON COLUMN odsdata.project_sequence_config.create_user IS '创建人';
COMMENT ON COLUMN odsdata.project_sequence_config.create_date IS '创建日期';
COMMENT ON COLUMN odsdata.project_sequence_config.update_user IS '更新人';
COMMENT ON COLUMN odsdata.project_sequence_config.update_date IS '更新日期';
ALTER TABLE odsdata.project_sequence_config ADD CONSTRAINT pk_psc_owner_table_column PRIMARY KEY(owner, table_name, column_name);
GRANT SELECT, INSERT, UPDATE ON odsdata.project_sequence_config TO odscde;
2.2 创建序列
CREATE SEQUENCE odsdata.seq_test
MINVALUE 1
MAXVALUE 99999999 -- 8 位 (请根据实际需求扩大)
START WITH 1
INCREMENT BY 1
CACHE 20
CYCLE
NOORDER;
GRANT SELECT ON odsdata.seq_test TO odscde;
-- 真实的 属主 odsdata 和 序列名 seq_test,其他的仅测试使用 (实际工作时,替换为 真实的 即可。)
INSERT INTO odsdata.project_sequence_config(owner, table_name, column_name, sequence_name, is_valid, create_user, create_date, update_user, update_date)
VALUES('odsdata', 'table_name', 'column_name', 'seq_test', 'Y', 'admin', SYSDATE, 'admin', SYSDATE);
COMMIT;
2.3 pkg_head
CREATE OR REPLACE PACKAGE odscde.pkg_project_sequence IS
--*************************************************************
--功能说明: 生成 sequence 的底层过程,供业务层应用程序调用
--参数说明: p_owner 属主
-- p_table_name 表名
-- p_column_name 列名
--异常说明: 此函数不做 exception 处理,请在应用程序中处理。
--修改记录: create by wangyou 2020-03-06
FUNCTION fetch_sequence(p_owner odsdata.project_sequence_config.owner%TYPE,
p_table_name odsdata.project_sequence_config.table_name%TYPE,
p_column_name odsdata.project_sequence_config.column_name%TYPE)
RETURN VARCHAR2;
END pkg_project_sequence;
/
2.4 pkg_body
CREATE OR REPLACE PACKAGE BODY odscde.pkg_project_sequence IS
--*************************************************************
--功能说明: 生成 sequence 的底层过程,供业务层应用程序调用
--参数说明: p_owner 属主
-- p_table_name 表名
-- p_column_name 列名
--函数返回值: v_sequence_no 序列号
--异常说明: 此函数不做 exception 处理,请在应用程序中处理。
--修改记录: create by wangyou 2020-03-06
FUNCTION fetch_sequence(p_owner odsdata.project_sequence_config.owner%TYPE,
p_table_name odsdata.project_sequence_config.table_name%TYPE,
p_column_name odsdata.project_sequence_config.column_name%TYPE)
RETURN VARCHAR2 IS
v_sequence_sql VARCHAR2(500);
v_sequence_no VARCHAR2(20);
v_sequence_name odsdata.project_sequence_config.sequence_name%TYPE;
cur_sequence_info SYS_REFCURSOR;
BEGIN
-- 避免大小写引起的漏洞,故都转为 "大写"
v_sequence_sql := 'SELECT psc.sequence_name
FROM odsdata.project_sequence_config psc
WHERE UPPER(psc.owner) = :b1
AND UPPER(psc.table_name) = :b2
AND UPPER(psc.column_name) = :b3
AND psc.is_valid = ''Y''';
OPEN cur_sequence_info FOR v_sequence_sql
USING upper(p_owner), upper(p_table_name), upper(p_column_name);
FETCH cur_sequence_info
INTO v_sequence_name;
-- 初始序列号 8 位
EXECUTE IMMEDIATE 'SELECT ' || p_owner || '.' || v_sequence_name ||
'.nextval FROM DUAL'
INTO v_sequence_no;
CLOSE cur_sequence_info;
-- 最终序列号 10 位 = "年份" + 初始序列号 (循环使用)
v_sequence_no := to_char(SYSDATE, 'YY') || v_sequence_no;
RETURN v_sequence_no;
END fetch_sequence;
END pkg_project_sequence;
/