Quando o Maven vira um Tormento

Quando o Maven vira um Tormento

Conhece o Maven? É uma ferramenta muito legal. Muito legal mesmo. Eu não o usava a até bem pouco tempo. Comecei a usar fortemente quando entrei pra equipe do Demoiselle. A partir daí, não consegui mais viver sem ele. E o principal motivo é o controle de dependências. É sucesso. É muito chato ter que sair procurando as dependências manualmente e incluir no seu projeto, né não? E quando tem versão nova de alguma biblioteca? É um saco ter que ir mudando tudo de novo! Ninguém merece.

E eu agora sempre uso o Maven para todos os meus projetos. E saiu colocando indiscriminadamente as dependências de que preciso. Sequer olho as dependências transitivas que cada projeto fornece consigo. Explicando para os incautos: dependências transitivas são aquelas dependências trazidas indiretamente por suas dependências diretas. Por exemplo, se seu projeto depende do Spring, você verá que não vem apenas o Jar do Spring, mas mais alguns que você nem esperava, como bibliotecas de log. E é aí que mora o perigo. Vou relatar para vocês como o aplicativo EncomendaZ saiu de 33mb de bibliotecas para 19mb. Vai ser um post meio que crítico e de desabafo. Vamos lá.

Começo alertando: usem o Maven com inteligência. Entendam que suas bibliotecas serão usadas em outros projetos e você não pode sobrecarregá-los com dependências desnecessárias. Veja na imagem abaixo uma pequena parte da árvore de dependências do EncomendaZ. Perceba a quantidade de dependências que existe. Você vai me perguntar: e você precisa de tanta dependência assim mesmo? Eu achava que sim. E agora descobri que não. Eu não entendia como um programa tão simples como o EncomendaZ poderia ter enormes 33mb de tamanho. Tinha algo errado.

Descobri erros dos mais simples a alguns gritantes. Vamos começar pelos mais loucos que vi. Estão vendo na imagem abaixo a biblioteca ezmorph? Ela é uma dependência indireta. E coloca indireta nisso. Mas, o mais curioso é você ver que o JUnit é uma dependência dele. Mas como “compile”?! JUnit é para ser uma dependência “test”. Esta biblioteca não é para ir junto com o deploy da aplicação. É apenas para estar na máquina dos desenvolvedores que realizam testes. Fail total!

Vamos a mais um exemplo, no mínimo, esquisito. Olha a imagem aí embaixo. É a biblioteca Jaxen. Eu sei que vocês já perceberam algo estranho. Por qual motivo uma versão mais recente de uma biblioteca precisaria depender de uma versão mais antiga dela mesma? Credo! Tem algo de errado com este projeto! Olha lá. A versão 1.1-beta-8 depende da versão 1.1-beta-6. Nunca tinha visto isso na minha vida. Eles devem ter um motivo, mas isto indica que tem algo de errado aí. Não faz sentido isso.

Mais uma. Tentem me explicar por qual motivo o Jasper Reports depende do jdtcore. Só tentem, porque não vão conseguir me convencer. Sabe o que é o JDT? Retirado do próprio site do Eclipse: “JDT Core is the Java infrastructure of the Java IDE“. WTF? Uma dependência de uma biblioteca da parte de infraestrutura do Eclipse? E o Jar dele é enorme, meu caro! Quase uns 4mb.

Agora chegamos na seção críticas construtivas. As críticas acima foram pra sacanear mesmo. Aliás, tem sacanagem maior do que fazer um POM porco como os caras acima fizeram? JUnit como compile? Haja paciência. Nesta sequência, quero apenas fazer um pedido para os criadores de bibliotecas. Modelem seus projetos pensando nas pessoas que irão usá-los. Seu projeto pode ser o MEGA-FAZ-TUDO, mas você não precisa incluir todas estas funcionalidades em um único módulo. Você acabará levando para o projeto dos outros dependências que eles podem não precisar. Vamos exemplificar.

Eu precisei gerar uma impressão no EncomendaZ e parti logo para o JasperReports. Mas minha impressão era bem simples. Eu não precisava gerar PDF. Não precisava gerar XLS. Era só mandar para a impressora e pronto. O JasperReports leva pra você, “de grátis”, o iText. Trata-se de uma ferramenta para geração de PDF. E o iText já lhe fornece o Bouncy Castle. Este último é uma biblioteca que será usada caso você queira assinar digitalmente seu PDF. O iText tem cerca de 2mb. O BouncyCastle uns 3mb. Veja a imagem abaixo.

Não acho a melhor estratégia embarcar o bcprov-jdk14 junto com o iText. Quantas pessoas vão querer realmente assinar digitalmente seus PDFs? Será que são tantas assim que é melhor incluí-lo logo? Eu, sinceramente, acho que não. Muito melhor seria o iText ter dois módulos: um core e outro que inclui assinatura digital. Teria me poupado 3mb. E digo mais, o JasperReports também poderia ter sido mais modularizado de forma que eu não precisasse trazer o iText caso não quisesse criar PDFs. Teria me poupado, agora, 5mb. Caso fossem mais modularizados, eu poderia ir escolhendo exatamente o que meu projeto necessita e não ficar criando EXCLUDES no meu POM. Esses excludes são chatos e poluem sensivelmente meu arquivo POM.

Eu sei que vocês perceberam mais um detalhe na última imagem. E é até engraçado. Não percebeu? Olha lá de novo. Tem uma dependência bcprov-jdk14 na versão 138 que o iText usa. E tem uma mesma bcprov-jdk14 mas na versão 1.38 de outra dependência. Sinistro, não? É simplesmente a mesma biblioteca mas com “groupId” e versões diferentes. Credo. Existia uma duplicidade de bibliotecas no meu projeto. Eram mais 3mb desnecessários.

Finalizando, quero deixar um alerta e um apelo! Cuidado com seus projetos Maven. Não coloquem indiscriminadamente as dependências. Analisem exatamente o que você precisa. No meu caso, eu precisava do JasperReports, mas não precisava de muitas das dependências transitivas que ele trazia. Consegui tirar quase 6mb de dependências indiretas só do JasperReports. O apelo fica para quem disponibiliza seus artefatos Maven. Cuidem com carinho o seu POM. Muito carinho. Não façam asneiras como colocar o Junit como dependência compile. Cuidem bem do seu projeto para que uma versão mais recente não precise depender de uma mais antiga. E tentem modularizar para que seus usuários escolham exatamente o que precisam e não sobrecarreguem seus projetos com megabytes a mais que são desnecessários. Vocês não tem ideia de quanto os usuários do EncomendaZ agradeceram em não terem que baixar 33mb ou mais a cada versão nova lançada.

×