相信,很多網友都有用SQL界面生成腳本再執行的習慣,今天在CSDN看到一個案例,好大的風險-_-!!!
本示例是將一個表的列由datetime變成char型:
step 1 生成數據庫:
USE master GO --創建測試數庫 CREATE DATABASE [DB_TEST] ON PRIMARY ( NAME = N'DB_TEST', FILENAME = N'D:\SQL2008\Data\DB_TEST.mdf' , SIZE = 512MB , FILEGROWTH = 1024KB, MAXSIZE = 524288KB ) LOG ON ( NAME = N'DB_TEST_log', FILENAME = N'D:\SQL2008\Log\DB_TEST_log.ldf' , SIZE = 1024KB , FILEGROWTH = 1024KB ) GO
step 2 生成表,並生成測試數據
USE [DB_TEST] GO CREATE TABLE TB_TEST (ID INT IDENTITY(1,1) PRIMARY KEY,B DATETIME) GO INSERT INTO TB_TEST SELECT GETDATE() GO 100000
step 3 通過界面修改列類型,然后生成腳本:
生成的腳本為:
BEGIN TRANSACTION SET QUOTED_IDENTIFIER ON SET ARITHABORT ON SET NUMERIC_ROUNDABORT OFF SET CONCAT_NULL_YIELDS_NULL ON SET ANSI_NULLS ON SET ANSI_PADDING ON SET ANSI_WARNINGS ON COMMIT BEGIN TRANSACTION GO CREATE TABLE dbo.Tmp_TB_TEST ( ID int NOT NULL IDENTITY (1, 1), B char(7000) NULL ) ON [PRIMARY] GO ALTER TABLE dbo.Tmp_TB_TEST SET (LOCK_ESCALATION = TABLE) GO SET IDENTITY_INSERT dbo.Tmp_TB_TEST ON GO IF EXISTS(SELECT * FROM dbo.TB_TEST) EXEC('INSERT INTO dbo.Tmp_TB_TEST (ID, B) SELECT ID, CONVERT(char(7000), B) FROM dbo.TB_TEST WITH (HOLDLOCK TABLOCKX)') GO SET IDENTITY_INSERT dbo.Tmp_TB_TEST OFF GO DROP TABLE dbo.TB_TEST GO EXECUTE sp_rename N'dbo.Tmp_TB_TEST', N'TB_TEST', 'OBJECT' GO ALTER TABLE dbo.TB_TEST ADD CONSTRAINT PK__TB_TEST__3214EC277F60ED59 PRIMARY KEY CLUSTERED ( ID ) WITH( STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY] GO COMMIT
step 4 然后把生成的腳本拿到ssms query里去執行,悲懼了:
文字為:
Msg 1105, Level 17, State 2, Line 1
無法為數據庫 'DB_TEST' 中的對象 'dbo.Tmp_TB_TEST' 分配空間,因為 'PRIMARY' 文件組已滿。請刪除不需要的文件、刪除文件組中的對象、將其他文件添加到文件組或為文件組中的現有文件啟用自動增長,以便增加可用磁盤空間。
Msg 1088, Level 16, State 11, Line 1
找不到對象 "dbo.Tmp_TB_TEST",因為它不存在或者您沒有所需的權限。
Msg 15248, Level 11, State 1, Procedure sp_rename, Line 321
參數 @objname 不明確或所聲明的 @objtype (OBJECT)有誤。
Msg 4902, Level 16, State 1, Line 1
找不到對象 "dbo.TB_TEST",因為它不存在或者您沒有所需的權限。
Msg 3902, Level 16, State 1, Line 1
COMMIT TRANSACTION 請求沒有對應的 BEGIN TRANSACTION。
step 5 你再去查看表,發現你要修改的表不見了。。
step 6 重新再做一遍,這次我們用界面操作顯示如下圖,但表沒有消失:
step 7 修改生成的腳本,去掉GO,再執行:
雖然報錯了,但可以看到表還在。
step 8 嘗試用ApexSQL Recover恢復一下:
選擇由於Drop table造成的數據丟失:
中間部分過程圖:
生成的腳本:測試版有限制
總結:生成腳本有風險,使用須謹慎。