IMasterPro: Curso de TDD em Java

Olá Pessoal, 
 
O post de hoje na verdade é para apresentar para vocês mais um curso que estou lançando no IMasterPro, o objetivo é para aquele que querem aprender TDD, já até tentou, mas não conseguiu ir muito adiante e não pegou o jeito da coisa. E como eu já passei por isso e tive bastante dificuldade na época em encontrar material mais focado e bem direcionado em nosso idioma, resolvi  montar o curso online para ajudar quem está chegando agora. A seguir  falo um pouco sobre o curso.
lets go..
 
Sobre o Curso 
Se você espera um curso teorico e cheio de bla bla, esquece. Nem eu gosto de curso assim. Fiz o curso bem focado na prática, ou seja, mão na massa. Com problemas, exercicios práticos para que você possa ir resolvendo a medida que vamos evoluindo no aprendizado. Não tem jeitinho brasileiro, receita de bolo para aprender. A única forma é praticar e não ter preguiça  de fazer os exercicios e resolver o problema, só aprende  programar orientado a teste programando e não lendo. Já viu alguém aprender a dirigir lendo um livro de como dirigir? 
 
Quem não deveria fazer o curso
– quem não gosta de programar; 
– quem gosta de respostas prontas;
– quem gosta de seguir passos para resolver um exercicio e achar que aprendeu; 
– quem acha que TDD é coisa de desenvolvedor nerd e é frescura :); 
 
 O que vou ver no curso? 
 – Muito código Java; 
 – problemas para resolver através de unit tests; 
 – entender o ciclo de TDD e ser direcionado para aplicar nos exercicios e problemas existente; 
 – Meter mão na massa do inicio ao fim.
 
 Mais sobre o curso vocês podem conferir aqui
 
 Dúvidas? Comentem 🙂
 
 abracos see ya!!

Série CI: Executando unit tests Jenkins via Maven

Olá Pessoal,

No post de hoje veremos como executar os unit tests, após executarmos mvn compile. Vou considerar que você já tem o Jenkins instalado e um projeto configurado.

Lets go…

Starting…

Primeiro passo é ir em configure do projeto no Jenkins, pare o mouse em cima do projeto/job criado e escolha  configure.

Em Build, configuramos para rodar mvn compile.

buildmavencompile

Mas e se você quiser também rodar os unit tests? Simples, basta adicionar mvn test

Clique no botão add build step escolha Invoke top-level Maven targets e deixe conforme a imagem a seguir:

mvntestbuild

Pronto, após  o compile vamos executar os testes.

Um problema

Se você mandar construir uma build e todos os testes tiverem passando, você não tem problemas aparentemente, mas faça um teste falhar e mande construir. Certamente verá isso:

 

readerwebbuildfailuretestes

Ué, um teste falhou, mas o build foi dado como sucess. Esse é o problema e vamos resolver.

Solução

A solução é muito simples, apenas vamos dizer que as falhas na execução de qualquer unit tests não podem ser ignoradas, para isso precisamos atualizar o comando mvn test, deixando assim:

test -Dmaven.test.failure.ignore=false

mvntestignoretest

Salve as alterações e rode uma nova build clicando em build now. E aguarde….

Resultado

É isso que esperamos:

readerwebtestpassedjenkinsbuild

Pronto. Agora sempre que um teste falhar a construção da build também vai falhar.

Vou ficando por aqui e espero que tenham gostado do post.

See ya!! 

Utilizando o Selenium para testes Automatizado

Olá Pessoal,

No post de hoje vamos ver como usar o Selenium para criação de testes funcionais. A ideia é um teste simples para mostrar a potência do framework e daí cabe a cada um usar de forma que atenda as necessidades do projeto. Para o post vou usar a versão selenium-server-standalone-2.32.0.jar  disponível http://docs.seleniumhq.org/

 lets go…

Overview sobre o Selenium

