Tối ưu hóa hiệu suất cơ sở dữ liệu SQL


7

Chúng tôi có cơ sở dữ liệu SQL nặng (SQL Server 2008) và tốc độ chèn giảm sau một thời gian. Tôi đã đọc những câu hỏi tương tự: Tốc độ chèn Sql tăng tốc , SQL: Điều gì làm chậm INSERT nếu không phải CPU hoặc IO? tăng tốc độ CHỨNG MINH .

Ngoài ra, tôi đã đọc bài đăng này về cách phân tích hiệu suất của SQL Server giúp tôi biết cách tìm ra các nút cổ chai (ví dụ: bằng cách truy vấn sys.dm_exec_requestssys.dm_os_wait_stats), nhưng tôi vẫn gặp khó khăn trong việc diễn giải kết quả truy vấn và khắc phục sự cố.

Đầu tiên, tôi bắt đầu với truy vấn sys.dm_exec_requestschỉ trả về một id phiên (chọn truy vấn) với trạng thái "đang chạy" (nghĩa là tôi không tìm thấy BÀI VIẾT NÀO). Vì vậy, nếu không có gì chặn phần chèn của tôi, tại sao nó trở nên chậm?

Tiếp theo, tôi đã sử dụng sys.dm_os_wait_statsđể kiểm tra số liệu thống kê về tất cả các loại chờ. Kết quả cho thấy LATCH_EX, CXPACKETPAGEIOLATCH_SH có nhất wait_time (694.379 ms, 310.364 ms và 308.335 ms tương ứng).

Sau đó, tôi đã sử dụng sys.dm_os_latch_statsđể tìm loại chốt phổ biến nhất mà trong trường hợp của tôi là ACCESS_METHODS_DATASET_PARENT.

  • Trước hết, tôi không biết cách tìm truy vấn liên quan đến từng session_id trong kết quả truy vấn sys.dm_exec_requests.
  • Thứ hai, số lượng thời gian chờ (trong sys.dm_os_wait_stats) nên được coi là cao? Và nếu các số được đề cập ở trên (kết quả của sys.dm_os_wait_stats) cao, làm thế nào tôi có thể giảm chúng?
  • Theo tôi hiểu, ACCESS_METHODS_DATASET_PARENTcó liên quan đến sự song song và một trong những giải pháp tôi tìm thấy là giảm mức độ song song. Có đúng không?
  • Trong MySQL, có một số cài đặt điều chỉnh có thể được thực hiện ngay sau khi cài đặt (ví dụ: tăng kích thước nhóm bộ đệm innodb), có gì tương tự trong SQL Server không?

Một số thông tin thêm:

  • Sử dụng sys.dm_db_index_usage_stats, số lần đọc và ghi lần lượt là 80336 và 70672.

  • Một trong những bảng bận rộn nhất của chúng tôi là trans_all(hiển thị tất cả các giao dịch thanh toán) với KHÔNG TRIGGERS, KHÔNG CONSTRAINTS (điều này giống nhau cho tất cả các bảng), nhưng nó có INDEX CLUSTERED, cụ thể, PK_trans_all bao gồm các cột sau: gs_id (smallint), pt_id (tinyint), Fueling_time (datetime), buy_type (tinyint).

  • Kích thước cơ sở dữ liệu là 2,6 GB và kích thước của trans_allbảng là 155 MB.

CẬP NHẬT_1

Về ACCESS_METHODS_DATASET_PARENT, tôi đã thử giải pháp mà tôi đã tìm thấy (nghĩa là thay đổi mức độ song song. Tôi đã thay đổi nó thành 1 để đảm bảo truy vấn đó không bao giờ đi đến song song), nhưng nó không khắc phục được vấn đề: | Tôi có nên thay đổi nó một lần nữa? mặc định mà tôi nên sử dụng là gì?

CẬP NHẬT_2

Tôi vừa kiểm tra kích thước tệp nhật ký giao dịch cho cơ sở dữ liệu của mình là 2,4 GB và% không gian nhật ký được sử dụng là 98%. Đây có thể là lý do để làm chậm chèn của tôi? Tôi có nên tăng kích thước tệp nhật ký?

Ngoài ra, tôi thường sys.database_fileskiểm tra kích thước tệp và dung lượng trống cho cơ sở dữ liệu của mình. Kết quả cho thấy kích thước tệp là 195 MBdung lượng trống là 0.187 MB .


Tôi luôn thấy sp_WhoIsActive sqlblog.com/files/ Folders/release/tags/who+is+active/ trộm là tuyệt vời cho một ảnh chụp ngắn gọn về những gì đang diễn ra mà không cần phải tìm hiểu về DMV. Nơi nào bạn quan sát 'tốc độ chèn giảm'? Bạn có một ứng dụng front end? Hoặc một logger dữ liệu? Nếu một bộ ghi dữ liệu làm thế nào nó báo cáo giảm tốc độ chèn? Từ mô tả của bạn, tôi đoán có rất nhiều lần chèn bản ghi nhỏ thường xuyên từ nhiều khách hàng hơn là rất nhiều phần chèn dữ liệu số lượng lớn?
Nick.McDilyn

1
Tôi đoán là chỉ mục được nhóm của bạn trên nhiều cột sẽ làm mọi thứ chậm lại, vì bạn sẽ không chèn vào không gian trống và trống ở cuối bảng, mà thay vào đó, chèn vào các trang đã bận rộn ở giữa. Tôi có thể khuyên bạn nên thay đổi chỉ mục được nhóm trên bảng đó thành một ID tăng đơn giản và di chuyển chỉ mục hiện tại của bạn sang một chỉ mục đơn giản không bao gồm nếu cần thiết. Nhưng dba sẽ là một nơi tốt hơn để hỏi, tôi muốn nói ...
Matt Gibson

