SSMS 18 で Diagram が無くなった

追記:18.1 で復活しました
SSMS 18.1 で Diagram が復活した - お だ のスペース

SSMS 18.0 が GA しました。*1
Download SQL Server Management Studio (SSMS) - SQL Server | Microsoft Docs

リリースノートの 「Deprecated and removed features in 18.0 (GA)」の中で Database Diagrams が Removed になっています。
Release notes for SQL Server Management Studio (SSMS) - SQL Server | Microsoft Docs
Diagram で編集はしないけど、たまに見るのに使ってたんだよ。。
これの代用機能は今のところ無さげなので、サードパーティー製の何かを使うか、SSMS 17 を使う必要がありそうです。

フィードバックサイトでも乱立しています。。
Database diagrams on new release 18 not work – Customer Feedback for Microsoft Azure
Database Diagram – Customer Feedback for Microsoft Azure
Database Diagram – Customer Feedback for Microsoft Azure
using sql server management studio database diagram extensively. essential part of databases. Why is it not included in sql 2019? – Customer Feedback for Microsoft Azure
SSMS 2018 Database Diagrams - Display Only – Customer Feedback for Microsoft Azure

SQL Server も普通のテーブル以外に、Graph とか増えたので GUI で編集するのが辛くなってきたのかな?
SQL Database Edge | Microsoft Azure で、時系列も増えるっぽいし。

個人的には、一番下の Feedback の Dispkay only な Diagram として復活してくれると嬉しいなぁ。

他にも T-SQL Debugger とかも Removed になっていますが、Debugger は SSDT で代用出来るのでまあ良いんじゃないでしょうか。

*1:日本語サイトは、未だ 17.9.1 が表示される

.NET Core の DacFx の bacpac 試してみた

.NET Core 2.2 のコンソールアプリなら、
NuGet Gallery | Microsoft.SqlServer.DACFx 150.4384.2-preview
でシンプルな DB なら問題無く bacpac 取れた。

.NET Core 2.1 なら、幾つかのアセンブリが古いっぽいので、バージョン上げたら動いた。

  • System.Data.SqlClient
  • System.IO.Packaging
  • System.Security.Permissions

DacFx .NET Core Support · Issue #20 · Microsoft/DACExtensions · GitHub

そろそろ正式くるかなー?

.NET で SQL Server/Database のbacpac を取得する

質問されたので書いときます。

DacFx 使ってサクッと出来ますよ~。
NuGet Gallery | Microsoft.SqlServer.DacFx.x64 150.4384.2

var connstr = @"~";
var dac = new DacServices(connstr);
dac.ExportBacpac(@"d:\TurorialDB.bacpac", "TutorialDB");

細かいオプション渡したい場合は、ドキュメント見てください。
ドキュメントは1年前のバージョンのようでちょっと古いですが、そんな大幅に変わってるとこは無さそう?
DacServices Class (Microsoft.SqlServer.Dac) | Microsoft Docs

注意点は .NET Core の DacFx は未だ正式提供されていないので、.NET Framework でお願いします。
※.NET Core のは Preview で提供されています。
NuGet Gallery | Microsoft.SqlServer.DACFx 150.4384.2-preview

これくらいなら PowerShell で書いてしまってもいいかもしれません。
アセンブリの参照だけ気を付けたらサクッと書けると思います。
Microsoft.SqlServer.Dac.dll は依存してる dll が幾つかあるので、それを読めるとこに置いとく必要あり。

メモ:コネクションプールを使ってる時の SqlConnection を Close した時の内部動作

GitHub 上でコード追っかけたのでメモ
※実行してトレースしたわけでは無いので間違ってるかも

生きてる SqlTransaction があっても、Rollback 呼んでそう。

SqlConnection.Close() で SqlConnection.CloseInnerConnection()
https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/SqlClient/SqlConnection.cs#L683

SqlConnection.CloseInnerConnection() で InnerConnection.CloseConnection()
https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/SqlClient/SqlConnection.cs#L637

SqlClient.InnerConnection の定義
https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/SqlClient/SqlConnectionHelper.cs#L92

DbConnectionInternal.CloseConnection() で connectionPool.PutObject()
https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/ProviderBase/DbConnectionInternal.cs#L270

DbConnectionPool.PutObject() で DeactivateObject()
https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/ProviderBase/DbConnectionPool.cs#L1454

DbConnectionPool.DeactiveObject() で DbConnectionInternal.DeactivateConnection()
https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/ProviderBase/DbConnectionPool.cs#L762

DbConnectionInternal.DeactiveConnection() で Deactivate()
https://github.com/dotnet/corefx/blob/v2.2.3/src/Common/src/System/Data/ProviderBase/DbConnectionInternal.cs#L241

SqlInternalConnection.Deactivate() で InternalDeactivate()
https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/SqlClient/SqlInternalConnection.cs#L262

SqlinternalConnectionTds.InternalDeactivate() で _parse.Deactivate()
https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/SqlClient/SqlInternalConnectionTds.cs#L768

TdsParser.Deactivate() で currentTransaction.CloseFromConnection()
https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/SqlClient/TdsParser.cs#L924

SqlInternalTransaction.CloseFromConnection() で innerConnection.ExecuteTransaction()
https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/SqlClient/SqlInternalTransaction.cs#L253

