Исключение WCF при чтении из очереди msmq

У меня есть следующая проблема:

У меня есть проект silveright 5 и проект wcf (iis/ hosted) (.net 4).

Проект wcf содержит несколько служб с привязкой basicHttpBinding и одну службу с привязкой netMsmqBinding.

Существует один сценарий использования этого приложения, в котором пользователь может генерировать несколько экспортов в формате Excel до 30 файлов на пользователя и до 10 пользователей. Это длительная операция, до 3 минут на файл.

Сначала служба экспорта была httpBinded, и с запросом на создание более 15 отчетов она не сработала. Так что я увеличил время ожидания. Это явно не было правильным решением проблемы.

Поэтому я решил использовать очередь и изменил привязку для служб экспорта с basicHttpBinding на netMsmqBinding.

Рабочий процесс следующий:

Клиент Silverlight отправляет запрос для каждого файла следующему методу в ReportsService:

[SecurityTokenValidation]
    [ErrorLogging]
    public string GenerateTablesReport(List<MeasurementDescription> measurements)
    {
        if (measurements == null || measurements.Count.Equals(0))
        {
            throw new FaultException("Invalid argument.", new FaultCode(ErrorCodes.InvalidArgumentException));
        }

        //put on queue from here

        ExportsServiceClient exportsServiceClient = new ExportsServiceClient();

        exportsServiceClient.GenerateTablesReport(measurements.ToArray());

        return new Guid().ToString();
    }

В указанном выше способе я отправляю сообщение, помещая его в очередь. Я создал частную транзакционную очередь с именем ExportsService с необходимыми правами безопасности.

Пока это работает. Я вижу сообщения в очереди.

Проблема в том, что ExportsService не удается при попытке прочитать сообщения, и все они оказываются в папке "retry".

Я перепробовал все за последние два дня. Я попытался с некоторыми простыми игрушечными проектами просто проверить, работает ли на компьютере что-то вроде msmq.

В svclog я нашел это исключение. в System.ServiceModel.Channels.MsmqBindingMonitor.OnTimer(состояние объекта)System.Messaging.MessageQueueException (0x80004005): удаленный компьютер недоступен. в System.Messaging.MessageQueue.GetPrivateQueuesByMachine(String machineName)

ExportsService выглядит так:

public class ExportsService : IExportsService
{
    [OperationBehavior(TransactionScopeRequired = true, TransactionAutoComplete = true)]
    [SecurityTokenValidation]
    [ErrorLogging]
    public void GenerateTablesReport(List<MeasurementDescription> measurements)
    {
        using (TransactionScope scope = new TransactionScope(TransactionScopeOption.Required))
        {
            if (measurements == null || measurements.Count.Equals(0))
            {
                throw new FaultException("Invalid argument.", new FaultCode(ErrorCodes.InvalidArgumentException));
            }

            BusinessFactory.ReportsManager.GenerateTablesReport(measurements);

            scope.Complete();
        }
    }
}

Интересные биты в веб-конфигурации выглядят так:

<client>
  <endpoint address="net.msmq://localhost/private/ExportsService"
    binding="netMsmqBinding" bindingConfiguration="NetMsmqBinding_IExportsService"
    contract="WCF.ExportsService.IExportsService" name="NetMsmqBinding_IExportsService" />
</client>

<behaviors>
  <endpointBehaviors>

    <behavior name="BatchingBehavior">
      <transactedBatching maxBatchSize="16"/>
    </behavior>

  </endpointBehaviors>

  <serviceBehaviors>
    <behavior name="foobar">
      <serviceMetadata httpGetEnabled="true" />
      <serviceDebug includeExceptionDetailInFaults="true" />
      <dataContractSerializer maxItemsInObjectGraph="2147483647" />
      <serviceThrottling maxConcurrentCalls="60"  maxConcurrentInstances="60"   maxConcurrentSessions="60" />
    </behavior>

    <behavior name="ThrottlingBehavior">
      <serviceMetadata httpGetEnabled="true"/>
      <serviceThrottling maxConcurrentCalls="4"/>
    </behavior>
  </serviceBehaviors>
</behaviors>
<serviceHostingEnvironment multipleSiteBindingsEnabled="true" />
<bindings>

  <basicHttpBinding>
    <binding name="defaultBasicHttpBinding" closeTimeout="00:10:00"
      openTimeout="00:10:00" sendTimeout="00:10:00" maxBufferSize="2147483647"
      maxReceivedMessageSize="2147483647">
      <readerQuotas maxDepth="2147483647" maxStringContentLength="2147483647"
        maxArrayLength="2147483647" maxBytesPerRead="2147483647" />
    </binding>
  </basicHttpBinding>
  <netMsmqBinding>
    <binding name="defaultNetMsmqBinding">
      <security mode="None" />
    </binding>
    <binding name="NetMsmqBinding_IExportsService">
      <security mode="None" />
    </binding>
  </netMsmqBinding>

</bindings>

<services>

  <service behaviorConfiguration="ThrottlingBehavior" name="FLM.Web.Services.ExportsService">
    <endpoint address="net.msmq://localhost/private/ExportsService" binding="netMsmqBinding" bindingConfiguration="defaultNetMsmqBinding" behaviorConfiguration="BatchingBehavior" contract="FLM.Web.Services.IExportsService"/>
    <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange"/>
  </service>

  <service behaviorConfiguration="foobar" name="FLM.Web.Services.ReportsService">
    <endpoint address="" binding="basicHttpBinding" bindingConfiguration="defaultBasicHttpBinding"  contract="FLM.Web.Services.IReportsService" />
    <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
  </service>
  <service behaviorConfiguration="foobar" name="FLM.Web.Services.SecurityService">
    <endpoint address="" binding="basicHttpBinding" bindingConfiguration="defaultBasicHttpBinding" contract="FLM.Web.Services.ISecurityService" />
    <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
  </service>
  <service behaviorConfiguration="foobar" name="FLM.Web.Services.OrderingService">
    <endpoint address="" binding="basicHttpBinding" bindingConfiguration="defaultBasicHttpBinding"  contract="FLM.Web.Services.IOrderingService" />
    <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
  </service>
  <service behaviorConfiguration="foobar" name="FLM.Web.Services.ReportConfigurationService">
    <endpoint address="" binding="basicHttpBinding" bindingConfiguration="defaultBasicHttpBinding"  contract="FLM.Web.Services.IReportConfigurationService" />
    <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
  </service>
  <service behaviorConfiguration="foobar" name="FLM.Web.Services.AdminService">
    <endpoint address="" binding="basicHttpBinding" bindingConfiguration="defaultBasicHttpBinding"  contract="FLM.Web.Services.IAdminService" />
    <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
  </service>

</services>

0 ответов

Другие вопросы по тегам