Sqlserver
 sql >> Cơ Sở Dữ Liệu >  >> RDS >> Sqlserver

Sự cố sao chép giao dịch SQL Server

Chúng tôi đã bắt đầu nói về các vấn đề sao chép giao dịch SQL Server trước đó. Bây giờ, chúng tôi sẽ tiếp tục với một số bản trình diễn thực hành khác để hiểu các vấn đề về hiệu suất Nhân bản thường gặp phải và cách khắc phục chúng một cách chính xác.

Chúng tôi đã thảo luận về các vấn đề như vấn đề về cấu hình, vấn đề về quyền, vấn đề về kết nối và vấn đề về tính toàn vẹn dữ liệu cùng với việc khắc phục sự cố và khắc phục chúng. Bây giờ, chúng ta sẽ tập trung vào các vấn đề Hiệu suất khác nhau và các vấn đề về Lỗi ảnh hưởng đến tính năng Sao chép máy chủ SQL.

Vì vấn đề tham nhũng là một chủ đề lớn, chúng tôi sẽ chỉ thảo luận về tác động của chúng trong bài viết này và sẽ không đi sâu vào chi tiết. Tôi đã chọn một số tình huống có thể thuộc các vấn đề về Hiệu suất và Tham nhũng dựa trên kinh nghiệm của mình:

  • Vấn đề về Hiệu suất
    • Các giao dịch đang hoạt động lâu dài trong cơ sở dữ liệu của nhà xuất bản
    • Thao tác CHÈN / CẬP NHẬT / XÓA hàng loạt trên Bài viết
    • Thay đổi dữ liệu lớn trong một Giao dịch duy nhất
    • Chặn trong cơ sở dữ liệu phân phối
  • Các vấn đề liên quan đến tham nhũng
    • Lỗi Cơ sở dữ liệu Nhà xuất bản
    • Lỗi Cơ sở dữ liệu Phân phối
    • Lỗi Cơ sở dữ liệu Người đăng ký
    • Lỗi Cơ sở dữ liệu MSDB

Vấn đề về Hiệu suất

SQL Server Transactional Replication là một kiến ​​trúc phức tạp bao gồm một số tham số như cơ sở dữ liệu Nhà xuất bản, cơ sở dữ liệu Nhà phân phối (phân phối), cơ sở dữ liệu Người đăng ký và một số Tác nhân nhân bản thực thi dưới dạng công việc SQL Server Agent.

Như chúng ta đã thảo luận chi tiết về tất cả các mục này trong các bài viết trước của mình, chúng ta biết tầm quan trọng của từng mục đối với chức năng Nhân bản. Bất kỳ điều gì tác động đến các thành phần này đều có thể ảnh hưởng đến hiệu suất của SQL Server Replication.

Ví dụ:phiên bản cơ sở dữ liệu Publisher đang giữ một cơ sở dữ liệu quan trọng với rất nhiều giao dịch mỗi giây. Tuy nhiên, tài nguyên Máy chủ có một nút cổ chai như mức sử dụng CPU nhất quán trên 90% hoặc Mức sử dụng bộ nhớ trên 90%. Nó chắc chắn sẽ có tác động đến hiệu suất Công việc của Tác nhân Trình đọc Nhật ký, công việc này đọc dữ liệu thay đổi từ Nhật ký Giao dịch của cơ sở dữ liệu Nhà xuất bản.

Tương tự, bất kỳ trường hợp nào như vậy trong các trường hợp cơ sở dữ liệu Nhà phân phối hoặc Người đăng ký đều có thể ảnh hưởng đến Đại lý Ảnh chụp hoặc Đại lý Phân phối. Vì vậy, với tư cách là một DBA, bạn cần đảm bảo rằng các tài nguyên máy chủ như CPU, Bộ nhớ vật lý và băng thông mạng được định cấu hình hiệu quả cho các phiên bản cơ sở dữ liệu Nhà xuất bản, Nhà phân phối và Người đăng ký.

Giả sử rằng máy chủ cơ sở dữ liệu Nhà xuất bản, Người đăng ký và Nhà phân phối được định cấu hình chính xác, chúng tôi vẫn có thể gặp sự cố về hiệu suất Sao chép khi gặp các tình huống dưới đây.

Giao dịch đang hoạt động kéo dài trong Cơ sở dữ liệu nhà xuất bản

Như tên cho biết, các giao dịch Hoạt động trong thời gian dài cho thấy rằng có một lệnh gọi Ứng dụng hoặc một hoạt động của người dùng trong phạm vi giao dịch được thực thi trong một thời gian dài.

Việc tìm thấy một Giao dịch đang hoạt động trong thời gian dài có nghĩa là giao dịch đó chưa được cam kết và có thể được ứng dụng khôi phục hoặc cam kết. Điều này sẽ ngăn Nhật ký giao dịch không bị cắt ngắn, dẫn đến kích thước tệp Nhật ký giao dịch tăng liên tục.