SqlInternalConnectionTds.ExecuteTransaction() で ExecuteTransactionYukon()
https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/SqlClient/SqlInternalConnectionTds.cs#L857

SqlInternalConnectionTds.ExecuteTransactionYukon() で _parser.TdsExecuteTransactionManagerRequest() https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/SqlClient/SqlInternalConnectionTds.cs#L986

TdsParser.TdsExecuteTransactionManagerRequest https://github.com/dotnet/corefx/blob/v2.2.3/src/System.Data.SqlClient/src/System/Data/SqlClient/TdsParser.cs#L6608

名前に Yukon とか出てきたけど、2005 のコードネームやっけ。

メモ:SQL Server 2019 Hybrid Buffer Pool

2019 の新機能見てて何やろ~?って思ったのでメモ。
Hybrid Buffer Pool - SQL Server | Microsoft Docs
2019 CTP2.1 から。

PMEM に データベース ファイル を置いてると、バッファープール に読み込まずに直接読むっぽい。
直接読むのは クリーン ページ だけ、ダーティページは今まで通りの動き。
ダーティページって何や~?ってサクッと書くと、変更があったけど未だ物理に書き込まれていない状態のページのこと。

NVDIMM-N 対応は、2016 SP1 で入った ログファイル を NVDIMM に置いてログバッファに使う Tail of Log ってのがあったけど、
Transaction Commit latency acceleration using Storage Class Memory in Windows Server 2016/SQL Server 2016 SP1 | SQL Database Engine Blog
Configuring Storage Spaces with a NVDIMM-N write-back cache - SQL Server | Microsoft Docs
今回のでデータファイルも PMEM に置いてパフォーマンス向上するって感じなんですかね。

環境無いので試せてないからアレ。

メモ:create table で filtered な unique index を作る

ドキュメントの構文に載ってないけどなんか出来たのでメモ。

SQL Server での unique 制約は unique index で実現されてます。
なので、unique 制約を作る = unique index を作る です。

UNIQUE 制約を作る場合
Create Unique Constraints - SQL Server | Microsoft Docs

後から UNIQUE INDEX 作る場合
Create Unique Indexes - SQL Server | Microsoft Docs

filtered ってなんやーですが、SQL Server では index を作る時に条件指定して index を作ることが出来ます。
Create Filtered Indexes - SQL Server | Microsoft Docs

特定の状態のデータに対して index を作りたい場合に使う感じ。
これを利用すると、複数行に null が含む列に対して unique 制約を付けることも出来ます。*1

で、create table の時にまとめて作るのはドキュメントでは出来なさそうだけど、何か書けたのでメモ。
CREATE TABLE (Transact-SQL) - SQL Server | Microsoft Docs

ドキュメントに無い構文だけど、エラーが出なかったクエリ例

create table [サンプル] (
  [有効なデータでは一意なId] bigint not null, 
  [状態] nchar(2) not null,
  index [UX_サンプル_Id] unique ([有効なデータでは一意なId]) where [状態] = N'有効'
)

ドキュメントでは

< table_constraint > ::=  
[ CONSTRAINT constraint_name ]   
{   
    { PRIMARY KEY | UNIQUE }   
        [ CLUSTERED | NONCLUSTERED ]   
        (column [ ASC | DESC ] [ ,...n ] )   
        [   
            WITH FILLFACTOR = fillfactor   
           |WITH ( <index_option> [ , ...n ] )   
        ]  
        [ ON { partition_scheme_name (partition_column_name)  
            | filegroup | "default" } ]   
    | FOREIGN KEY   
        ( column [ ,...n ] )   
        REFERENCES referenced_table_name [ ( ref_column [ ,...n ] ) ]   
        [ ON DELETE { NO ACTION | CASCADE | SET NULL | SET DEFAULT } ]   
        [ ON UPDATE { NO ACTION | CASCADE | SET NULL | SET DEFAULT } ]   
        [ NOT FOR REPLICATION ]   
    | CHECK [ NOT FOR REPLICATION ] ( logical_expression )  

< table_index > ::=   
{  
    {  
      INDEX index_name [ CLUSTERED | NONCLUSTERED ]   
         (column_name [ ASC | DESC ] [ ,... n ] )   
    | INDEX index_name CLUSTERED COLUMNSTORE  
    | INDEX index_name [ NONCLUSTERED ] COLUMNSTORE (column_name [ ,... n ] )  
    }  
    [ WITH ( <index_option> [ ,... n ] ) ]   
    [ ON { partition_scheme_name (column_name )   
         | filegroup_name  
         | default   
         }  
    ]   
    [ FILESTREAM_ON { filestream_filegroup_name | partition_scheme_name | "NULL" } ]  

}  

ってなってるので、constraint で unique 付ける場合に where は指定出来ないとなってるし、
index の方では、unique 指定出来ないし where もダメってなってる。

普通に unique index を作る場合は、

create unique index [UX_サンプル_Id] on [サンプル] ([有効なデータでは一意なId]) where [状態] = N'有効'

って構文なので、unique の位置が変わるのは注意点?

ただ、ドキュメントに載ってないのでどのバージョンで使えるのかは動かしてみないと分からない。。
とりあえず SQL Server 2016、SQL Database v12 では動いてる。
SQL DB v12 で動いてるから、新しい SQL Server なら問題なさそう。

*1:not null を条件に付ける