Golang: Chain Of Responsibility

Breno Augusto Ribeiro Campos
Fretebras Tech
Published in
3 min readMay 16, 2022
Ref: https://go.dev/

"O Chain of Responsibility é um padrão de projeto comportamental que permite passar a solicitação ao longo da cadeia de handlers em potencial até que um deles lide com a solicitação." (REFACTORING.GURU)

Você já se deparou com um comportamento similar a este?

Output

Por incrível que pareça códigos com um monte de IFs um atrás do outro são até que comuns, mas conhecer padrões de projeto, pode evitar com que essa estrutura seja criada.

O problema desse código é que ele funciona, mas a que custo? Esse é um exemplo básico e muito pouco real, em sistemas reais, legados ou não, pode acontecer de ter códigos com milhares de linhas. Assim, aos poucos o código vai se tornando muito pouco manutenível, qualquer alteração que for feita, será custosa e crítica, podendo quebrar partes que nem estão envolvidas na alteração.

Sempre quando você se deparar com um cenário onde você possui uma "entidade" e essa entidade passará por um fluxo, tendo sucesso ou não, muito provavelmente o padrão Chain of Responsibility pode deixar seu código mais legível, compreensível e manutenível.

Que tal uma abordagem assim:

Perceba que agora conseguimos ler com clareza, todas as etapas na qual o paciente será submetido, conseguimos ver até mesmo a ordem!

Para fazer isso, foi adicionado o conceito de Handler, o handler como a própria tradução já diz, irá fazer o papel de manipulador, interagindo com a entidade, e tomando a ação necessária, podendo identificar erros e rejeitar a entidade se necessário.

Para isso ser refletido em código, primeiro criamos uma interface para os Handlers:

Essa interface basicamente carrega duas funções, a primeira Execute, é onde você irá descrever todo o processo no qual o paciente passará. Já o SetNext é onde você define quem será o próximo handler a ser executado, se não for definido nenhum next, o processo é finalizado.

E depois um maestro para o chain:

Assim, criando a corrente automaticamente, utilizando o método Handle(Patient), esse método basicamente irá configurar a ordem de execução, para cada Handler inserido na slice Handlers, será verificado se existe uma posição seguinte, caso exista, essa posição será configuração como a próxima tarefa a ser executada pelo handler atual.

Agora vejamos os Handlers:

Handler da recepção
Handler do médico

O handler do medicamente segue o mesmo formato…

Dessa forma, quando acontecer a chamada "chain.Handle(patient)" no main.go, o fluxo será iniciado, percorrendo todos os manipuladores e emitindo a mesma saída anteriormente citada.

Output

Desse modo, caso você precise alterar a mensagem de resposta do médico, por exemplo, você sabe exatamente qual arquivo será alterado, você não precisa ficar procurando no main ou em qualquer outro.

A manutenibilidade e a legibilidade aumentaram muito!

Baseado em: https://refactoring.guru/pt-br/design-patterns/chain-of-responsibility/go/example

Obrigado por ler! Se você gostou do artigo, dê um clap 👏. Achou algo errado ou que pode ser melhorado? Comenta aí e ajuda a gente!

--

--