Bem, se você usar o Google e pesquisar sobre “Selenium unit test” verá vários links para a definição, então não há motivos para repetir no post. Veja no famoso Wikipedia. Há um post que gosto bastante sobre o Selenium  que está no blog da Caelum.

Em poucas palavras, nos permite realizar teste funcionais simulando ações que um usuário estaria fazendo.

Mas por que usar um framework para isso?

Há vários motivos para fazer isso de maneira automatizada, como por exemplo:

  • – produtividade;
  • – qualidade;
  • – custo;
  • – feedback.

Contratar um time de profissionais para fazer testes que você pode automatizar, além de custar caro, o tempo gasto é muito maior que de forma automatizada e isso é importante. Assim podemos contratar profissionais para realizar em pontos estratégicos onde não temos como testar de forma automatizada. Como toda e qualquer ferramenta sempre há uma limitação e ai que entra o fator o humano.

Colocando mão na massa

Vamos colocar a mão na massa e criar um projeto muito simples. Faremos um teste que terá como objetivo acessar uma determinada página na internet e fazer uma pesquisa. Se tudo ocorrer bem, o teste vai passar. Mas, por exemplo, se a página estiver indisponível ou o endereço informado para o teste for inválido o teste vai falhar.  

  1. Crie um Java project e dê o nome que quiser;
  2. Adicione a biblioteca do Selenium ao  classpath do projeto;
  3. Crie uma classe de teste, ou seja, Junit Class. No meu caso criei com o nome de HelloSeleniumTest.java

helloseleniumproject

Vamos criar o nosso primeiro teste que vai acessar a página do Google e pesquisar por “Camilo Lopes”. Veja o código a seguir.

public class HelloSeleniumTest { 

       @Before

       public void setUp() throws Exception {

       } 

       @Test

       public void testSearchInGooglePage() {

             WebDriver driver  = new FirefoxDriver();            

//           Digo qual url para acessar

             driver.get(“http://www.google.com”);            

//           Agora vamos buscar o elemento na página

             WebElement inputTextGoogle = driver.findElement(By.name(“q”));

             inputTextGoogle.sendKeys(“Camilo Lopes”);        

/*           faz um submit na página

 *           poderia buscar o botão search e fazer o submit tb.

 */

             inputTextGoogle.submit();            

             assertTrue(driver.getPageSource().contains(driver.findElement(By.id(“gbqfq”)).getText()));

       } 

}

Entendendo o código

Apesar de que em alguns trechos eu coloquei comentários somente para facilitar o entendimento, vou explicar alguns pontos que considero importantes.

WebDriver: é uma interface do Selenium que todo Web Browser Drivers implementa. O Firefox Browser tem  sua implementação, assim como IE e Chrome, cada um com sua particularidade, e é preciso dar uma olhada na documentação sobre como implementar.

Depois que instanciamos o driver,  dizemos a URL que queremos testar (nesse caso será do Google), mas em um projeto JEE, por exemplo, vamos colocar o caminho onde está nossa aplicação.

Em seguida pesquisamos pelos elementos na página, para isso no Chrome podemos usar o atalho F12, clica na lupa que fica no rodapé e clica sobre o input text e ver qual o nome daquele campo. Podemos usar o id, nome etc. Veja:

seleniuminputgooglesearch

Depois que fizemos isso, criamos uma variável para representar esse campo :

WebElement inputTextGoogle = driver.findElement(By.name(“q”));

 

E em seguida invocamos o método sendKeys(…) e passamos o valor que queremos que seja digitado no input. Para descobrir e conhecer melhor os métodos disponíveis tem que passar por alguns minutos vendo o que temos na documentação do framework.

inputTextGoogle.sendKeys(“Camilo Lopes”);

 

Logo em seguida fizemos o submit página

inputTextGoogle.submit();

 

Criando o assert

Bem, para que  seja testado precisamos usar algum assertXXX do framework Junit. Então vamos verificar se após ter feito o submit há um elemento com o id informado na página.

seleniumtestgreen

O teste passa. Na verdade esse teste  não tem nada de inteligente. Se você reparar, ele verifica se o input que pesquisamos na primeira página do Google é o mesmo na página do resultado da busca.

Claro que em nossa aplicação íamos testar algo mais voltado para regras de negócio. E o método getPageSource() nos ajuda nisso, em busca de um elemento na página corrente.

 

Execute o teste

Vamos executar os testes e aguardar por alguns segundos e veremos que o Selenium vai abrir o browser que definimos (no caso do post foi o Firefox)  e realizar a pesquisa.