Tác nhân đọc nhật ký quét tất cả các bản ghi đã cam kết được đánh dấu để sao chép từ Nhật ký giao dịch theo thứ tự tuần tự dựa trên Số thứ tự nhật ký (LSN), bỏ qua tất cả các thay đổi khác xảy ra đối với các bài viết không được sao chép. Nếu các lệnh giao dịch Hoạt động lâu dài chưa được cam kết, thì Replication sẽ bỏ qua việc gửi các lệnh đó và gửi tất cả các giao dịch đã cam kết khác tới cơ sở dữ liệu phân phối. Khi giao dịch Hoạt động lâu dài được cam kết, các bản ghi sẽ được gửi đến cơ sở dữ liệu phân phối và cho đến thời điểm đó, phần không hoạt động của tệp Nhật ký giao dịch của Publisher DB sẽ không bị xóa, do đó khiến kích thước tệp Nhật ký giao dịch của cơ sở dữ liệu Nhà xuất bản tăng lên.

Chúng tôi có thể kiểm tra kịch bản Giao dịch hoạt động trong thời gian dài bằng cách thực hiện các bước sau:

Theo mặc định, Đại lý phân phối xóa tất cả các thay đổi đã cam kết đối với cơ sở dữ liệu Người đăng ký, giữ lại bản ghi cuối cùng để theo dõi các thay đổi mới dựa trên Số thứ tự nhật ký (LSN).

Chúng tôi có thể thực hiện các truy vấn dưới đây để kiểm tra trạng thái của các bản ghi có sẵn trong MSRepl_Commands bảng hoặc sử dụng sp_browsereplcmds thủ tục trong cơ sở dữ liệu phân phối:

exec sp_browsereplcmds
GO
SELECT * FROM MSrepl_commands

Bây giờ, hãy mở một cửa sổ truy vấn mới và thực thi tập lệnh bên dưới để tạo một giao dịch hoạt động lâu dài trên AdventureWorks cơ sở dữ liệu. Lưu ý rằng tập lệnh dưới đây không bao gồm bất kỳ lệnh ROLLBACK hoặc COMMIT TRANSACTION nào. Do đó, chúng tôi khuyên bạn không nên chạy những loại lệnh này trên cơ sở dữ liệu Sản xuất.

Các giá trị
BEGIN TRANSACTION 

SET IDENTITY_INSERT Person.ContactType ON;
insert into person.ContactType (ContactTypeId, Name, ModifiedDate) values ( 22, 'Test New Position', GETDATE());
SET IDENTITY_INSERT Person.ContactType OFF;

Chúng tôi có thể xác minh rằng bản ghi mới này chưa được sao chép vào cơ sở dữ liệu Người đăng ký. Vì vậy, chúng tôi sẽ thực hiện câu lệnh SELECT trên Person.ContactType trong cơ sở dữ liệu Người đăng ký:

Hãy xác minh xem lệnh INSERT ở trên có được đọc bởi Log Reader Agent và được ghi vào cơ sở dữ liệu Phân phối hay không.

Thực thi lại các tập lệnh từ phần của Bước 1. Kết quả vẫn hiển thị trạng thái cũ, xác nhận rằng bản ghi không được đọc từ Nhật ký giao dịch của cơ sở dữ liệu Nhà xuất bản.

Bây giờ, hãy mở Truy vấn mới và thực thi tập lệnh UPDATE bên dưới để xem liệu Tác nhân đọc nhật ký có thể bỏ qua giao dịch đang hoạt động lâu dài hay không và đọc các thay đổi được thực hiện bởi câu lệnh UPDATE này.

UPDATE AdventureWorks.dbo.AWBuildVersion
SET ModifiedDate  = GETDATE()

Kiểm tra cơ sở dữ liệu Phân phối xem Tác nhân đọc nhật ký có thể nắm bắt được sự thay đổi này hay không. Chạy tập lệnh như một phần của Bước 1:

Vì tuyên bố UPDATE ở trên đã được cam kết trong cơ sở dữ liệu Publisher, Log Reader Agent có thể quét thay đổi này và chèn nó vào cơ sở dữ liệu Phân phối. Sau đó, nó áp dụng thay đổi này cho cơ sở dữ liệu Người đăng ký như được hiển thị bên dưới:

CHÈN vào Person.ContactType sẽ được sao chép vào cơ sở dữ liệu Người đăng ký chỉ sau khi giao dịch INSERT được cam kết trong cơ sở dữ liệu Nhà xuất bản. Trước khi cam kết, chúng tôi có thể nhanh chóng kiểm tra cách xác định một giao dịch Hoạt động lâu dài, hiểu nó và xử lý nó một cách hiệu quả.

Xác định một giao dịch đang hoạt động lâu dài

Để kiểm tra bất kỳ Giao dịch đang hoạt động lâu dài nào trên bất kỳ cơ sở dữ liệu nào, hãy mở Cửa sổ truy vấn mới và kết nối với cơ sở dữ liệu tương ứng mà chúng tôi cần kiểm tra. Thực thi DBCC OPENTRAN lệnh console - nó là Lệnh của Bảng điều khiển Cơ sở dữ liệu để xem các giao dịch đang mở trong cơ sở dữ liệu tại thời điểm thực thi.

