web-dev-qa-db-ja.com

varbinary(max)列を使用したスロー削除

処理される前にWebアプリケーションからアップロードされたデータを一時的に保持する2つのテーブルがあります。これは、Azure SQLデータベースで実行されています。

ファイルをアップロードする

_Id uniqueidentifier
CustomerId uniqueidentifier
FileName nvarchar(MAX) NULL
UploadDate datetime
UploadedBy nvarchar(MAX) NULL
_

UploadFileChunk

_Id uniqueidentifier
Data varbinary(MAX) NULL
UploadFileId uniqueidentifier
[Index] int
_

UploadFileには、UploadFileChunkへのカスケード削除を伴う外部キーがあります。 UploadFileChunkUploadFileIdに非クラスター化インデックスを持っています。それぞれ1MBのチャンクをアップロードしています。

このデータの挿入と読み取りは非常にうまく機能していますが、データが処理された後にUploadFileからレコードを削除すると、本当に遅くなります。 S0 10 DTUテストのAzure環境では、子のチャンクが500個以下の12個のレコードをまとめて削除するのに38分かかりました(例に過ぎません。高出力の本番環境と高速のローカルマシンではパフォーマンスが低下します)。

どうすれば速くできますか?

_UploadFileChunk.FileUploadId_のインデックスがです。これが 実行計画 です。

次のクエリを実行しました( [SQL Azureでのブロッククエリの検索 から))。スローデリートは途中で行われ、結果は返されませんでした。

_SELECT TOP 10
    r.session_id,
    r.plan_handle,
    r.sql_handle,
    r.request_id,
    r.start_time,
    r.status,
    r.command,
    r.database_id,
    r.user_id,
    r.wait_type,
    r.wait_time,
    r.last_wait_type,
    r.wait_resource,
    r.total_elapsed_time,
    r.cpu_time,
    r.transaction_isolation_level,
    r.row_count,
    st.text
FROM sys.dm_exec_requests r
CROSS APPLY sys.dm_exec_sql_text(r.sql_handle) AS st
WHERE
    r.blocking_session_id = 0
    AND r.session_id IN 
    (
        SELECT DISTINCT (blocking_session_id) FROM sys.dm_exec_requests)
GROUP BY
    r.session_id,
    r.plan_handle,
    r.sql_handle,
    r.request_id,
    r.start_time,
    r.status,
    r.command,
    r.database_id,
    r.user_id,
    r.wait_type,
    r.wait_time,
    r.last_wait_type,
    r.wait_resource,
    r.total_elapsed_time,
    r.cpu_time,
    r.transaction_isolation_level,
    r.row_count,
    st.text
ORDER BY
    r.total_elapsed_time DESC;
_

切り捨ては[削除するより]速いかもしれませんが、これらの2つのテーブルには複数のファイルのデータが含まれているため、一度に1つずつ削除できる必要があります。 nvarchar(max)列はおそらく別のものになる可能性があります。これは、ドメインクラスに基づいてEntity Frameworkが生成したものにすぎません。それがこの問題に役立つと思いますか?

FileUploadChunksから直接レコードを削除するのと同じくらい遅いことを確認しました。私の非常に遅い例(S0 10 DTU)では、削除された行ごとに約1秒です。

4
James Orr

Microsoftのゴールドパートナーサポートとの1週間のやり取りを終えたところです。彼らは、この状況は改善されておらず、これらの遅い削除はSQL Azure/2016の通常の動作であることを確認しています。

1
James Orr