O maravilhoso mundo das annotations do Spring Boot

Um dos possíveis tipos de projetos que você pode gerar a partir do SetupMyProject é o que vem configurado com o Spring Boot. Uma das belezas dele é justamente a de omitir várias das configurações que você seria obrigado a fazer se tivesse optado por criar um projeto baseado em toda stack do Spring. Como um dos objetivos deste blog é não deixar o programador usar alguma coisa apenas pelo esporte, vamos analisar um pouco as classes e annotations usadas em um projeto gerado com o Boot.

O SetupMyProject gera para você uma classe chamada Boot e já deixa ela no pacote base do seu projeto.  A ideia é justamente é que todos outros pacotes fiquem abaixo dela, mas por que precisamos disso? Para ficar mais claro precisamos destrinchar um pouco a annotation SpringBootApplication:

  @Configuration
  @EnableAutoConfiguration
  @ComponentScan
  public @interface SpringBootApplication {
    ...
  }

Essa annotation na verdade é só um atalho de configuração, ela pode ser substituída pelo seguinte conjunto:

  @Configuration
  @EnableAutoConfiguration
  @ComponentScan
  public class Boot {
    ...
  }

O Spring permite que você faça uso sempre que achar que algum conjunto de configurações do seu projeto vai começar a se repetir ou até para dar um pouco mais de semântica mesmo, como é o caso da annotation criada pelo time do Spring Boot. Entre as annotations encapsuladas pela SpringBootApplication, existem duas que são mais comuns: @Configuration e a @ComponentScan.  Só que sobrou ainda a @EnableAutoConfiguration, que talvez seja a mais importante desse pacote.

Essa é uma outra annotation do Spring Boot que indica a necessidade da auto configuração do seu projeto. Por conta da existência dela que vai ser disparado o processo de análise das classes presentes no seu classpath para que várias das configurações que nos acostumamos a fazer sejam evitadas. Por exemplo, quando for achado os jars do Hibernate já vai ser configurado automaticamente um LocalEntityManagerFactoryBean para que seja possível criar EntityManager no seu projeto. Um outro exemplo é a configuração automática do servlet container embedded, quando você adiciona o starter do Tomcat no seu projeto.

Indo um pouco além, na definição da annotation @EnableAutoConfiguration, percebemos que ela faz referência para a annotation @AutoConfigurationPackage. Essa outra annotation é a que indica que o pacote da classe anotada com ela, deve servir de base para o scan que o Spring vai fazer em busca das classes que estão anotadas com @Component ou @Configuration.  Tanto em uma annotation quanto na outra, está sendo utilizada mais uma annotation chamada @Import.

A @Import referência uma classe que vai ser usada pelo Spring como uma @Configuration. Por exemplo, a @AutoConfigurationPackage aponta para a classe Registrar, que é uma classe interna da AutoConfigurationPackages. Olhando um pedaço do código fonte dela, fica até mais simples de entender.

	private static String[] addBasePackages(
			ConstructorArgumentValues constructorArguments, String[] packageNames) {
		String[] existing = (String[]) constructorArguments.getIndexedArgumentValue(0,
				String[].class).getValue();
		Set<String> merged = new LinkedHashSet<String>();
		merged.addAll(Arrays.asList(existing));
		merged.addAll(Arrays.asList(packageNames));
		return merged.toArray(new String[merged.size()]);
	}

Perceba pelo nome do método que ele, de maneira dinâmica, está adicionando os pacotes que devem ser scaneados na nossa aplicação. Tem muito mais detalhe que a gente pode analisar. Por exemplo, qual é a mágica que a classe SpringApplication faz para conseguir subir a sua aplicação?

Lembre que quanto mais pragmático você for em relação ao ambiente que você trabalha, um melhor programador você será. Usar uma ferramenta, framework ou servidor é só o primeiro passo da jornada para você realmente dominar alguma coisa.

Advertisements

Melhorias no SetupMyProject

Nos últimos tempos trabalhamos para atender algumas solicitações dos usuários do nosso serviço :). As melhorias passam por projetos baseados em Spring, VRaptor e JSF. Abaixo seguem algumas delas.

A primeira tem a ver com o tipo de servidor que você quer usar no seu projeto. Antigamente o SetupMyProject gerava todas as configurações supondo que o programador estava trabalhando com um Servlet Container, estilo Tomcat. A partir de agora você pode decidir se quer realmente usar um Servlet Container ou Application Server. Por enquanto os projetos suportados para isso são o VRaptor e o JSF, que já fazem uso da stack do JAVA EE. Quando a opção Application Server for escolhida, as dependências do pom.xml já virão marcadas como provided, o que é o ideal quando vamos usar as bibliotecas que já estão no servidor.

Uma segunda novidade interessante, para qualquer projeto baseado no CDI, é a possibilidade de adicionar o DeltaSpike. Nesse momento fizemos o suporte apenas para os projetos baseados no JSF, mas não vai demorar para projetos baseados no VRaptor também passarem a ter esse benefício.  Só não adicionamos para o VRaptor porque ele já possui um plugin para integração com a JPA e, por enquanto, esse foi o único módulo que adicionamos do DeltaSpike.

Um outro ponto que chateava os usuários é que nosso projeto gerava uma tag chamada dependencyManagement que, na maioria das vezes, era inútil para o projeto em questão. Acaba que o programador adicionava a dependência lá e a mesma não era refletida no projeto!

Para fechar, adicionamos mais possibilidades para a geração de CRUD’s. Uma muito legal é que adicionamos um componente de paginação para as listagens de projetos baseados em VRaptor ou Spring. Paginação está presente em quase todo cadastro que somos obrigados a fazer e, querendo ou não, perdemos um certo tempo nas lógicas. Para os amantes do JSF, ainda vamos suportar a paginação baseada no componente do PrimeFaces.

Ainda no campo do CRUD, agora também é possível gerar novos cadastros para projetos que já estejam em andamento. Logo na primeira tela do fluxo de geração, tem uma opção para você seguir baseado em algum projeto que já esteja em andamento. No fim é gerado um zip que você pode importar como um archive file no seu Eclipse.

Estamos comprometidos em ser uma ferramenta de geração de código que não deixa o programador alienado. Hoje já geramos um pequeno readme explicando o que ele precisa fazer quando escolhe cada uma das opções. Nossa ideia é deixar esse readme mais completo, mostrando para o programador o motivo da geração de cada parte do código.

Por enquanto é isso pessoal, o projeto vai andando bem e com downloads diários. O objetivo é suportar a geração automática de código para o máximo de trabalho braçal que for possível. Afinal de contas queremos gastar tempo pensando em features que realmente exijam da gente :).