如何根据部署配置文件

时间:2016-02-03 10:11:15

标签: publish sql-server-data-tools

我在Visual Studio 2013中使用SSDT。

我为开发服务器创建了一些发布前和发布后脚本。预部署脚本从表中清空数据并重新设置所有自动标识字段。部署后脚本使用静态和示例数据填充表。

现在我需要将数据库发布到我们的登台和实时数据库服务器。我为这些服务器创建了新的“publish.xml”配置文件。但显然我不希望运行相同的前后脚本。

如何根据发布配置文件指定不同的脚本,或使脚本知道目标并执行不同的操作。

我最担心的是发布到实时服务器并意外破坏数据。

提前致谢。

道格

4 个答案:

答案 0 :(得分:5)

您有几个选择:

1 - 在对@servername的调用或环境特有的内容中包含您的数据更改,以便您有类似的内容:

if @@servername = 'dev_server'
begin
     delete blah
     insert blah

end

2 - 你也可以使用sqlcmd变量实现类似的东西,传入一个名为“/ v:DestoryData = true”的变量,然后你可以在你的脚本中引用它。

3 - 不要使用前/后部署脚本,但有自己的运行机制,即使用批处理文件来部署dacpacs并在之前和之后添加对sqlcmd的调用 - 这是在部署时的缺点,对表的更改会导致在预部署之前禁用任何外键,并在部署后重新启用。

4 - 编辑dacpacs,前/后部署脚本只是dacpac中的文本文件,它本质上是一个遵循microsoft打包格式的zip文件,并且有一个.net打包api可以让你修改它。

我认为就是这样,请问是否有任何不清楚的地方:)

答案 1 :(得分:4)

我建议使用SQLCMD变量来执行条件脚本。

如果右键单击数据库项目并选择“属性”,则会出现一个选项卡" SQLCMD变量"

DB Properties

输入" $(ServerName)"作为变量和某些东西作为默认值。

然后你需要在XML编辑器中打开你的每个.publish.xml,在PropertyGroup部分之后插入以下代码:

<ItemGroup>
    <SqlCmdVariable Include="ServerName">
        <Value>[YourVersionOfServer]</Value>
    </SqlCmdVariable>
</ItemGroup>

[YourVersionOfServer]应该等于每台服务器上@@ servername的结果。

最终的.publish.xml可能如下所示:

enter image description here

然后,您应该使用以下命令将部署代码中的条件代码包装起来:

if @@servername = '$(ServerName)'
begin
    ... code for specific server
end

因此,您可以保证正确的代码能够访问正确的服务器

答案 2 :(得分:0)

首先通过右键单击项目并转到属性和“ SQLCMD变量”选项卡来设置SQLCMD变量: Project Properties

然后为您设置一个文件夹结构,以组织要为特定服务器运行的脚本或要关闭的其他任何事物(例如客户)。每个服务器获得的文件夹。我喜欢将要为该文件夹运行的所有脚本打包到该文件夹​​中的索引文件中。索引列出了:r命令,后跟应该运行的文件夹中的每个脚本,均按带有数字前缀的文件名进行组织,以便可以控制顺序。

Folder Structure

在对所有服务器文件夹进行分组的文件夹中的索引文件中,与列出对每个服务器的索引文件的调用相比,它会执行不同的操作,而是根据基于发布的传入SQLCMD变量切换要运行的索引文件轮廓。使用以下简单代码即可做到这一点:

:r .\$(Customer)\Index.sql

之所以要通过设置文件夹和索引文件来做到这一点,是因为它不仅可以使事情井井有条,而且还允许您在所有文件中使用Go语句。然后,您可以将一个脚本与:r语句一起用于要运行的所有其他脚本,以嵌套您的内心内容。 您可以按照以下方式设置sqlcmd文件来执行此操作,该方法不需要设置文件夹或文件的特定名称,但是需要删除所有GO语句。通过上述方法,您不必删除任何go语句。

if @@servername = '$(ServerName)'
begin
    ... code for specific server
end

然后,当我右键单击该项目并单击“发布”时,它将构建该项目并弹出以下对话框。我可以通过更改SQLCMD变量来更改要运行的脚本。 Publish Database Dialog

我想将最常用的设置保存为单独的发布配置文件,然后只需在解决方案资源管理器中单击它的.xml文件即可返回到它。此过程使一切变得如此简单,无需手动修改xml,只需使用上面显示的“发布数据库”对话框单击“将配置文件另存为”,“加载配置文件”或“创建配置文件”即可。

此外,您可以使用以下powershell脚本生成索引文件:

foreach($directory in (Get-ChildItem -Directory -Recurse) | Get-Item)
{
    #skip writing to any index file with ---Ignore in it.
    if(-Not ((Test-Path $directory\Index.sql) -and (Get-Content $directory\Index.sql | %{$match = $false}{ $match = $match -or $_ -match "---Ignore" }{$match})))
    {
        $output = "";
        foreach($childitem in (Get-ChildItem $directory -Exclude Index.sql, *.ps1 | Sort-Object | Get-Item))
        {
            $output= $output + ":r .\" + $childitem.name 
            if($childitem -is [system.io.directoryinfo])
            {
                $output = $output + "\Index.sql";
            }
            $output = $output + "`r`n"
        }
        Out-File $directory\Index.sql -Encoding utf8 -InputObject $output       
    }
}

答案 3 :(得分:0)

对于任何想知道您也可以这样做的人:

发布个人资料:

<ItemGroup>
    <SqlCmdVariable Include="Environment">
        <Value>Dev</Value>
    </SqlCmdVariable>
</ItemGroup>

部署后脚本:

if '$(Environment)' = 'Dev'
begin
    ... code for specific server
end

与“ServerName”语义相比,这种方式对我来说似乎更自然一些。我在尝试使用 @@servername 时也遇到了问题,但不知道为什么。