PSQL中的显示游标 D. Yemanov
现在,在PSQL中能够定义并使用多重游标. 显示游标与在存储过程和触发器中一样,能够在DSQL的EXECUTE BLOCK结构中使用.
语法格式:
DECLARE [VARIABLE] <游标名> CURSOR FOR ( < SELECT语句> );
OPEN <游标名>;
FETCH <游标名> INTO [, ...];
CLOSE <游标名>;
例子
1.
DECLARE RNAME CHAR(31);
DECLARE C CURSOR FOR
( SELECT RDB$RELATION_NAME FROM RDB$RELATIONS );
BEGIN
OPEN C;
WHILE (1 = 1) DO
BEGIN
FETCH C INTO :RNAME;
IF (ROW_COUNT = 0) THEN
LEAVE;
SUSPEND;
END
CLOSE C;
END
2.
DECLARE RNAME CHAR(31);
DECLARE FNAME CHAR(31);
DECLARE C CURSOR FOR
( SELECT RDB$FIELD_NAME FROM RDB$RELATION_FIELDS
WHERE RDB$RELATION_NAME = :RNAME ORDER BY RDB$FIELD_POSITION );
BEGIN
FOR
SELECT RDB$RELATION_NAME
FROM RDB$RELATIONS
INTO :RNAME
DO
BEGIN
OPEN C;
FETCH C INTO :FNAME;
CLOSE C;
SUSPEND;
END
END
游标定义只允许出现在PSQL块/过程/触发器的定义部分,作为任何规定的本地变量来定义.
游标名在上下文中必须是唯一的.它们不能和其他通过AS CURSOR子句, FOR SELECT已经定义的游标名冲突.然而,一个游标能在同一个上下文中通过任何其它类型的变量所共享它的名称,因为对各自的有效的运转是不一样的.
允许使用WHERE CURRENT OF子句来对指定位置进行更新与删除.
禁止试图取得或关闭一个FOR SELECT游标.
试图去打开一个已经打开的游标,或者取得或关闭一个已经关闭的游标,都将失败.
所有没有明确关闭的游标都将在退出当前PSQL块/过程/触发器时自动关闭.
ROW_COUNT系统变量能够被使用在FETCH语句之后,检查是否有记录返回.
存储过程变量的缺省值 V. Horsun
现在能够定义存储过程变量的缺省值.语法和定义一个字段或域的缺省值一样,除非你使用’=’来代替’DEFAULT’关键字.
有缺省值的变量必须位于变量列表的最后, 也就是说,不能将没有默认值的变量在有默认值的变量之后定义.调用者必须在有缺省值的变量之前对没有缺省值的变量赋值.例如,象这样是不合法的:为arg1,arg2赋值,没有设置arg3,设置arg4…
在运行中改变缺省值.如果你定义一个有缺省值的过程(如P1),从另一个过程(如P2)中调用它,缺省的变量,那么P1的缺省值将被引擎在执行P1开始的时候直接所代替.意思就是,如果你对P1改变了缺省值,,它不需要去重新编译P2了.
然而,它仍然需要断开所有客户连接,因为在Borland Interbase 6 beta "Data Definition Guide" (DataDef.pdf),在” Altering and dropping procedures in use(在使用中改变和删除过程)”章节中.
例子:
CONNECT ... ;
CREATE PROCEDURE P1 (X INTEGER = 123)
RETURNS (Y INTEGER)
AS
BEGIN
Y = X;
SUSPEND;
END;
COMMIT;
SELECT * FROM P1;
Y
============
123
EXECUTE PROCEDURE P1;
Y
============
123
CREATE PROCEDURE P2
RETURNS (Y INTEGER)
AS
BEGIN
FOR SELECT Y FROM P1 INTO :Y
DO SUSPEND;
END;
COMMIT;
SELECT * FROM P2;
Y
============
123
ALTER PROCEDURE P1 (X INTEGER = CURRENT_TRANSACTION)
RETURNS (Y INTEGER)
AS
BEGIN
Y = X;
SUSPEND;
END;
COMMIT;
SELECT * FROM P1;
Y
============
5875
SELECT * FROM P2;
Y
============
123
COMMIT;
CONNECT ... ;
SELECT * FROM P2;
Y
============
5880
注,变量缺省值的原始资料和BLR被保存在RDB$FIELDS中.
LEAVE <label> 语法的支持 D. Yemanov
新的LEAVE语法现在允许象Java风格一样,在PSQL循环中跳出标记处并且终止. 它的用途是去停止当前执行块并退出指定标记,恢复到执行循环以后的语句..
语法格式:
<标记名>: <循环语句>
...
LEAVE [<标记名>]
<循环语句> 处应是其中之一: WHILE, FOR SELECT, FOR EXECUTE STATEMENT
例子:
1.
FOR
SELECT COALESCE(RDB$SYSTEM_FLAG, 0), RDB$RELATION_NAME
FROM RDB$RELATIONS
ORDER BY 1
INTO :RTYPE, :RNAME
DO
BEGIN
IF (RTYPE = 0) THEN
SUSPEND;
ELSE
LEAVE; -- 退出当前循环
END
2.
CNT = 100;
L1:
WHILE (CNT >= 0) DO
BEGIN
IF (CNT < 50) THEN
LEAVE L1; --退出WHILE循环
CNT = CNT - l;
END
3.
STMT1 = 'SELECT RDB$RELATION_NAME FROM RDB$RELATIONS';
L1:
FOR EXECUTE STATEMENT :STMT1 INTO :RNAME
DO
BEGIN
STMT2 = 'SELECT RDB$FIELD_NAME FROM RDB$RELATION_FIELDS
WHERE RDB$RELATION_NAME = ';
L2:
FOR EXECUTE STATEMENT :STMT2 || :RNAME INTO :FNAME
DO
BEGIN
IF (RNAME = 'RDB$DATABASE') THEN
LEAVE L1; --退出到外部循环
ELSE
IF (RNAME = 'RDB$RELATIONS') THEN
LEAVE L2; -- 退出内部循环
ELSE
SUSPEND;
END
END
注意LEAVE后面没有标记,意味着中断当前(最内部)循环.
OLD 环境变量现在只读 D. Yemanov
OLD环境变量集现在在触发器模块中是只读的.试图去访问一些OLD值将会被拒绝.以后会有更多的这方面的信息.
PSQL 栈跟踪 V. Horsun
当PSQL执行(存储过程或触发器)中出现异常时,现在API客户端分离出一个简单的栈跟踪错误状态矢量.栈跟踪从出现异常错误的点开始,通过一个字符串(最大2048字节)表述出并且由所有的存储过程和触发器组成返回给最外层的调用者.如果实际的跟踪信息长于2KB的话,它将被截断.
附加消息条目将被添加到状态矢量,如下:
isc_stack_trace, isc_arg_string, <字串长度>, <字串>
isc_stack_trace is a new error code with value of 335544842L.
例子
建立元数据
CREATE TABLE ERR (
ID INT NOT NULL PRIMARY KEY,
NAME VARCHAR(16));
CREATE EXCEPTION EX '!';
CREATE OR ALTER PROCEDURE ERR_1 AS
BEGIN
EXCEPTION EX 'ID = 3';
END;
CREATE OR ALTER TRIGGER ERR_BI FOR ERR
BEFORE INSERT AS
BEGIN
IF (NEW.ID = 2)
THEN EXCEPTION EX 'ID = 2';
IF (NEW.ID = 3)
THEN EXECUTE PROCEDURE ERR_1;
IF (NEW.ID = 4)
THEN NEW.ID = 1 / 0;
END;
CREATE OR ALTER PROCEDURE ERR_2 AS
BEGIN
INSERT INTO ERR valueS (3, '333');
END;
1. 来自触发器的用户异常:
SQL> INSERT INTO ERR valueS (2, '2');
Statement failed, SQLCODE = -836
exception 3
-ID = 2
-At trigger 'ERR_BI'
2.来自过程调用触发器的用户异常:
SQL> INSERT INTO ERR valueS (3, '3');
Statement failed, SQLCODE = -836
exception 3
-ID = 3
-At procedure 'ERR_1'
At trigger 'ERR_BI'
3. 在触发器运行中出现异常(被0除):
SQL> INSERT INTO ERR valueS (4, '4');
Statement failed, SQLCODE = -802
arithmetic exception, numeric overflow, or string truncation
-At trigger 'ERR_BI'
4. 来自过程中的用户异常:
SQL> EXECUTE PROCEDURE ERR_1;
Statement failed, SQLCODE = -836
exception 3
-ID = 3
-At procedure 'ERR_1'
5. 来自过程中更深层调用栈的用户异常:
SQL> EXECUTE PROCEDURE ERR_2;
Statement failed, SQLCODE = -836
exception 3
-ID = 3
-At procedure 'ERR_1'
At trigger 'ERR_BI'
At procedure 'ERR_2'
调用一个UDF作为空功能 N. Samofatov
在PSQL中支持UDF, 如: RDB$SET_CONTEXT,尽管是它是空的功能,但是它能被调用.
(a.k.a "procedures" in Object Pascal). 以后会有更多的这方面的信息.
新的保留字与变化
从Firebird 1.5以来,下面的关键字已经被增加或改变.那些标有星号 (*)是没有出现在标准的SQL中的.
新增的保留关键字
BIT_LENGTH
BOTH
CHAR_LENGTH
CHARACTER_LENGTH
CLOSE
CROSS
FETCH
LEADING
LOWER
OCTET_LENGTH
OPEN
ROWS
TRAILING
TRIM
CLOSE
OPEN
从非保留关键字改变成保留关键字
USING
新增的非保留关键字
BACKUP *
BLOCK *
COLLATION
COMMENT *
DIFFERENCE *
IIF *
NEXT
SCALAR_ARRAY *
SEQUENCE
RESTART
RETURNING *
从保留关键字改变成非保留关键字
ACTION
RESTRICT
WEEKDAY *
CASCADE
ROLE
YEARDAY *
FREE_IT *
TYPE
取消的保留关键字
BASENAME *
GROUP_COMMIT_WAIT *
NUM_LOG_BUFS *
CACHE *
LOGFILE *
RAW_PARTITIONS *
CHECK_POINT_LEN *
LOG_BUF_SIZE *
