The operation could not be performed because the OLE DB provider 'SQLOLEDB' was unable to begin a distributed transaction...
Published 26 June 2013
While in the process of synchronizing two databases, either directly through SQL Compare/SQL Packager or when running a SQL script produced by them, the following message may appear:
The operation could not be performed because the OLE DB provider 'SQLOLEDB' was unable to begin a distributed transaction.
[OLE/DB provider returned message: New transaction cannot enlist in the specified transaction coordinator. ]
OLE DB error trace [OLE/DB Provider 'SQLOLEDB' ITransactionJoin::JoinTransaction returned 0x8004d00a].
This error message is displayed when a SQL Server programmability object such as a stored procedure or function references a linked server or distributed query connecting to another server. The transaction isolation level selected to run the SQL Compare script is incompatible with distributed queries, and this is the reason for the script failure. SQL Compare uses TRANSACTION ISOLATION LEVEL SERIALIZABLE in order to protect the schema from interference while the update is being performed. We do not intend on changing the isolation level to be compatible with distributed queries for this reason.
One workaround for this issue is to save the migration script to a file using the synchronization wizard of SQL Compare after a database comparison by clicking the 'Save SQL Script' button. Once the script is saved to disk, locate the line reading SET TRANSACTION ISOLATION LEVEL SERIALIZABLE and change this to SET TRANSACTION ISOLATION LEVEL READ COMMITTED. The script can then be run in SQL Server Query Analyzer or Management Studio. Although this could cause problems by allowing competing DDL operations to run at the same time as the SQL Compare script, it will allow distributed query DDL to be submitted.
The second workaround is to go into the project settings, click the options tab, and select 'do not use transactions in synchronization scripts'. This eliminates the issue by not breaking the script up into transactional units, but you will lose the rollback functionality if an error occurs during the running of the script, possibly leaving the database in an 'unknown' synchronization state.