USE AdventureWorks
GO
DBCC OPENTRAN

Bây giờ chúng tôi biết rằng đã có SPID ( ID quy trình máy chủ ) 69 chạy lâu. Hãy xác minh lệnh nào đã được thực thi trên giao dịch đó bằng cách sử dụng DBCC INPUTBUFFER lệnh giao diện điều khiển (Lệnh Bảng điều khiển Cơ sở dữ liệu được sử dụng để xác định lệnh hoặc hoạt động đang xảy ra trên ID quy trình máy chủ đã chọn).

Để dễ đọc, tôi đang sao chép EventInfo giá trị trường và định dạng nó để hiển thị lệnh chúng ta đã thực hiện trước đó.

Nếu không có bất kỳ giao dịch Hoạt động lâu dài nào trên cơ sở dữ liệu đã chọn, chúng tôi sẽ nhận được thông báo dưới đây:

Tương tự với DBCC OPENTRAN lệnh bảng điều khiển, chúng ta có thể CHỌN từ DMV có tên sys.dm_tran_database_transactions để có được kết quả chi tiết hơn (tham khảo bài viết MSDN để biết thêm dữ liệu).

Bây giờ, chúng ta biết cách xác định giao dịch Dài hạn. Chúng tôi có thể thực hiện giao dịch và xem cách sao chép câu lệnh INSERT.

Đi tới cửa sổ nơi chúng tôi đã chèn bản ghi vào Person.ContactType trong Phạm vi giao dịch và thực hiện GIAO DỊCH CAM KẾT như được hiển thị bên dưới:

Việc thực hiện GIAO DỊCH CAM KẾT đã đưa bản ghi vào cơ sở dữ liệu của Nhà xuất bản. Do đó, nó sẽ hiển thị trong cơ sở dữ liệu Phân phối và cơ sở dữ liệu Người đăng ký:

Nếu bạn nhận thấy, các bản ghi cũ hơn từ cơ sở dữ liệu Phân phối đã được dọn dẹp bởi công việc Dọn dẹp Đại lý Phân phối. Bản ghi mới cho INSERT trên Person.ContactType bảng đã hiển thị trong MSRepl_cmds bảng.

Từ thử nghiệm của mình, chúng tôi đã học được những điều sau:

  • Công việc Tác nhân đọc nhật ký của SQL Server Transactional Replication sẽ chỉ quét các bản ghi đã cam kết từ cơ sở dữ liệu Nhật ký giao dịch của nhà xuất bản và CHÈN vào cơ sở dữ liệu người đăng ký.
  • Thứ tự dữ liệu đã thay đổi trên cơ sở dữ liệu Nhà xuất bản được gửi đến Người đăng ký sẽ dựa trên trạng thái Đã cam kết và thời gian trên cơ sở dữ liệu Nhà xuất bản mặc dù dữ liệu được sao chép sẽ có cùng thời gian với cơ sở dữ liệu Nhà xuất bản.
  • Việc xác định các Giao dịch đang hoạt động trong thời gian dài có thể giúp giải quyết sự phát triển của Tệp nhật ký giao dịch của Nhà xuất bản hoặc Nhà phân phối hoặc Người đăng ký hoặc bất kỳ cơ sở dữ liệu nào.

Thao tác CHÈN / CẬP NHẬT / XÓA SQL hàng loạt trên các bài báo

Với dữ liệu khổng lồ nằm trong cơ sở dữ liệu của Publisher, chúng tôi thường gặp phải các yêu cầu CHÈN hoặc CẬP NHẬT hoặc XÓA các bản ghi khổng lồ cho các bảng được sao chép.

Nếu các hoạt động CHÈN, hoặc CẬP NHẬT hoặc XÓA được thực hiện trong một Giao dịch duy nhất, nó chắc chắn sẽ dẫn đến việc Nhân bản bị kẹt trong một thời gian dài.

Giả sử chúng ta cần CHÈN 10 Triệu bản ghi vào một bảng sao chép. Việc chèn các bản ghi đó trong một lần chụp sẽ gây ra các vấn đề về Hiệu suất.

INSERT INTO REplicated_table
SELECT * FROM Source_table

Thay vào đó, chúng tôi có thể CHÈN bản ghi theo lô 0,1 hoặc 0,5 Triệu bản ghi trong WHILE vòng lặp hoặc vòng lặp CURSOR , và nó sẽ đảm bảo sao chép nhanh hơn. Chúng tôi có thể không nhận được các vấn đề lớn đối với các câu lệnh INSERT trừ khi bảng liên quan có rất nhiều chỉ mục. Tuy nhiên, điều này sẽ ảnh hưởng rất lớn đến hiệu suất đối với các câu lệnh UPDATE hoặc DELETE.

Giả sử chúng ta đã thêm một cột mới vào bảng Nhân rộng có khoảng 10 Triệu bản ghi. Chúng tôi muốn cập nhật cột mới này với giá trị mặc định.

Lý tưởng nhất là lệnh dưới đây sẽ hoạt động tốt để CẬP NHẬT tất cả 10 Triệu bản ghi với giá trị mặc định là Abc :