 seleniumfirefox

Convertendo isso para uma aplicação

Em uma aplicação web, vamos ter que usar a url onde nossa aplicação está rodando. Claro que vamos evitar que o endereço seja informado dentro da classe Java, este pode ser informado de um arquivo .properties por exemplo, efaremos assert voltado para as regras de negócio.

Conclusão

O objetivo desse post não era explorar como escrever bons testes com o Selenium, a ideia era apresentar o framework e vê-lo em ação. Após isso podemos tirar nossas próprias conclusões sobre a eficiência e produtividade gerada  quando usamos corretamente.  Já passei por algumas empresas e projetos onde falaram que o Selenium foi o responsável pelo aumento do dos prazos nas entregas. Acredito que o problema certamente não foi com o Selenium, mas sim na forma de como este foi usado ou adotado dentro do projeto.

 

E você tem usado o Selenium em seus projetos? Compartilhe sua experiência…

Abraços, see ya!!! 

Série Spring: CRUD Spring 3 + Hibernate + Unit Tests

Olá Pessoal,

No post de hoje veremos como fazer um simples CRUD usando o Spring, integrando com Hibernate e testando via unit tests com JUNIT4. No último posts vimos apenas uma integração com o Hibernate e também um CRUD usando HibernateTemplate, esse aqui  veremos que na versão 3 do Spring não precisamos mais do HiberanteTemplate e vamos testar nosso código com unit test.

Lets go…

Starting…

Primeiro passo é que  estarei assumindo que você já tem .jars necessário  para o ambiente. Já que esse não é o primeiro post da série, caso contrário terá que baixar os .jars para: driver Mysql 5, Hibernate 3.6, AOP, AspectJ, Spring 3.x.

Antes de começarmos a desenvolver, vamos primeiro estruturar nosso projeto e packages conforme a imagem a seguir:

springrentcarproject

Nosso CRUD será o cadastro  de veículos  que serão alugados. Claro que há muito mais regras de negócios do que a que veremos no exemplo a seguir, porém o nosso objetivo é explorar o framework Spring e não tratar todas as regras de negócio em um post.

  1. Crie a estrutura conforme a imagem acima
  2. Crie o arquivo de configuração de Spring, o qual chamei de springconfiguration.xml, e coloque dentro do package config.
  3.    Agora vamos colocar a carne no nosso XML

Cabeçalho fica assim:

<beans xmlns=“http://www.springframework.org/schema/beans”

xmlns:xsi=“http://www.w3.org/2001/XMLSchema-instance”

xmlns:context=“http://www.springframework.org/schema/context”

xmlns:tx=“http://www.springframework.org/schema/tx”

xmlns:aop=“http://www.springframework.org/schema/aop”

xsi:schemaLocation=“http://www.springframework.org/schema/beans

http://www.springframework.org/schema/beans/spring-beans-3.0.xsd

http://www.springframework.org/schema/context

http://www.springframework.org/schema/context/spring-context-3.0.xsd

http://www.springframework.org/schema/tx

http://www.springframework.org/schema/tx/spring-tx-3.0.xsd

http://www.springframework.org/schema/aop

http://www.springframework.org/schema/aop/spring-aop-3.2.xsd”>

 

Estarei comentando mais na frente ou in line apenas o que  ainda não foi abordado nos posts anteriores.

O cara que busca os beans: 

<context:component-scan base-package=“*”/>

