存储过程开发模板

存储过程开发模板
总结的一个存储过程开发模板,主要是避免一些常见问题。
书写规范为:SQL关键字均使用小写。但是定义连接属性,如SET NOCOUNT ON可以用大写;变量采用Camel风格,单词首字符大写。

/**/ /**********************************************
作者:    XXX
创建日期:YYYY-MM-DD
功能描述:(清楚、详尽。如:本存储过程主要用于生成主键ID,
    为了适应分布式数据库的应用,采用SiteID(三位)+YYYYMMDD(八位)+顺序位(八位)组成BigInt类型编码。)
-----------------------------------------------
修改者:
修改日期:
修改描述:(如:本次修改加入了对存储过程的错误捕获。)
-----------------------------------------------
传入参数:
          @X1
           数据类型:
             描述:
          @X2
           数据类型:
             描述:
传出参数:
          @X1
           数据类型:
             描述:
返回值:
          @XX
           数据类型:
             描述:
*********************************************
*/

--  先检查存储过程是否存在,如果存在,先drop掉
if   Object_Id (N ' [dbo].[P_xxxx] ' , N ' P ' is   not   null
begin
    
drop   procedure   [ dbo ] . [ P_xxxx ]
end
go  

create   procedure   [ dbo ] . [ P_xxxx ]
    
@xxx1  DataType,
    
@xxx2  DataType output
as
begin
    
--  出于性能考虑,这是每个存储过程的第一条语句
     --  当SET NOCOUNT为ON时,将不向客户端发送存储过程中每个语句的DONE_IN_PROC消息。
        -- 如果存储过程中包含的一些语句并不返回许多实际数据,则该设置由于大量减少了网络流量,因此可显著提高性能。

     SET  NOCOUNT  ON

    
--  定义错误变量,为raiserror使用
     declare   @ErrorMessage   nvarchar ( 4000 );
    
declare   @ErrorSeverity   int ;
    
declare   @ErrorState   int ;

    
--  注释:
     -- -- 1、为方便调试,在存储过程内部一律使用“--”代替“/* */”
     -- -- 2、每个关键性操作请在前面注释

    
--  变量定义:
     -- -- 1、不要在循环中定义变量
     -- -- 2、如果变量是用于存储某个字段的值,请使变量类型(包括精度)和字段类型一致
     -- -- 3、最好显示的为变量初始化

    
--  变量赋值:
     -- -- 使用set @xxx = ?,不要用早期版本的select @xxx = ?方式
     -- -- 从SQL中为变量赋值采用
     select   @xxx1   =  col1,
           
@xxx2   =  col2
    
from  tabelname

    
--  一次性清空表,请使用truncate代替delete
     truncate   table  tablename

    
--  insert语句要把字段名写全
     insert   into  tablename(col1, col2…)
    
values ( @xxx1 @xxx2 …);

    
--  批量插入
     insert   into  tablename1(col1, col2…) 
    
select  col1, col2…
    
from  tablename2
    ……

    
--  判断语句
     if  ( @xxx1   =  ?  or   @xxx2   =  ?)
    
begin
        ……
    
end
    
else
    
begin
        ……
    
end

    
--  循环语句
     while  ( @xxx1   <>  ?)
    
begin
        ……
    
end

    
--  游标:
     -- -- 尽量避免使用游标

    
-- -- 定义游标
     declare  cursor_xxx  cursor   for
    
select  col1, col2 …
    
from  tablename
    
where  col1  =   @xxx ;

    
-- -- 打开游标
     open  cursor_xxx;

    
-- -- 将游标中的值取到变量中
     fetch   next   from  cursor_xxx
    
into   @xxx1 @xxx2  …;

    
-- -- 开始游标循环
     while  ( @@fetch_status   =   0 )
    
begin
        ……
    
fetch   next   from  cursor_xxx
    
into   @xxx1 @xxx2  …; 
    
end

    
-- -- 结束游标
     close  cursor_xxx;

    
-- -- 销毁游标
     deallocate  cursor_xxx;

    
--  事务
     -- -- 如果显式使用事务,请注意SQL Server默认的事务隔离级别是读提交(Read Committed)
     -- -- 如果使用更高级别的事务隔离级别,请详细阅读帮助文档,避免不必要的锁阻塞
     begin   tran
    
update  ……;
    
commit ;

    
--  异常处理机制
     -- -- 1、在第一次使用异常处理机制之前声明异常变量
     -- -- 2、对容易发生错误的操作,用trycatch进行异常捕获(声明变量不需要)
     -- -- 3、在清理资源后,将错误记录保存在ExecProcdure_ErrorLog表中
     -- ---- ExecProcdure_ErrorLog建表脚本如下:
     -- ---- create table dbo.ExecProcdure_ErrorLog(
     -- ---- [ID] [bigint] identity(1, 1) not null,
     -- ---- [ErrorNumber] [int] null,
     -- ---- [ErrorSeverity] [int] null,
     -- ---- [ErrorState] [int] null,
     -- ---- [ErrorProcedure] [nvarchar](200) null,
     -- ---- [ErrorLine] [nvarchar](50) null,
     -- ---- [ErrorMessage] [nvarchar](4000) null,
     -- ---- [ErrorDateTime] [datetime] null,
     -- ---- constraint [PK_ExecProcdure_ErrorLog] primary key clustered
     -- ---- ([ID] asc ) 
     -- ---- with (IGNORE_DUP_KEY = OFF) ON [primary]
     -- ---- ) ON (primary]
     -- -- 4、最后使用raiserror将错误返回给调用者

    
-- -- 错误处理例子
    ……
    
begin  try
        ……
    
end  try
    
-- -- begin catch 要紧跟着end try,中间不允许有其他语句
     begin  catch
    
-- -- 清理上面try中使用的资源,如删除临时表、销毁游标、回滚事务等
    ……
    
-- -- 设置错误变量
     set   @ErrorMessage   =  ERROR_mESSAGE(),
    
set   @ErrorSeverity   =  ERROR_SEVERITY(),
    
set   @ErrorState   =  ERROR_STATE();

    
-- -- 返回错误信息
     raiserror  ( @ErrorMessage ,
           
@ErrorSeverity ,
           
@ErrorState );
    
    
-- -- 保存错误信息
     insert   into  ExecProcdure_ErrorLog
        (ErrorNumber,
        ErrorSeverity,
        ErrorState,
        ErrorProcedure,
        ErrorLine,
        ErrorMessage,
        ErrorDateTime)
    
select
        ERROR_NUMBER() 
as  ErrorNumber,
        ERROR_SEVERITY() 
as  ErrorSeverity,
        ERROR_STATE() 
as  ErrorState,
        ERROR_PROCEDURE() 
as  ErrorProcedure,
        ERROR_LINE() 
as  ErrorLine,
        ERROR_MESSAGE() 
as  ErrorMessage,
        
getdate ()  as  ErrorDateTime;

    
end  catch

    ……

end

你可能感兴趣的:(存储过程开发模板)