2016-05-10 10 views
2

私たちのSSDTプロジェクトには、巨大なスクリプトがあり、古いシステムからデータをインポートするためのINSERT文がたくさんあります。 sqlcmd変数を使用して、条件付きでファイルを展開後スクリプトに含めることができます。私は条件付きでssdt post配備スクリプトに大きなスクリプトを含めることができますか?

我々は現在、スクリプトをインラインで含まれ:r構文を使用している:スクリプトはインラインかかわらず$(ImportData)がtrueまたはfalseで、ファイルがあるかどうかの含まれているため、

IF '$(ImportData)' = 'true' 
BEGIN 
    :r .\Import\OldSystem.sql 
END 

これは問題です非常に大きいので、ビルドを約15分遅くしています。

このスクリプトファイルを条件付きで含めてビルドの速度を落とさない別の方法はありますか?

+1

:Rコマンドと他のすべてのSQLCMDコマンドは、条件ブロック内では機能しません。常に実行されます。この問題を回避するには、Old SystemSqlファイルでIF '$(ImportData)' = 'true'を使用して古いシステムコードをラップすることです。 –

+0

http://stackoverflow.com/a/7189002/623190 –

+0

パフォーマンスについては、 INSERTではなく? –

答えて

0

これを実現するために、ビルドツール(Jenkins)とSSDTを組み合わせて使用​​しました。これは私がしたことです:

  1. テキストファイルに書き込む各環境固有のJenkinsジョブにビルドステップを追加しました。私は、インポートファイルを含むSQLCMDコマンドを書くか、そうでなければ、ユーザーが選択したビルドパラメータに応じて空白のままにします。
  2. :rを介して、配置後スクリプトに新しいテキストファイルを含めます。

これだけです!また、この同じ手法を使用して、アプリケーションバージョンに基づいてプロジェクトに含める事前配布スクリプトと配布後スクリプトを選択します。ただし、コードからバージョン番号を取得し、代わりにVSで事前ビルドイベントを使用してファイルに書き込みますビルドツールの(テキストファイル名を.gitignoreに追加してコミットしないようにしました)

1

:rを使用して参照されるスクリプトは常に含まれます。いくつかのオプションがありますが、スクリプトを取り出すとパフォーマンスが向上することをまず確認します。

最も単純なアプローチは、ビルドプロセス全体の外に置いて、展開プロセスを変更して2段階になるようにすることです(DACを展開してからスクリプトを展開する)。これのポジティブな点は、ssdtプロセスの外でも実行できることですが、配備時に変更されるテーブルの制約を自動的に無効にするようなことはありません。

2番目の方法は、ビルド時にスクリプトにスクリプトを含めないことですが、dacpacでスクリプトをポストデプロイスクリプトとして追加するAfterBuild msbuildタスクを作成することです。 dacpacはzipファイルなので、.NETパッケージングApiを使用してpostdeploy.sqlという名前のパーツを追加し、展開プロセスに含めます。

これらの2つの方法は、検証を失うため、メインプロジェクトと同じデータベース参照を持つ別のssdtプロジェクトに保存したい場合は、変更があったときにビルドを遅くしますが、残りの時間。

0

これは私がそれをしなければならない方法です。

1)ダミーの展開後スクリプトを作成します。

2)展開シナリオごとにプロジェクトでビルド構成を作成します。

3)pre-buildイベントを使用して、使用するデプロイメント後の構成を判断します。 設定ごとに別々のスクリプトを作成することも、ビルド前のイベントで展開後スクリプトを動的にビルドすることもできます。どちらの方法でも、ビルド・イベントに常に存在する$(構成)の値に基づいて作業します。

個別の静的スクリプトを使用する場合、ビルドイベントでは、適切な静的ファイルをコピーするだけで、その展開シナリオで有用なスクリプトを使用してダミーのポストデプロイメントを上書きする必要があります。

私の場合、どのスクリプトを含めるかの決定には、デプロイされるデータベースの現在の状態を知る必要があるため、動的生成を使用する必要がありました。そこで、構成変数を使用して、どの環境がどの環境に展開されているかを教えて、SQLCMDスクリプトを使用しました。OUTを自分の配置後スクリプトの場所に設定しました。したがって、私のプリビルドスクリプトは、配布後のスクリプトを動的に記述します。

どちらの方法でも、ビルドが完了し、通常のデプロイプロセスが開始された後、デプロイ後のスクリプトには、私が望むような:rコマンドが含まれていました。

ここでは、プリビルドで呼び出すSQLCMDスクリプトの例を示します。

:OUT .\Script.DynamicPostDeployment.sql 

PRINT ' /*'; 
PRINT '  DO NOT MANUALLY MODIFY THIS SCRIPT.            '; 
PRINT '                      '; 
PRINT '  It is overwritten during build.             '; 
PRINT '  Content IS based on the Configuration variable (Debug, Dev, Sit, UAT, Release...) '; 
PRINT '                      '; 
PRINT '  Modify Script.PostDeployment.sql to effect changes in executable content.   '; 
PRINT ' */'; 
PRINT 'PRINT ''PostDeployment script starting at''+CAST(GETDATE() AS nvarchar)+'' with Configuration = $(Configuration)'';'; 
PRINT 'GO'; 
IF '$(Configuration)' IN ('Debug','Dev','Sit') 
BEGIN 
    IF (SELECT IsNeeded FROM rESxStage.StageRebuildNeeded)=1 
    BEGIN 
     -- These get a GO statement after every file because most are really HUGE 
     PRINT 'PRINT ''ETL data was needed and started at''+CAST(GETDATE() AS nvarchar);'; 
     PRINT '             '; 
     PRINT 'EXEC iESxETL.DeleteAllSchemaData ''pExternalETL'';'; 
     PRINT 'GO'; 
     PRINT ':r .\PopulateExternalData.sql   '; 
.... 
2

私の以前の回答を別のものに上げるのではなく、非常にシンプルなオプションの特別なケースがあります。

実行可能性ごとに個別のSQLCMD入力ファイルを作成します。 ここでのキーは、コントロール変数の値を使用して実行入力ファイルに名前を付けることです。

たとえば、パブリッシュスクリプトは、 'Dev'、 'QA'、または 'Prod'のいずれかの値を持つ変数 'Config'を定義します。

「DevPostDeploy.sql」、「QAPostDeploy.sql」、および「ProdPostDeploy.sql」という3つの導入後スクリプトを作成します。

コードこのような実際のポストデプロイファイル:

:R「\」$(コンフィグ)PostDeploy.sql

これは非常にあなたが適切なものとするスクリプトを上書きし、ビルドイベントメカニズムのようなものですただし、ビルド・イベントは必要ありません。しかし、あなたはスクリプトを非常に具体的に命名することに依存しています。

+0

データベースは、この方法で使用される異なるSQLCMDプロパティで2回展開されます。両方の配備で、2番目の配備で渡された値のみが使用されます。それは、最初のものの値が上書きされるようなものです。それらは順番に行われます...最初の展開のターゲット接続は正しいものです。 – MrFox

+0

公正な警告 - まだVS2013がついていない場合、この方法で含まれているファイルは必ずしも「公開」ダイアログと一致するとは限りません。 SQLCMD変数タブの* Project *プロパティで指定された変数の値に基づいてファイルが常に含まれるように見えます。私はVisual Studioのより新しいバージョンではテストしていません。 – Nathan

関連する問題