简体   繁体   中英

MassTransit State Machine Configuration

How can I configure MassTransit to use quorum queues instead of classic queues when using a state machine saga? In the following code if I uncomment the cfg.ReceiveEndpoint(x => x.SetQuorumQueue()) line, it stil creates classic queues.

Also where do I use UseScheduledRedelivery and UseMessageRetry methods to configure retry and redelivery?

    public static IServiceCollection RegisterMassTransit(
        this IServiceCollection services,
        string sagaStateConnectionString,
        SerilogLoggerFactory factory,
        TransportSettings transportSettings)
    {
        services.AddDbContext<OrderSagaDbContext>(r =>
        {
            r.UseSqlServer(sagaStateConnectionString, m =>
            {
                m.MigrationsAssembly(Assembly.GetExecutingAssembly().GetName().Name);
                m.MigrationsHistoryTable($"__{nameof(OrderSagaDbContext)}");
            });
        });


        services.AddMassTransit(c =>
        {
            c.SetKebabCaseEndpointNameFormatter();

            c.AddSagaStateMachine<OrderStateMachine, OrderState>()
                .EntityFrameworkRepository(r =>
                {
                    r.ExistingDbContext<OrderSagaDbContext>();
                    r.UseSqlServer();
                });

            c.AddBus(context => ConfigureBus(context, transportSettings));

            foreach (var q in transportSettings.Queues)
            {
                c.AddConsumers(TypeNamesToTypes(q.Processors));
                
            }
        });

        return services;
    }

    private static IBusControl ConfigureBus(
        IBusRegistrationContext context,
        TransportSettings transportSettings)
    {
        return Bus.Factory.CreateUsingRabbitMq(cfg =>
        {
            cfg.Host(transportSettings.Host, transportSettings.VirtualHost, hst =>
            {
                hst.Username(transportSettings.UserName);
                hst.Password(transportSettings.Password);
            });
            
            //cfg.ReceiveEndpoint(x => x.SetQuorumQueue());
            cfg.ConfigureEndpoints(context);

        });
    }

To override the receive endpoint configuration of the saga endpoint, you can create a saga definition:

public class OrderStateSagaDefinition :
    SagaDefinition<OrderState>
{
    protected override void ConfigureSaga(IReceiveEndpointConfigurator endpointConfigurator, ISagaConfigurator<OrderState> sagaConfigurator)
    {
        if(endpointConfigurator is IRabbitMqReceiveEndpointConfigurator rmq)
            rmq.SetQuorumQueue();

        endpointConfigurator.UseScheduledRedelivery(...);
        endpointConfigurator.UseMessageRetry(...);
        endpointConfigurator.UseInMemoryOutbox();
    }
}

You can also configure the message retry/redelivery/outbox in the definition as shown.

Then, add that definition to the container configuration:

c.AddSagaStateMachine<OrderStateMachine, OrderState, OrderStateSagaDefinition>()

You'll need to configure a scheduler as well. If you're using RabbitMQ delayed exchange for redelivery, change UseScheduledRedelivery to UseDelayedRedelivery .

With Chris's help above I was able to figure out how to set properties for all queues in an application that uses multiple queues and a state machine saga.

Add an extension method as follows:

public static class RabbitMqReceiveEndpointConfigurationExtensions
{
    public static void Configure(
        this RabbitMqReceiveEndpointConfiguration rmq)
    {
        rmq.PublishFaults = ...;
        rmq.PrefetchCount = ...;
        rmq.SetQuorumQueue();
        rmq.UseScheduledRedelivery(...);
        rmq.UseMessageRetry(...);
    }
}

Then we can call the extension method for each queue when configuring the container as follows:

services.AddMassTransit(c =>
{
    c.SetKebabCaseEndpointNameFormatter();
    c.AddConfigureEndpointsCallback((endpoint, endpointConfigurator) =>
    {
        if (endpointConfigurator is RabbitMqReceiveEndpointConfiguration rmq)
        {
            rmq.Configure();
        }
    });
    ...
});

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM