NServiceBus не может найти Endpoint или MessageEndpointMappings в ненавязчивом режиме

Я пытаюсь подключить примитив TestService конечная точка примитивной службы WCF, куда экземпляр службы WCF отправляет примитив TestCommand к TestService конечная точка, использующая последнюю версию NSB 5.2.9/Host6.0:

[ServiceBehavior(
    InstanceContextMode = InstanceContextMode.PerCall,
    ConcurrencyMode = ConcurrencyMode.Single )]
public class MyService : IMyService
{
    private readonly IBus bus;

    public MyService( IBus bus )
    {
        this.bus = bus;
    }

    public void Test( string value )
    {
        bus.Send( new TestCommand( value ) );
    }
}

Я не могу настроить это правильно. Сообщение об ошибке:

Exception thrown: 'System.InvalidOperationException' in System.ServiceModel.dll

Additional information: No destination could be found for message type Company.App.Commands.TestCommand. Check the <**MessageEndpointMappings**> section of the configuration of this endpoint for an entry either for this specific message type or for its assembly.

Я могу сделать это без использования "ненавязчивого узла", но не с соглашениями. Я очень озадачен тем, как это настроить после того, как все перепробовал. Хост WCF размещается самостоятельно, а конечная точка теста размещается NServiceBus.Host.

  1. web.config приложения IIS WCF Host
  2. через NServiceBus.Config.IConfigurationSource
  3. через NServiceBus.Config.IProvideConfiguration

Прямо сейчас у меня есть это в web.config, который кажется бесполезным и игнорируется:

<MessageEndpointMappings>
    <add Assembly="Company.App.Messages" Type="Company.App.Commands.TestCommand" Endpoint="testservice" />
</MessageEndpointMappings>

"Ненавязчивый режим": я создал отдельный проект для соглашений, на который ссылаются конечная точка хоста WCF и конечная точка TestService.

public class MessageConventions : INeedInitialization
{
    public void Customize( BusConfiguration configuration )
    {
        var conventions = configuration.Conventions();

        conventions.DefiningCommandsAs( t => t.Namespace != null && t.Namespace.StartsWith( "Company.App" ) && t.Namespace.EndsWith( "Commands" ) );
        conventions.DefiningEventsAs( t => t.Namespace != null && t.Namespace.StartsWith( "Company.App" ) && t.Namespace.EndsWith( "Events" ) );
        conventions.DefiningMessagesAs( t => t.Namespace != null && t.Namespace.StartsWith( "Company.App" ) );

        //conventions.DefiningTimeToBeReceivedAs( t => GetTimeToBeReceived( t ) )
        //conventions.DefiningDataBusPropertiesAs( pi => IsDataBusProperty( pi ) );
    }
}

Эти соглашения, похоже, подобраны TestService,

Насколько я понимаю, узел IIS WCF должен объявить сопоставления в своем файле web.config, чтобы служба WCF знала, куда отправлять сообщения с помощью bus.Send(new TestCommand("test")); но это не работает.

Затем я попытался определить эти отображения в обеих конечных точках, но безуспешно.

Этот метод выведет все типы сообщений, которые были найдены с использованием вышеуказанных соглашений:

public class Startup : IWantToRunWhenBusStartsAndStops
{
public MessageMetadataRegistry Messages { get; set; }
public Conventions Conventions { get; set; }

public void Start()
{
    var getAllMessagesMethod = typeof( MessageMetadataRegistry ).GetMethod( "GetAllMessages",
        BindingFlags.NonPublic | BindingFlags.Instance );

    var allMessages = getAllMessagesMethod.Invoke( Messages, new object[ 0 ] ) as IEnumerable<MessageMetadata>;

    foreach ( var metadata in allMessages )
    {
        Type type = metadata.MessageType;
        string name = type.FullName;

        if ( this.Conventions.IsInSystemConventionList( type ) )
            Console.WriteLine( "System Msg: {0}", name );
        else if ( this.Conventions.IsCommandType( type ) )
            Console.WriteLine( "   Command: {0}", name );
        else if ( this.Conventions.IsEventType( type ) )
            Console.WriteLine( "     Event: {0}", name );
        else if ( this.Conventions.IsMessageType( type ) )
            Console.WriteLine( "   Message: {0}", name );

        if ( metadata.TimeToBeReceived != TimeSpan.MaxValue )
            Console.WriteLine( "            TimeToBeReceived={0}", metadata.TimeToBeReceived );
    }
}

public void Stop()
{
}
}

Выше метод выводит тип сообщения "TestCommand", поэтому он знает о принятых соглашениях.

Я уже проверил 1000x на опечатки, корпус, все. Я убрал решение. Мой вопрос: почему NServiceBus не может найти конечную точку?

Пожалуйста помоги.

1 ответ

Ненавязчивость означает, что вы сообщаете NServiceBus, какие классы являются командами и событиями в соответствии с соглашениями, а не реализуете интерфейсы маркеров, вам все равно нужно добавить отображение сообщений в конфигурации app/web, чтобы NServiceBus знал, в какую очередь отправлять сообщение.

Исключение предполагает, что это ваша проблема

Check the <**MessageEndpointMappings**> section of the configuration of this endpoint for an entry either for this specific message type or for its assembly.

Убедитесь, что у вас все еще есть что-то подобное в вашем файле web.config:

<UnicastBusConfig>
  <MessageEndpointMappings>
    <add Messages="Company.App.Commands.TestCommand, Company.App.Commands" Endpoint="test.server" />
  </MessageEndpointMappings>
</UnicastBusConfig>

РЕДАКТИРОВАТЬ

Теперь, когда вы опубликовали свой файл web.config, проблема выглядит так, как будто вы неправильно указали имя типа в файле web.config:

<add Assembly="Company.App.Messages" Type="Company.App.Commands.RunTestCommand"

но ты делаешь это bus.Send(new TestCommand(value));

Так что web.config не так, он должен быть

<add Assembly="Company.App.Messages" Type="Company.App.Commands.TestCommand"
Другие вопросы по тегам