-- UPDATE 10 Million records on Replicated Table with some DEFAULT values
UPDATE Replicated_table
SET new_column = 'Abc'

Tuy nhiên, để tránh ảnh hưởng đến Nhân bản, chúng ta nên thực hiện thao tác CẬP NHẬT ở trên theo lô 0,1 hoặc 0,5 Triệu bản ghi để tránh các vấn đề về hiệu suất.

-- UPDATE in batches to avoid performance impacts on Replication
WHILE 1 = 1
BEGIN
	UPDATE TOP(100000) Replicated_Table
	SET new_Column = 'Abc'
	WHERE new_column is NULL

	IF @@ROWCOUNT = 0
	BREAK
END

Tương tự, nếu chúng ta cần XÓA khoảng 10 triệu bản ghi khỏi một bảng được sao chép, chúng ta có thể thực hiện theo lô:

-- DELETE 10 Million records on Replicated Table with some DEFAULT values
DELETE FROM Replicated_table

-- UPDATE in batches to avoid performance impacts on Replication
WHILE 1 = 1
BEGIN
	DELETE TOP(100000) Replicated_Table

	IF @@ROWCOUNT = 0
	BREAK
END

Xử lý BULK INSERT hoặc UPDATE hoặc DELETE một cách hiệu quả có thể giúp giải quyết các vấn đề về Sao chép.

Mẹo chuyên nghiệp :Để CHÈN dữ liệu khổng lồ vào bảng Sao chép trong cơ sở dữ liệu của Nhà xuất bản, hãy sử dụng trình hướng dẫn NHẬP / XUẤT trong SSMS, vì nó sẽ chèn các bản ghi theo lô 10000 hoặc dựa trên kích thước bản ghi được SQL Server tính toán nhanh hơn.

Thay đổi dữ liệu lớn trong một giao dịch

Để duy trì tính toàn vẹn của dữ liệu từ quan điểm ứng dụng hoặc phát triển, nhiều ứng dụng có các giao dịch rõ ràng được xác định cho các hoạt động quan trọng. Tuy nhiên, nếu nhiều thao tác (CHÈN, CẬP NHẬT hoặc XÓA) thực hiện trong một phạm vi Giao dịch, thì trước tiên, Tác nhân đọc nhật ký sẽ đợi giao dịch hoàn tất, như chúng ta đã thấy trước đó.

Khi giao dịch được ứng dụng cam kết, Tác nhân đọc nhật ký cần quét những thay đổi dữ liệu khổng lồ đó được thực hiện trên nhật ký giao dịch cơ sở dữ liệu của Nhà xuất bản. Trong quá trình quét đó, chúng tôi có thể thấy các cảnh báo hoặc thông báo thông tin trong Tác nhân đọc nhật ký như

Tác nhân đọc nhật ký đang quét nhật ký giao dịch để tìm các lệnh được sao chép. Khoảng bản ghi nhật ký xxxxxx đã được quét trong đường chuyền # xxxx trong số đó đã được đánh dấu để sao chép, thời gian đã trôi qua xxxxxxxxx (mili giây)

Trước khi xác định giải pháp cho trường hợp này, chúng ta cần hiểu cách Tác nhân đọc nhật ký quét các bản ghi từ Nhật ký giao dịch và chèn các bản ghi vào cơ sở dữ liệu phân phối MSrepl_transactions MSrepl_cmds bảng.

SQL Server nội bộ có Số thứ tự nhật ký (LSN) bên trong nhật ký giao dịch. Tác nhân đọc nhật ký sử dụng các giá trị LSN để quét các thay đổi được đánh dấu cho SQL Server Replication theo thứ tự.

Tác nhân đọc nhật ký thực thi sp_replcmds quy trình được lưu trữ mở rộng để tìm nạp các lệnh được đánh dấu sao chép từ cơ sở dữ liệu Nhật ký giao dịch của nhà xuất bản.

Sp_replcmds chấp nhận một tham số đầu vào có tên @maxtrans để tìm nạp số lượng giao dịch tối đa. Giá trị mặc định sẽ là 1 có nghĩa là nó sẽ quét bất kỳ số lượng giao dịch nào có sẵn từ các bản ghi để được gửi đến cơ sở dữ liệu phân phối. Nếu có 10 hoạt động CHÈN được thực hiện thông qua một Giao dịch duy nhất và được cam kết trong cơ sở dữ liệu của Nhà xuất bản, thì một lô duy nhất có thể chứa 1 Giao dịch với 10 lệnh.

Nếu nhiều giao dịch với các lệnh ít hơn được xác định, Tác nhân đọc nhật ký sẽ kết hợp nhiều giao dịch hoặc XACT số thứ tự đến một Lô sao chép duy nhất. Nhưng nó lưu trữ dưới dạng một XACT khác Trình tự số trong MSRepl_transactions bàn. Các lệnh riêng lẻ thuộc giao dịch đó sẽ được ghi lại trong MSRepl_commands bảng.

