多语句事务中不允许使用ALTER DATABASE语句


13

我已经从此处下载了基于AdventureWorks的内存中示例,并遵循了随附文档中描述的所有步骤。但是,当我尝试在SQL Server Management Studio中运行脚本时,出现错误消息:

多语句事务中不允许使用ALTER DATABASE语句

错误指向第9行,即:

IF NOT EXISTS (SELECT * FROM sys.data_spaces WHERE type='FX')
    ALTER DATABASE CURRENT ADD FILEGROUP [AdventureWorks2012_mod] 
    CONTAINS MEMORY_OPTIMIZED_DATA
GO

由于这是(或多或少)正式的Microsoft文档,所以我认为这是我做错的事情,但是我不知道这是什么。

Answers:


13

不,您没有做错任何事情。我有同样的事情。我通过将示例分解为多个脚本并在其自己的查询窗口中而不是一个大型脚本中依次运行脚本的每个部分来解决了该问题。就我而言,这是可行的,因为我总是在隔离的VM(而不是在生产服务器上!)上运行这些示例,并且由于我是唯一的一个,因此不需要进行事务处理。

今天再仔细查看一下脚本,没有显式定义事务处理,但是也许您将脚本粘贴到了已经有活动事务的查询窗口中,或者创建了一个自动添加BEGIN TRANSACTION; / COMMIT TRANSACTION;语句的新查询窗口。

我还在这篇博客文章中指出了其他一些潜在的陷阱。


1
“也许您将脚本粘贴到已经有活动事务的查询窗口中”,这似乎是问题所在,因为当我在新窗口中运行整个查询时,它就起作用了。
Petter Brodin 2014年

9

我同意@AaronBertrand,您没有做错任何事情。这不是我第一次看到带有错误的Microsoft脚本。实际上,如果发布了这么多脚本,我会惊讶地发现没有任何脚本。

具体来说,问题是ALTER DATABASE交易根本不允许。您可以在此处看到BOL参考:事务中允许的Transact-SQL语句

实际上,即使像这样简单的脚本也会因相同的错误而失败。

BEGIN TRANSACTION
ALTER DATABASE AdventureWorks2012 SET READ_WRITE
COMMIT

正如亚伦所说,删除事务处理(或至少ALTER DATABASE从事务中的语句),您应该会没事的。


-2

使用“开始”分隔事务。那将解决问题。(比一一运行起来容易。)还可以更改隔离级别(未测试)

SET TRANSACTION ISOLATION LEVEL SERIALISABLE

Begin tran

---Statements goes here

commit tran

SET TRANSACTION ISOLATION LEVEL READ COMMITTED

如果已经确定其他ALTER DATABASE事务中无法执行的代码,则可能需要在发布之前测试代码。将隔离级别设置为SERIALIZABLE对此没有影响。
Max Vernon 2014年

“ GO”不是SQL语句。这是对SSMS的指令,该请求将先前的语句作为批处理提交给SQL Server。如果您觉得很勇敢,可以更改此设置:工具->选项->查询执行-> SQL Server。单个事务中可以提交许多批次。
Michael Green
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.