Neste artigo, vou focar especificamente no processo de migração do outbox MySQL.
Requisitos
- .NET 8 ou superior
- Um projeto .NET com estes pacotes NuGet
- Paramore.Brighter.Outbox.Hosting - Fornece a infraestrutura fundamental para implementar o padrão outbox em aplicações Brighter
- Paramore.Brighter.Outbox.MySql - Implementa o armazenamento do outbox especificamente para bancos de dados MySQL
- Paramore.Brighter.MessagingGateway.Kafka - Fornece recursos de mensageria com Kafka
- Paramore.Brighter.ServiceActivator.Extensions.DependencyInjection - Integra o Brighter com o framework de Injeção de Dependência da Microsoft
- Paramore.Brighter.ServiceActivator.Extensions.Hosting - Habilita a integração com a infraestrutura de Host Genérico da Microsoft
- Serilog.AspNetCore - Fornece recursos de logging estruturado para aplicações ASP.NET Core
Recapitulação do Brighter
Antes de continuar falando sobre a configuração do outbox MySQL, vamos recapitular o que já sabemos sobre o Brighter.
Requisição (Comando/Evento)
Defina mensagens usando IRequest
:
public class OrderPlaced() : Event(Id.Random())
{
public string OrderId { get; set; } = string.Empty;
public decimal Value { get; set; }
}
-
Comandos: Operações para um único destinatário (ex:
SendEmail
). -
Eventos: Notificações de broadcast (ex:
OrderShipped
).
Mapeador de Mensagens (Opcional)
Traduz entre mensagens do Brighter e objetos da sua aplicação. Por padrão, o Brighter usará um serializador JSON.
public class OrderPlacedMapper : IAmAMessageMapper<OrderPlaced>, IAmAMessageMapperAsync<OrderPlaced>
{ ... }
Manipulador de Requisições
Processa mensagens recebidas:
public class OrderPlaceHandler(ILogger<OrderPlaceHandler> logger) : RequestHandler<OrderPlaced>
{
public override Greeting Handle(Greeting command)
{
logger.LogInformation("{OrderId} placed with value {OrderValue}", command.OrderId, command.Value);
return base.Handle(command);
}
}
Usando o Outbox no Brighter
Antes de configurar o outbox, entenda como interagir com ele:
Publicando Mensagens através do Outbox
O Brighter fornece o método DepositPostAsync
para armazenar mensagens no outbox
await commandProcessor.DepositPostAsync(
new OrderPlaced { OrderId = "ORD-123", Value = 99.99m },
cancellationToken: cancellationToken);
Isso armazena a mensagem na sua tabela MySQL do outbox para processamento posterior.
Configuração do pacote outbox
1. Garanta que a tabela existe
Primeiro, crie a tabela do outbox no seu banco de dados MySQL. O Brighter não gerenciará esta tabela para você - você é responsável por criá-la e adicionar os índices necessários:
CREATE TABLE outboxmessages (
`MessageId`VARCHAR(255) NOT NULL ,
`Topic` VARCHAR(255) NOT NULL ,
`MessageType` VARCHAR(32) NOT NULL ,
`Timestamp` TIMESTAMP(3) NOT NULL ,
`CorrelationId`VARCHAR(255) NULL ,
`ReplyTo` VARCHAR(255) NULL ,
`ContentType` VARCHAR(128) NULL ,
`PartitionKey` VARCHAR(128) NULL ,
`WorkflowId` VARCHAR(255) NULL ,
`JobId` VARCHAR(255) NULL ,
`Dispatched` TIMESTAMP(3) NULL ,
`HeaderBag` TEXT NOT NULL ,
`Body` TEXT NOT NULL ,
`Source` VARCHAR(255) NULL,
`Type` VARCHAR(255) NULL,
`DataSchema` VARCHAR(255) NULL,
`Subject` VARCHAR(255) NULL,
`TraceParent` VARCHAR(255) NULL,
`TraceState` VARCHAR(255) NULL,
`Baggage` TEXT NULL,
`Created` TIMESTAMP(3) NOT NULL DEFAULT NOW(3),
`CreatedID` INT(11) NOT NULL AUTO_INCREMENT,
UNIQUE(`CreatedID`),
PRIMARY KEY (`MessageId`)
) ENGINE = InnoDB;
2. Configurar o outbox
Configure o outbox na sua configuração de injeção de dependência:
var conn = new RelationalDatabaseConfiguration(connectionString, "brightertests", "outboxmessages");
services
.AddSingleton<IAmARelationalDatabaseConfiguration>(conn)
.AddConsumers(opt => { ... }) // Ou AddBrighter
.AddProducers(opt =>
{
opt.ConnectionProvider = typeof(MySqlUnitOfWork);
opt.TransactionProvider = typeof(MySqlUnitOfWork);
opt.Outbox = new MySqlOutbox(outbox);
...
})
3. Configurar o Sweeper (Varredor)
Configure o varredor do outbox na sua configuração de injeção de dependência:
services
.AddSingleton<IAmARelationalDatabaseConfiguration>(conn)
.AddConsumers(opt => { ... }) // Ou AddBrighter
.UseOutboxSweeper(opt => { opt.BatchSize = 10; })
Observação: Se estiver executando em um ambiente multi-máquina, garanta que apenas uma instância execute o varredor ou configure o bloqueio distribuído no Brighter para evitar entrega duplicada de mensagens.
4. Configurar o Arquivamento do Outbox
Após as mensagens serem enviadas com sucesso, você pode querer arquivá-las:
services
.AddSingleton<IAmARelationalDatabaseConfiguration>(conn)
.AddConsumers(opt => { ... }) // Ou AddBrighter
.UseOutboxArchiver<DbTransaction>(new NullOutboxArchiveProvider(),
opt => opt.MinimumAge = TimeSpan.FromMinutes(1));
Principais Diferenças Entre o Brighter V9 e V10
Outbox como Serviço Singleton
No Brighter V10, o outbox é implementado como um serviço singleton, o que representa uma mudança arquitetônica significativa:
- V9: O outbox era escopo por requisição, permitindo compartilhamento de transação entre o código da aplicação e o outbox
- V10: O outbox é um singleton, o que melhora o desempenho, mas significa que você não pode mais compartilhar transações diretamente
Se a publicação atômica de mensagens em várias mensagens for crítica para sua aplicação, você precisará implementar uma solução personalizada ou considerar abrir uma discussão no repositório GitHub do Brighter.
Mudanças na Configuração do Banco de Dados
No Brighter V10, o outbox é um singleton, então agora não é possível compartilhar transações (talvez exista uma solução alternativa que eu não tenha encontrado), tornando impossível ter uma publicação atômica de mensagens, como se algo falhar não enviar nenhuma mensagem. Se você sentir que isso é uma limitação em sua aplicação, por favor abra uma discussão/issue no GitHub do Brighter.
Mudanças na Configuração do Banco de Dados
Os parâmetros do construtor RelationalDatabaseConfiguration
foram alterados:
// V9
new RelationalDatabaseConfiguration(connectionString, "outboxmessages");
// V10
new RelationalDatabaseConfiguration(connectionString, "database_name", "outboxmessages");
O segundo parâmetro agora especifica o nome do banco de dados em vez do nome da tabela do outbox, o que suporta capacidades aprimoradas de telemetria.
Mudanças no Esquema da Tabela
O esquema da tabela do outbox V10 inclui várias novas colunas em comparação com o V9:
- Colunas TraceParent, TraceState e Baggage para melhor rastreamento distribuído
- Colunas Source, Type, DataSchema e Subject para metadados mais ricos das mensagens
Conclusão
Migrar seu outbox MySQL para o Brighter V10 requer atenção a várias mudanças-chave na arquitetura e configuração. Embora a implementação do outbox singleton melhore o desempenho, ela requer ajustar sua abordagem para o gerenciamento de transações. O esquema aprimorado fornece melhor suporte para rastreamento distribuído e metadados de mensagens mais ricos, alinhando o Brighter mais estreitamente com práticas modernas de observabilidade.
Lembre-se de:
- Atualizar seu esquema da tabela para incluir as novas colunas
- Ajustar sua configuração do banco de dados para especificar tanto o nome do banco de dados quanto o nome da tabela
- Reconsiderar sua estratégia de transação devido à implementação do outbox singleton
- Configurar o varredor e o arquivador com parâmetros apropriados para seu ambiente
Com essas mudanças implementadas, sua aplicação estará pronta para aproveitar o desempenho e recursos aprimorados no Brighter V10, mantendo a entrega confiável de mensagens através do padrão outbox MySQL.
Top comments (0)