Để xác minh những điều chúng ta đã thảo luận ở trên, tôi đang cập nhật Ngày được sửa đổi cột dbo.AWBuildVersion bảng đến ngày hôm nay và xem điều gì sẽ xảy ra:

UPDATE AdventureWorks.dbo.AWBuildVersion
SET ModifiedDate  = GETDATE()

Trước khi thực hiện CẬP NHẬT, chúng tôi xác minh các bản ghi có trong MSrepl_commands MSrepl_transactions bảng:

Bây giờ, hãy thực thi tập lệnh UPDATE ở trên và xác minh các bản ghi có trong 2 bảng đó:

Một bản ghi mới với thời gian UPDATE đã được chèn vào MSrepl_transactions bảng có entry_time gần đó . Kiểm tra lệnh trên xact_seqno này sẽ hiển thị danh sách các lệnh được nhóm hợp lý bằng cách sử dụng sp_browsereplcmds thủ tục.

Trong Trình theo dõi nhân bản, chúng ta có thể thấy một câu lệnh CẬP NHẬT duy nhất được ghi lại trong 1 (các) Giao dịch với 1 (các) lệnh từ Nhà xuất bản đến Nhà phân phối.

Và chúng ta có thể thấy cùng một lệnh được gửi từ Nhà phân phối đến Người đăng ký trong một phần nhỏ của sự khác biệt của giây. Nó chỉ ra rằng Tái tạo đang diễn ra đúng cách.

Bây giờ, nếu có một số lượng lớn giao dịch được kết hợp trong một xact_seqno , chúng ta có thể thấy các thông báo như 10 (các) giao dịch với 5000 lệnh đã được gửi .

Hãy kiểm tra điều này bằng cách thực hiện UPDATE trên 2 bảng khác nhau cùng một lúc:

Chúng tôi có thể thấy hai bản ghi giao dịch trong MSrepl_transactions bảng phù hợp với hai hoạt động UPDATE và sau đó là số không. trong số các bản ghi trong bảng đó khớp với số không. hồ sơ được cập nhật.

Kết quả từ MSrepl_transactions bảng:

Kết quả từ MSrepl_commands bảng:

Tuy nhiên, chúng tôi nhận thấy rằng 2 giao dịch này được nhóm một cách hợp lý bởi Tác nhân đọc nhật ký và được kết hợp thành một lô duy nhất là 2 giao dịch với 109225 lệnh.

Nhưng trước đó, chúng ta có thể thấy các thông báo như Đang phân phối các giao dịch được lặp lại, số lượng xact:1, số lệnh 46601 .

Điều này sẽ xảy ra cho đến khi Tác nhân đọc nhật ký quét toàn bộ các thay đổi và xác định rằng 2 giao dịch CẬP NHẬT đã được đọc đầy đủ từ Nhật ký giao dịch.

Khi các lệnh được đọc đầy đủ từ Nhật ký giao dịch, chúng tôi thấy rằng 2 giao dịch với 109225 lệnh đã được phân phối bởi tác nhân Trình đọc nhật ký:

Vì Đại lý phân phối đang đợi một giao dịch lớn được nhân rộng, chúng tôi có thể thấy thông báo như Đang phân phối các giao dịch được lặp lại cho thấy rằng có một giao dịch lớn đang được sao chép và chúng ta cần đợi nó được nhân rộng hoàn toàn.

Sau khi sao chép, chúng ta cũng có thể thấy thông báo dưới đây trong Đại lý phân phối:

Một số cách hữu ích để giải quyết những vấn đề này.

Cách 1:TẠO Quy trình Lưu trữ SQL Mới

Bạn cần tạo một thủ tục mới được lưu trữ và đóng gói logic ứng dụng vào nó trong phạm vi Giao dịch.

Sau khi nó được tạo, hãy thêm bài viết Thủ tục đã lưu trữ đó vào Sao chép và thay đổi thuộc tính bài viết Replicate thành Thực thi thủ tục đã lưu trữ tùy chọn.

Nó sẽ giúp thực hiện bài viết Thủ tục được lưu trữ trên Người đăng ký thay vì sao chép tất cả các thay đổi dữ liệu riêng lẻ đã xảy ra.

Hãy xem lại cách Thực hiện thủ tục được lưu trữ tùy chọn Replicate giảm tải cho Replication. Để làm điều đó, chúng ta có thể tạo một Quy trình được lưu trữ thử nghiệm như được hiển thị bên dưới:

CREATE procedure test_proc
AS
BEGIN
UPDATE AdventureWorks.dbo.AWBuildVersion
SET ModifiedDate  = GETDATE()

UPDATE TOP(10) Production.TransactionHistoryArchive
SET ModifiedDate  = GETDATE()

UPDATE TOP(10) Person.Person
SET ModifiedDate  = GETDATE()
END

Quy trình trên sẽ CẬP NHẬT một bản ghi duy nhất trên AWBuildVersion mỗi bảng và 10 bản ghi trên Production.TransactionHistoryArchive Person.Person bảng tổng cộng lên đến 21 thay đổi bản ghi.

Sau khi tạo quy trình mới này trên cả Nhà xuất bản và Người đăng ký, hãy thêm nó vào Nhân bản. Để làm điều đó, hãy nhấp chuột phải vào Ấn phẩm và chọn bài viết thủ tục để sao chép với Chỉ định nghĩa thủ tục được lưu trữ mặc định tùy chọn.

Sau khi hoàn tất, chúng tôi có thể xác minh các bản ghi có sẵn trong MSrepl_transactions MSrepl_commands bảng.

Bây giờ, hãy thực hiện quy trình trong cơ sở dữ liệu Nhà xuất bản để xem có bao nhiêu bản ghi được theo dõi.

Chúng ta có thể thấy thông tin sau trên bảng Phân phối MSrepl_transactions MSrepl_commands :

Ba xact_seqno đã được tạo cho ba hoạt động UPDATE trong MSrepl_transactions bảng và 21 lệnh đã được chèn vào MSrepl_commands bảng.

Mở Trình theo dõi nhân bản và xem liệu chúng được gửi dưới dạng 3 lô Sao chép khác nhau hay một lô duy nhất với 3 giao dịch cùng nhau.

Chúng ta có thể thấy rằng ba xact_seqno đã được hợp nhất thành một lô Nhân bản duy nhất. Do đó, chúng ta có thể thấy rằng 3 giao dịch với 21 lệnh đã được gửi thành công.

Hãy xóa thủ tục khỏi Sao chép và thêm lại bằng Thực hiện thủ tục đã lưu thứ hai lựa chọn. Bây giờ, hãy thực hiện thủ tục và xem cách các bản ghi được sao chép.

Kiểm tra hồ sơ từ các bảng Phân phối cho thấy các chi tiết dưới đây:

Bây giờ, hãy thực hiện quy trình trên cơ sở dữ liệu Publisher và xem có bao nhiêu bản ghi đang được đăng nhập vào các bảng Phân phối. Việc thực hiện một thủ tục đã cập nhật 21 bản ghi (1 bản ghi, 10 bản ghi và 10 bản ghi) so với trước đó.

Xác minh bảng phân phối hiển thị dữ liệu dưới đây:

Hãy xem nhanh sp_browsereplcmds để xem lệnh thực nhận được:

Lệnh là “{call“ dbo ”.” Test_proc ”}” sẽ được thực thi trên cơ sở dữ liệu Người đăng ký.

Trong Replication Monitor, chúng ta có thể thấy rằng chỉ có 1 (các) giao dịch với 1 (các) lệnh được gửi qua Replication:

Trong trường hợp thử nghiệm của chúng tôi, chúng tôi đã sử dụng một quy trình chỉ có 21 thay đổi dữ liệu. Tuy nhiên, nếu chúng tôi thực hiện điều đó đối với một thủ tục phức tạp liên quan đến hàng triệu thay đổi, thì phương pháp tiếp cận Thủ tục được lưu trữ với Thực hiện thủ tục được lưu trữ tùy chọn sẽ hiệu quả trong việc giảm tải Nhân bản.

Chúng tôi cần xác thực cách tiếp cận này bằng cách kiểm tra xem quy trình có logic để chỉ cập nhật cùng một bộ bản ghi trong cơ sở dữ liệu Nhà xuất bản và Người đăng ký hay không. Nếu không, điều này sẽ tạo ra các vấn đề không nhất quán về dữ liệu giữa Nhà xuất bản và Người đăng ký.

Cách 2:Định cấu hình các thông số tác nhân trình đọc nhật ký MaxCmdsInTran, ReadBatchSize và ReadBatchThreshold

MaxCmdsInTran - cho biết số lượng Lệnh tối đa có thể được nhóm một cách hợp lý trong một Giao dịch trong khi đọc dữ liệu từ cơ sở dữ liệu Nhật ký Giao dịch của Nhà xuất bản và được ghi vào cơ sở dữ liệu Phân phối.

Trong các thử nghiệm trước đó của chúng tôi, chúng tôi nhận thấy rằng khoảng 109225 lệnh đã được tích lũy trong một chuỗi chính xác Replication duy nhất, dẫn đến độ trễ hoặc độ trễ nhẹ. Nếu chúng tôi đặt MaxCmdsInTran tham số đến 10000, chuỗi xact đơn số sẽ được chia thành 11 trình tự xact dẫn đến phân phối lệnh nhanh hơn từ Nhà xuất bản đến Nhà phân phối . Mặc dù tùy chọn này giúp giảm bớt sự tranh chấp của cơ sở dữ liệu Phân phối và sao chép dữ liệu nhanh hơn từ Nhà xuất bản sang cơ sở dữ liệu Người đăng ký, hãy cẩn thận khi sử dụng tùy chọn này. Nó có thể kết thúc việc phân phối dữ liệu đến cơ sở dữ liệu Người đăng ký và truy cập nó từ các bảng cơ sở dữ liệu Người đăng ký trước khi kết thúc phạm vi giao dịch ban đầu.

