在日常的开发中,sometimes我们会不得不更改一些表结构,多数时候我们是只增不减,但有时我们也会删减一些废弃的字段,更特殊的情况是我们会更改表字段的类型,这样会有一些的连带的问题出现,比方在存储过程或视图中使用到了废弃的字段,类型的改变也会产生不小的影响。如果视图、函数不很很多,单一执行下就能排查哪些受到了影响,但是如果很多呢,上百个视图+存储过程呢?这里我贴出我的解决方式,目前我对这个解决方式也不是特别满意,没有达到我心中的效果,希望看到的朋友有好的解决方案@下憋人。
CREATE TABLE #ErrViewTable (NAMES varchar(8000)) DECLARE @i INT,@totalNum INT,@name VARCHAR(255) DECLARE @t TABLE(id INT IDENTITY ,col VARCHAR(255)) SET NOCOUNT ON INSERT INTO @t SELECT Name FROM dbo.sysobjects WHERE OBJECTPROPERTY(id, N'IsView') = 1 AND ( NOT name IN ( 'sysconstraints', 'syssegments' )) SELECT @totalNum = @@ROWCOUNT , @i = 1 WHILE @i < @totalNum BEGIN SELECT @name = col FROM @t WHERE id = @i EXEC (N'SELECT top 1 * FROM '+ @name) IF(@@error>0) INSERT INTO #ErrViewTable SELECT @name SET @i=@i+1 END SELECT NAMES AS 存在错误的视图 FROM #ErrViewTable
DROP TABLE #ErrViewTable
有些时候我们会更改表的结构,如字段类型,这个时候引用到表的视图是不会自动修改的,有什么办法可以解决这个问题吗?当然有,手动执行下Alter View [ViewName]即可,可是当视图很多的时候这么执行也太不智能了,有没有好的办法呢?当然有,可以构造动态SQL用EXEC来执行就可以了,形式如下
EXEC (‘语句’)
上面的语句执行起来过于笨拙,其实SQL提供了系统的存储过程sp_refreshview, 使用她就可以很优雅的完成这项工作了
DECLARE @t TABLE(id INT IDENTITY,col VARCHAR(255)) DECLARE @i INT,@totalNum int,@name VARCHAR(255) INSERT INTO @t select Name from dbo.sysobjects where OBJECTPROPERTY(id, N'IsView') = 1 and (not name in ('sysconstraints','syssegments')) SELECT @totalNum=@@ROWCOUNT,@i=1 WHILE @i < @totalNum BEGIN SELECT @name = col FROM @t WHERE id = @i EXEC sp_refreshview @name SET @i = @i + 1 END