Можно ли разделить транзакцию между приложением .Net и объектом COM+?

StackOverflow https://stackoverflow.com/questions/21589

Вопрос

Некоторое время назад я провел несколько тестов и так и не понял, как заставить это работать.

Ингредиенты:

  • Транзакционный объект COM+ (разработан в VB6)
  • Веб-приложение .Net (с транзакцией) в IIS, которое...
    выполняет вызов компонента COM+
    обновляет строку в базе данных SQL

Тестирование:

Запустите приложение .Net и создайте исключение.

Результат:

Обновление, сделанное из приложения .Net, откатывается.
Обновление, выполненное объектом COM+, не откатывается.

Если я вызываю объект COM+ со старой страницы ASP, откат работает.

Я знаю, что некоторые люди могут подумать: «Что?!COM+ и .Net, вы, должно быть, с ума сошли!», но есть места в этом мире, где все еще существует много компонентов COM+.Мне просто было любопытно, сталкивался ли кто-нибудь с этим и поняли ли вы, как заставить это работать.

Это было полезно?

Решение

Поскольку VB и .NET будут использовать разные соединения SQL (и невозможно заставить ADO и ADO.NET использовать одно и то же соединение), ваша единственная возможность — подключить DTC (координатор распределенных транзакций).DTC будет координировать две независимые транзакции, чтобы они одновременно фиксировались или откатывались.

Из .NET, EnterpriseServices управляет функциями COM+, такими как DTC.В .NET 2.0 и более поздних версиях вы можете использовать пространство имен System.Transactions, что делает работу немного удобнее.Я думаю, что-то вроде этого должно работать (непроверенный код):

void SomeMethod()
{
    EnterpriseServicesInteropOption e = EnterpriseServicesInteropOption.Full;
    using (TransactionScope s = new TransactionScope(e))
    {
        MyComPlusClass o = new MyComPlusClass();

        o.SomeTransactionalMethod();
    }
}

Я недостаточно знаком с этим, чтобы дать вам больше советов на данный момент.

На стороне COM+, ваш объект необходимо настроить для использования (скорее всего, «требования») распределенной транзакции.Вы можете сделать это из COM+ Explorer, перейдя в папку вашего объекта. Характеристики, выбрав Сделка вкладку и нажмите «Необходимый".Я не помню, можно ли это сделать и из кода;VB6 был создан до выпуска COM+, поэтому он не полностью поддерживает все, что делает COM+ (его поддержка транзакций предназначалась для предшественника COM+, называемого MS Transaction Server).

Если все работает правильно, ваш объект COM+ должен быть включен в существующий контекст, созданный вашим кодом .NET.

Вы можете использовать узел «Координатор распределенных транзакций\Список транзакций» в «Службах компонентов», чтобы проверить и просмотреть распределенную транзакцию, создаваемую во время вызова.

Имейте в виду, что вы не сможете увидеть изменения компонента COM+, отраженные в запросах данных со стороны .NET, пока транзакция не будет зафиксирована!На самом деле возможен тупик!Помните, что DTC позаботится о том, чтобы две транзакции были парными, но они по-прежнему являются отдельными транзакциями базы данных.

Другие советы

Как вы это реализуете?Если вы используете EnterpriseServices для управления транзакцией .NET, то обе транзакции должны быть отменены, поскольку вы используете для них один и тот же контекст.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top