ReadBatchSize - Tham số này có thể không hữu ích cho một tình huống giao dịch lớn. Tuy nhiên, nó sẽ hữu ích khi có rất nhiều và rất nhiều giao dịch nhỏ hơn xảy ra trên cơ sở dữ liệu của Nhà xuất bản.

Nếu số lượng lệnh cho mỗi giao dịch ít hơn, Tác nhân đọc nhật ký sẽ kết hợp nhiều thay đổi cho một phạm vi giao dịch lệnh Sao chép duy nhất. Kích thước Hàng loạt Đọc cho biết số lượng Giao dịch có thể được đọc trong Nhật ký Giao dịch trước khi gửi các thay đổi đến cơ sở dữ liệu Phân phối. Các giá trị có thể từ 500 đến 10000.

ReadBatchThreshold - cho biết số lượng lệnh được đọc từ nhật ký giao dịch của cơ sở dữ liệu Nhà xuất bản trước khi được gửi đến Người đăng ký với giá trị mặc định là 0 để quét toàn bộ tệp nhật ký. Tuy nhiên, chúng tôi có thể giảm giá trị này để gửi dữ liệu nhanh hơn bằng cách giới hạn nó ở 10000 hoặc 100000 lệnh như vậy.

Cách 3:Định cấu hình Giá trị Tốt nhất cho Tham số Dòng Đăng ký

Dòng đăng ký - cho biết số lượng kết nối mà một đại lý phân phối có thể thực hiện song song để lấy dữ liệu từ cơ sở dữ liệu phân phối và truyền dữ liệu đó đến cơ sở dữ liệu người đăng ký. Giá trị mặc định là 1 chỉ đề xuất một luồng hoặc kết nối từ bản phân phối đến cơ sở dữ liệu người đăng ký. Các giá trị có thể nằm trong khoảng từ 1 đến 64. Nếu nhiều luồng Đăng ký được thêm vào, nó có thể dẫn đến tắc nghẽn CXPACKET (nói cách khác là song song). Do đó, bạn nên cẩn thận khi định cấu hình tùy chọn này trong Sản xuất.

Tóm lại, hãy thử tránh CHÈN, CẬP NHẬT hoặc XÓA rất lớn trong một giao dịch duy nhất. Nếu không thể loại bỏ các thao tác này, lựa chọn tốt nhất là thử nghiệm các cách trên và chọn cách phù hợp nhất với các điều kiện cụ thể của bạn.

Chặn trong Cơ sở dữ liệu phân phối

Cơ sở dữ liệu phân phối là trung tâm của SQL Server Transactional Replication và nếu nó không được duy trì đúng cách, sẽ có rất nhiều vấn đề về hiệu suất.

Để tóm tắt tất cả các phương pháp được đề xuất cho cấu hình cơ sở dữ liệu phân phối, chúng tôi cần đảm bảo các cấu hình dưới đây được thực hiện đúng cách:

  1. Các tệp dữ liệu của cơ sở dữ liệu phân phối phải được đặt trên các ổ đĩa IOPS cao. Nếu cơ sở dữ liệu Publisher sẽ có nhiều thay đổi dữ liệu, chúng tôi cần đảm bảo rằng cơ sở dữ liệu phân phối được đặt trên ổ đĩa có IOPS cao. Nó sẽ liên tục nhận dữ liệu từ tác nhân Trình đọc nhật ký, gửi dữ liệu đến cơ sở dữ liệu Người đăng ký thông qua tác nhân Phân phối. Tất cả dữ liệu được sao chép sẽ bị xóa khỏi cơ sở dữ liệu phân phối 10 phút một lần thông qua công việc dọn dẹp Phân phối.
  2. Định cấu hình các thuộc tính Kích thước tệp ban đầu và Tự động phát triển của cơ sở dữ liệu Phân phối với các giá trị được đề xuất dựa trên mức hoạt động của cơ sở dữ liệu Nhà xuất bản. Nếu không, nó sẽ dẫn đến phân mảnh dữ liệu và tệp nhật ký gây ra các vấn đề về hiệu suất.
  3. Đưa cơ sở dữ liệu phân phối vào các công việc Bảo trì chỉ mục thường xuyên được định cấu hình trên Máy chủ nơi đặt cơ sở dữ liệu phân phối.
  4. Đưa cơ sở dữ liệu phân phối vào lịch trình toàn bộ công việc sao lưu để khắc phục mọi sự cố cụ thể.
  5. Đảm bảo rằng Dọn dẹp phân phối:phân phối công việc đang chạy 10 phút một lần theo lịch trình mặc định. Nếu không, kích thước của cơ sở dữ liệu phân phối sẽ tiếp tục tăng và dẫn đến các vấn đề về hiệu suất.

Như chúng tôi đã nhận thấy cho đến nay, trong cơ sở dữ liệu phân phối, các bảng quan trọng có liên quan là MSrepl_transactions MSrepl_commands . Các bản ghi được chèn vào đó bởi công việc Tác nhân đọc nhật ký, được chọn bởi công việc Đại lý phân phối, áp dụng tại cơ sở dữ liệu Người đăng ký, sau đó xóa hoặc làm sạch bằng công việc Tác nhân làm sạch phân phối.