@MattGibson các phần chèn nằm ở cuối các bảng
monamona

1
Đó có phải là thứ tự chính xác mà chỉ mục cụm của bạn được xác định trong ( gs_id, pt_id, fueling_time, purchase_type) không? Nếu vậy, tôi hy vọng các phần chèn không nằm ở cuối các bảng như bạn đã nói và bạn đang gặp phải một số lượng lớn các phân chia trang trong khi chèn.
GarethD

Đo độ phân mảnh. Là chèn nhanh hơn sau khi bạn chống phân mảnh?
paparazzo

Câu trả lời:


2

Có nhiều yếu tố có thể gây ra sự chậm chạp của chèn như bạn đã mô tả.

Một cái gì đó tôi không thấy trong thông tin của bạn là kích thước Cơ sở dữ liệu / Bảng mà các phần chèn đang đi vào. Khi bảng phát triển, các phần chèn của bạn sẽ mất nhiều thời gian hơn do kích thước bảng, phân mảnh và ghi cùng một dữ liệu vào các chỉ mục của bạn.

Các truy vấn DM bạn đang chạy đã cung cấp cho bạn một số thông tin tốt. Tôi cũng sẽ khuyên bạn nên sử dụng bộ công cụ của Brent Ozar. Liên kết

Tôi sẽ đề nghị bạn sử dụng SP_Blitz Index và SP_BlitzCache. Chúng sẽ cung cấp cho bạn một cái nhìn khác về những gì đang thực sự xảy ra trong cơ sở dữ liệu và những truy vấn chèn bạn đang chạy đang làm gì vào thời điểm đó.

Tôi cũng sẽ kiểm tra lần cuối cùng khi DBCC CHECKDB được chạy và lần cuối cùng bạn xây dựng lại các chỉ mục và số liệu thống kê của mình.

Cảm ơn các bản cập nhật, xem bên dưới:

Một số thông tin thêm:

Không phải là một số lượng lớn đọc / viết nên tôi không quá quan tâm.

Bạn có biết lần cuối cùng chỉ số trans_all được xây dựng lại không? Nếu bạn chỉ có một chỉ mục bao gồm và nhiều lần chèn, sẽ mất nhiều thời gian hơn mỗi lần khi chèn dữ liệu vào nó nếu nó đã lỗi thời. Dưới đây là một truy vấn để kiểm tra phân mảnh trên các bảng cơ sở dữ liệu của bạn:

Use <Database>
GO

SELECT OBJECT_NAME(ind.OBJECT_ID) AS TableName, 
ind.name AS IndexName, indexstats.index_type_desc AS IndexType, 
indexstats.avg_fragmentation_in_percent 
FROM sys.dm_db_index_physical_stats(DB_ID(), NULL, NULL, NULL, NULL) indexstats 
INNER JOIN sys.indexes ind  
ON ind.object_id = indexstats.object_id 
AND ind.index_id = indexstats.index_id 
WHERE indexstats.avg_fragmentation_in_percent > 30 
ORDER BY indexstats.avg_fragmentation_in_percent DESC

CẬP NHẬT 1:

Cài đặt MAX DOP có thể ảnh hưởng đến thời gian chạy truy vấn của bạn, nhưng tôi không thể chắc chắn nó đang làm như vậy mà không thấy truy vấn bạn đang sử dụng và sau đó nhìn vào kết quả kế hoạch ước tính để xem máy chủ SQL nào đang sử dụng. Có hai số liệu thống kê để sử dụng để tìm hiểu xem truy vấn bị ảnh hưởng như thế nào khi điều chỉnh MAX DOP.

SET STATISTICS IO ON;
SET STATISTICS TIME ON;
GO

Dưới đây là một số thông tin của Kendra Little tại Brent Ozar về việc sử dụng chúng để cung cấp cho bạn các hướng dẫn.

tsql-đo-hiệu suất-cải tiến

q-can-high-maxdop-make-a-query-chậm

CẬP NHẬT 2:

Tôi khuyên bạn nên tăng kích thước Nhật ký của mình nếu nó đầy đủ 98%. Hoặc thêm một bản ghi trans hoặc tăng nó. Bạn cũng có thể nhìn vào TEMP_DB và xem nó đang làm gì vì SQL sử dụng điều đó như một bãi rác cho nhiều thứ.

Không gian trống không thực sự là một vấn đề trừ khi bạn hết phòng để phát triển. Nó chỉ cho bạn biết còn lại bao nhiêu phòng cho đến khi chiếc ô tô tiếp theo phát triển.


Cảm ơn vì đã trả lời. Vì vậy, bạn có nghĩ rằng vấn đề không liên quan đến mức độ song song? (vì tôi đã xem ACCESS_METHODS_DATASET_PARENTlà kết quả của sys.dm_os_latch_stats? Ý tôi là, nếu đó không phải là vấn đề tại sao tôi phải sử dụng dmv?
monamona

0

Nếu cơ sở dữ liệu của bạn đang được vận chuyển, thì điều có thể xảy ra là nhật ký được lấp đầy với Giao dịch, sau đó đợi đến lần sao lưu nhật ký tiếp theo trước khi dọn sạch chúng và tạo khoảng trống cho các giao dịch mới tiếp tục xử lý. Hãy thử giảm khoảng cách giữa các giai đoạn Nhật ký vận chuyển hoặc tăng kích thước của tệp nhật ký. Có những thứ khác bạn có thể làm như kiểm tra chỉ số sử dụng chỉ mục và loại bỏ các chỉ mục không sử dụng, bảo trì của chúng sẽ tạo thêm nhu cầu về nhật ký.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.