 Colocando translation

<!– esse cara faz as traduções das exception checked para as unchecked do Spring –>

<bean class=“org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor”/>

Data source

<!– pelo nome diz, data source para conexão com o DB –>

<bean id=“dataSource” class=“org.springframework.jdbc.datasource.DriverManagerDataSource”>

<property name=“driverClassName” value=“com.mysql.jdbc.Driver”/>

<property name=“url” value=“jdbc:mysql://localhost/test”/>

<property name=“username” value=“root”/>

<property name=“password” value=“camilo2593”/>

</bean>

 

Configurando a SessionFactory

<!– Aqui estamos definido como será a parte de persistêcia, e dizemos que faremos via annotation –>

<bean id=“sessionFactory” class=“org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean”>

<!– informando a quem estaremos conectado –>

<property name=“dataSource” ref=“dataSource”/>

<!– dizendo onde estão as classes dominio, ele saberá devido anotação @Entity  –>

<property name=“packagesToScan” value=“br.com.camilolopes.rentcar.domain.bean”/>

<!– configurando coisas especificas do Hibernate –>

<property name=“hibernateProperties”>

<props>

<prop key=“hibernate.dialect”>org.hibernate.dialect.MySQL5InnoDBDialect</prop>

<prop key=“hibernate.hbm2ddl.auto”>update</prop>

</props>

</property>

</bean>

 

Definindo Transaction

 <!– definindo quem vai gerenciar as transaction, ou seja, será o Hibernate –>

<bean id=“transactionManager” class=“org.springframework.orm.hibernate3.HibernateTransactionManager”>

<property name=“sessionFactory” ref=“sessionFactory”/>

</bean>

</beans>

Há duas formas de declararmos as transaction no Spring por XML ou Annotation.  Veremos as duas formas, no nosso caso de usarmos o XML faremos com AOP e você entenderá o  motivo:

Via XML

<!– todo medoto que começa com add é required uma transaction –>

<tx:advice id=“txAdvice”>

<tx:attributes>

<tx:method name=“add*” propagation=“REQUIRED”/>

<tx:method name=“update*” propagation=“REQUIRED”/>

<tx:method name=“*” propagation=“SUPPORTS” read-only=“true”/>

</tx:attributes>

</tx:advice>

<!– toda classe que extends a interface terá uma referência para o advisor –>

<aop:config>

<aop:advisor pointcut = “execution(* *..RentCar.*(..)))” advice-ref=“txAdvice”/>

</aop:config>

 

Em alguns contexto dessa forma é bem mais prático que usar Annotations.

 

Via annotation

Remove todo o código XML acima e apenas adiciona a seguinte linha:

<tx:annotation-driven/>

 

Claro que teremos que anotar nas classes/métodos como @Transaction e informar como esse deve se comportar , seguindo o exemplo do XML acima seria algo  assim:

@Transactional(readOnly=true,propagation=Propagation.SUPPORTS)

public class myClass{  }

 

Normalmente você colocaria isso na camada de serviço.Mas, se você está brincando  e não tem uma camada de serviço, pode colocar direto no DAO.

E o método que faria uma das operações de banco ficaria assim:

@Transactional(isolation=Isolation.DEFAULT,propagation=Propagation.REQUIRED)

      public void save(Car car) {

            getCurrentSession().save(car);}

 

No nosso exemplo vamos não vamos usar Annotations e exploraremos o benefício de usar a versão do XML conforme acima, se vc deixar a tag para annotation no arquivo de configuração o Spring não vai se importar com isso.

Desenvolvimento

Após toda essa configuração, vamos agora desenvolver nossas classes .java. Começando pela classe de domínio:

@Entity

@Table(name=”CARS”)

public class Car implements Serializable{

private static final long serialVersionUID = -2896368465389020843L;

      @Id

      @GeneratedValue

      private Long id;

      private String manufacter;