Nếu cơ sở dữ liệu phân phối không được định cấu hình đúng cách, chúng tôi có thể gặp phải các khóa phiên trên 2 bảng này, điều này sẽ dẫn đến các vấn đề về hiệu suất sao chép SQL Server.

Chúng tôi có thể thực hiện truy vấn dưới đây trên bất kỳ cơ sở dữ liệu nào để xem các phiên chặn có sẵn trong phiên bản SQL Server hiện tại:

SELECT * 
FROM sys.sysprocesses
where blocked > 0
order by waittime desc

Nếu truy vấn trên trả về bất kỳ kết quả nào, chúng tôi có thể xác định các lệnh trên các phiên bị chặn đó bằng cách thực thi DBCC INPUTBUFFER (spid) lệnh console và thực hiện các hành động tương ứng.

Các vấn đề liên quan đến tham nhũng

Cơ sở dữ liệu SQL Server sử dụng thuật toán hoặc logic của nó để lưu trữ dữ liệu vào các bảng và giữ nó trong phạm vi hoặc trang. Lỗi cơ sở dữ liệu là một quá trình mà trạng thái vật lý của các tệp / phạm vi / trang liên quan đến cơ sở dữ liệu thay đổi từ trạng thái bình thường sang trạng thái không ổn định hoặc không thể truy xuất khiến cho việc truy xuất dữ liệu khó hơn hoặc không thể.

Tất cả Cơ sở dữ liệu SQL Server đều có xu hướng bị hỏng cơ sở dữ liệu. Nguyên nhân có thể là:

  • Các lỗi phần cứng như sự cố về Đĩa, Bộ nhớ hoặc Bộ điều khiển;
  • Lỗi hệ điều hành máy chủ như sự cố vá lỗi;
  • Sự cố về nguồn dẫn đến việc Máy chủ bị tắt đột ngột hoặc cơ sở dữ liệu bị tắt không đúng cách.

Nếu chúng tôi có thể khôi phục hoặc sửa chữa cơ sở dữ liệu mà không bị mất dữ liệu, thì SQL Server Replication sẽ không bị ảnh hưởng. Tuy nhiên, nếu có bất kỳ mất mát dữ liệu nào trong khi khôi phục hoặc sửa chữa cơ sở dữ liệu bị hỏng, chúng tôi sẽ bắt đầu nhận được nhiều vấn đề về tính toàn vẹn của Dữ liệu mà chúng tôi đã thảo luận trong bài viết trước của chúng tôi.

Lỗi có thể xảy ra ở các thành phần khác nhau, chẳng hạn như:

  • Dữ liệu nhà xuất bản / tệp nhật ký bị hỏng
  • Dữ liệu người đăng ký / Hồ sơ nhật ký bị hỏng
  • Dữ liệu cơ sở dữ liệu phân phối / tệp nhật ký bị hỏng
  • Dữ liệu Msdb Cơ sở dữ liệu / Tệp nhật ký bị hỏng

Nếu chúng tôi nhận được nhiều vấn đề về tính toàn vẹn dữ liệu sau khi khắc phục các vấn đề về Tham nhũng, chúng tôi nên xóa hoàn toàn Bản sao, khắc phục tất cả các sự cố Tham nhũng trong cơ sở dữ liệu của Nhà xuất bản, Người đăng ký hoặc Nhà phân phối rồi định cấu hình lại Bản sao để khắc phục. Otherwise, data integrity issues will persist and lead to data inconsistency across the Publisher and Subscriber. The time required to fix the Data integrity issues in case of Corrupted databases will be much more compared to configuring Replication from scratch. Hence identify the level of Corruption encountered and take optimal decisions to resolve the Replication issues faster.

Wondering why msdb database corruption can harm Replication? Since msdb database hold all details related to SQL Server Agent Jobs including Replication Agent jobs, any corruption on msdb database will harm Replication. To recover quickly from msdb database corruptions, it is recommended to restore msdb database from the last Full Backup of msdb database. This also signifies the importance of taking Full Backups of all system databases including msdb database.

Kết luận

Thanks for successfully going through the final power-packed article about the Performance issues in the SQL Server Transactional Replication. If you have gone through all articles carefully, you should be able to troubleshoot almost any Transactional Replication-based issues and fix them out efficiently.

If you need any further guidance or have any Transactional Replication-related issues in your environment, you can reach out to me for consultation. And if I missed anything essential in this article, you are welcome to point to that in the Comments section.


  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Khắc phục “tên hồ sơ không hợp lệ” khi gửi thư từ máy chủ SQL

  2. Cách sử dụng Sắp xếp (Thứ tự Theo) trong Câu lệnh Chọn trong SQL Server - Hướng dẫn SQL Server / TSQL Phần 109

  3. Cách chỉ định tên khóa chính trong EF-Code-First

  4. Các truy vấn ANSI JOIN và không phải ANSI JOIN có thực hiện khác nhau không?

  5. Hợp nhất các giá trị hàng thành CSV (còn gọi là GROUP_CONCAT cho SQL Server)