Motivação
Recentemente foi aprovada a utilização do CMS Strapi aqui na empresa para poder delegar coisas simples como edição de texto, cor e imagens nas páginas de produto. Basicamente vamos entregar a linda dashboard do Strapi para a galera do marketing e deixar eles mesmos mudarem texto, cor e imagens na páginas sem a necessidade de um desenvolvedor (claro que com seus devidos cuidados). Isso ainda vai ser assunto para outro post aqui.
Quando fui apresentar o Strapi, uma feature que por padrão ele não tem foi requisitada: versionamento de conteúdo. Felizmente, ele tem um plugin que faz exatamente isso. Ao instalar esse plugin, percebi que o próprio autor faz um pequeno "hack" para sobrescrever o comportamento padrão do Strapi, ai entra o patch.
O que é um patch?
Um patch nada mais é do que uma representação das diferenças entre dois arquivos. Considerando os arquivos A e B, um patch dos arquivos A > B é uma descrição do que deve ser feito para transformar o arquivo A em B. Um exemplo de patch gerado pelo git diff:
diff --git a/foo.c b/foo.c
index 30cfd169..8de130c2 100644
--- a/foo.c
+++ b/foo.c
@@ -1,5 +1,5 @@
#include <string.h>
int check (char *string) {
- return !strcmp(string, "ok");
+ return (string != NULL) && !strcmp(string, "ok");
}
no topo vemos a sinalização que foi gerado pelo git diff e os tais aquivos A e B, logo após vemos identificações de linhas e conteúdos que devem ser adicionados ou removidos, sendo sinalizados por - e +. Não necessariamente um patch precisa ser e apenas um arquivo, como vocês podem ver, na primeira linha há uma identificação do nome dos arquivos que foram modificados, logo abaixo poderia ter a identificação de mais dois arquivos por exemplo e suas mudanças para transformar um no outro.
O que um patch tem a ver com um plugin do Strapi?
O plugin de versionamento de conteúdo que comentei é esse aqui, cumpre bem seu papel mesmo tendo algumas limitações. Se vocês forem nesse link, vão ver que que tem uma parte da documentação chamada "Override Save Button (Optional)", que basicamente explica como sobrescrever o comportamento do botão padrão de save do Strapi, para toda vez que tiver um novo save ele automaticamente criar uma nova versão e assim ter sucesso no versionamento. E ai você me pergunta: como ele sobrescreve isso?
Usando um patch
ele basicamente sobrescreve o componente do Strapi que faz esse funcionamento, como podemos ver na identificação no topo do arquivo que fala o que está sendo mudado
diff --git a/node_modules/@strapi/admin/admin/src/content manager/components/CollectionTypeFormWrapper/index.js b/node_modules/@strapi/admin/admin/src/content-manager/components/CollectionTypeFormWrapper/index.js
não é muito bom de ler, mas vemos que ele acessa o componente CollectionTypeFormWrapper dentro da node modules e ai sim começa a fazer as mudanças necessárias, colocando o comportamento desejado. Para aplicar esse patch ele usa uma lib chamada patch-package.
Sobrescrever algo dessa maneira é bom?
Bem.... O Strapi continua funcionando perfeitamente com o comportamento desejado e o nosso problema foi resolvido! Já que é algo tão pontual e que não interfere em nada no resto, acredito que não há problema nenhum. A própria dashboard do strapi permite algumas customizações, mas nada a esse nível. Já que o patch resolveu o problema, todo mundo sai feliz.
Conclusão
Eu cai nisso de paraquedas, tanto que só fui ver isso a fundo por que o patch que tem na documentação simplesmente parou de funcionar na versão 4.1.7 que é a que estou usando (o componente teve algumas mudanças, por isso o patch quebrou). Com isso, fui procurar e vi que tinha uma issue aberta no Github, como não tinha solução ainda, fui lá e adaptei o patch para funcionar na versão 4.1.17 e abri um pull request para atualizarem na documentação. Foi uma experiência legal.