      private String description;

      private BigDecimal marketValue;

                //getters/setters omitidos

Basicamente isso .

Interface DAO

public interface RentCarDAO {

      void save(Car car);

      List<Car> findAll();

      List<Car> findAllByDescription(String description);

      void update(Car car);

      void delete();

}

Implementação da Interface:

@Repository

public class RentCarDAOImpl implements RentCarDAO {

      @Autowired

      private SessionFactory sessionFactory;

      public Session getCurrentSession(){

            return sessionFactory.getCurrentSession();

      }

      @Override

      public void save(Car car) {

            getCurrentSession().save(car);

      }

      public void setSessionFactory(SessionFactory sessionFactory) {

            this.sessionFactory = sessionFactory;

      }

      @Override

      public List<Car> findAll() {

            return getCurrentSession().createCriteria(Car.class).list();

      }

      @Override

public List<Car> findAllByDescription(String description) {

Criteria createCriteria = getCurrentSession().createCriteria(Car.class);

createCriteria.add(Restrictions.ilike(“description”, description));

            return (List<Car>) createCriteria.list();

      }

      @Override

      public void update(Car car) {

            getCurrentSession().update(car);

      }

      @Override

      public void delete() {

Query query = getCurrentSession().createQuery(“delete from Car where id >0”);

            query.executeUpdate();

      }

Interface de Serviço

@Service

public interface RentCar {

      void addNewCar(Car car);

      List<Car> findAll();

      List<Car> findCarByDescription(String description);

      void updateCar(Car car);

      void delete();

}

Classe que implementa o Serviço

@Service

public class RentCarServiceImpl implements RentCar {

      @Autowired

      private RentCarDAO rentCarDAO;

      @Override

      public void addNewCar(Car car) {

            rentCarDAO.save(car);

      }

      public void setRentCarDAO(RentCarDAO rentCarDAO) {

            this.rentCarDAO = rentCarDAO;

      }

      @Override

      public List<Car> findAll() {           

            return rentCarDAO.findAll();

      }

      @Override

      public List<Car>findCarByDescription(String description) {

           return (List<Car>) rentCarDAO.findAllByDescription(description);

      }

      @Override

      public void updateCar(Car car) {

            rentCarDAO.update(car);

      }

      @Override

      public void delete() {

      rentCarDAO.delete();     

      }

}

 

Unit Test

Se não reparou quando criou o projeto, temos um source  apenas  para os unit tests, conforme a imagem a seguir:

springrentcarunittestssource

Agora crie a classe de teste. A seguir mostrarei apenas dois simples testes, você deve criar os demais para validar os cenários, não coloquei todos para não ficar mais longo ainda o post.

@RunWith(SpringJUnit4ClassRunner.class)

@ContextConfiguration(locations={“classpath:config/springconfiguration.xml”})

public class RentCarServicesTest {

      @Autowired

      private RentCar rentCarServicesImpl;

      private Car car;

      @Before

      public void setUp() throws Exception {

            car = new Car();

      }

      @Test

      public void testAddingNewCarWithSuccess(){

            try{

                  car.setDescription(“Civic”);

                  car.setManufacter(“Honda”);

                  car.setMarketValue(new BigDecimal(740000));

                  rentCarServicesImpl.addNewCar(car );

            }catch (Exception e) {

                  Assert.fail(“not expected result”);

            }

      }

      @Test

      public void testListAllCarIsNotEmpty(){

            assertFalse(rentCarServicesImpl.findAll().isEmpty());

      }

 Resultado

Lembre-se que seu BD precisa está rodando

springhibernateunittestresult

 

Ufa! Esse post foi longo heim, mas não tinha outra forma de mostrar tudo se não fosse assim, e olha que busquei resumir ao máximo possível. Enfim, vou ficando por aqui.

GitHub

Acesse o repositório no github com todos os projetos da série Spring:  https://github.com/camilolopes/workspacespring

Espero que tenham gostado do post.

Abraços, see ya!! 

Série Spring:Rodando Unit Test com Spring Framework

Olá Pessoal,

Nesse post veremos como rodar nossos unit tests com o Spring framework, ou seja, aproveitar tudo de bom que tem o Spring e fazer nossos unit test funcionar normalmente. É bastante simples.

lets go…

Começando

Bem não vou entrar nos detalhes do que  é unit test, Spring, JUnit etc. Vamos direto ao ponto de maneira prática. Primeiro Crie um Java Project, o meu será SpringExampleUnitTest

note: claro que você precisa ter baixado o Spring framework core versão 3.x.

 

springexampleunittestproject

Note: adicione o arquivo commons-logging-1.1.1.jar  caso não tenha só baixar esse arquivo, basta digitar o nome no Google .

Desenvolvendo

Como bom baiano e pensando no carnaval de salvador vamos de chicletão. Temos uma interface que tem um método e uma classe que vai implementar:

 

package br.com.camilolopes;

public interface Competidor {

public void apresentar();

}

public class Chicletao implements Competidor {

                private Chicleteiro chicleteiroMusica;

                @Override

                public void apresentar() {

                               chicleteiroMusica.cantar();

                }

                public void setChicleteiroMusica(Chicleteiro chicleteiroMusica) {

                               this.chicleteiroMusica = chicleteiroMusica;

                }

}

 

public interface Musica {

void cantar();

}

public class Chicleteiro implements Musica {

                @Override

                public void cantar() {

                               System.out.println(“chicleteiro eu, chicleteira ela”);

                }

}

 

E no package conf, criamos um xml com as configurações do Spring:

<beans xmlns=”http://www.springframework.org/schema/beans”

xmlns:xsi=”http://www.w3.org/2001/XMLSchema-instance”

xsi:schemaLocation=”http://www.springframework.org/schema/beans

http://www.springframework.org/schema/beans/spring-beans-3.0.xsd”>

 <!– classe normal –>

 <bean id=”chicleteiro” />

<!– classe que implementa a interface –>

 <bean id=”bell”>

                <property name=”chicleteiroMusica” ref=”chicleteiro”/>

 </bean>

</beans>

 

Pronto. Agora vamos criar a classe de teste.Porém, vamos entender o que acontece com a nossa aplicação. Quando o método apresentar() é invocado, a classe vai se apresentar com a musica que deseja, no caso da classe Chicleteiro, vai cantar: “chicleteiro eu, chicleteira ela”.

 

@RunWith(SpringJUnit4ClassRunner.class)

@ContextConfiguration(locations={“classpath:conf/idolos.xml”})

public class ChicletaoTest {

                @Autowired

                private Chicleteiro chicleteiro;

               

                @Test

                public void testCantar() {

                Chicletao chicletao = new Chicletao();

                chicletao.setChicleteiroMusica(chicleteiro);

                try{

                               chicletao.apresentar();

                }catch (NullPointerException e) {

                               Assert.fail(“not expected result”);

                }

                }

 

Com Spring precisamos usar anotação @RunWith e informar qual framework vamos usar, no nosso caso usamos o JUNIT.Em seguida com anotações @ContextConfiguration estamos dizendo qual o xml que tem as configurações do Spring que usaremos para os testes. Que é o mesmo da aplicação. Em seguida fizemos um teste que apenas chama o método apresentar, e esperamos que nunca tenhamos um NullPointerException, mas para isso acontecer é apenas se a instância que chama o método for null, ou seja, não for instanciada. E com esse teste estamos validando duas coisas, uma que o Spring realmente está instanciando o atributo e que o resultado é o que esperamos. Veja:

springexampleunitestgreenresult

 

E assim temos nosso unit test integrado com o Spring. Simples não?

GitHub

Acesse o repositório no github com todos os projetos da série Spring:  https://github.com/camilolopes/workspacespring

Vou ficando por aqui!!

See ya!