Behaviour-Driven Development y Continuos Integration

Conectando los Requisitos con Pruebas e Implementación Automáticas

Jaime Andrés García

CEO Ingenio Sólido - Analytic Board

Pero primero una historia ....

Proyecto

Hardware + Web + Java + Data Visualization

Situación

Deadline 1 mes

Alta complejidad

Recursos disponibles 3

Recursos necesarios 7

Perfil de los recursos faltantes: 4 Expertos en Java con más de 3 años de experiencia

Ante esta situación, hay varias opciones ...

1.Entrar en pánico

2.Contratar 4 expertos en Java en Colombia

Características de la contratación

Radicados en la India

Hablan inglés

Disponibilidad de 56 horas semanales

Cómo evitar el caos?

Metodología

Scrum

Sprints de una semana

Explicar verbalmente historias de usuario

Historias de usuario con mayor detalle - Pasos, Escenarios y Criterios de Aceptación

Segmentación de las tareas para reducir complejidad

Sin embargo, el proceso es bastante complejo...

Afortunadamente, uno de los desarrolladores tiene una buena idea

Ejemplo de implementación


// Descripción User Story

// Paso 1

funcionPaso1(param1,param2,...);

// Comentario Resultado Esperado
print(resultadoPaso1);

// Paso 2

funcionPaso2(param1,param2,...);

// Comentario Resultado Esperado
print(resultadoPaso2);

// Paso 3 ...

Momento de Agregar Escenarios

Ejemplo de implementación


// Descripción User Story

// Escenario 1

  // Paso 1
  funcionPaso1(param1,param2,...);
  print(resultadoPaso1);
  
  // Paso 2
  funcionPaso2(param1,param2,...);
  print(resultadoPaso2);
  
  // Paso 3 ..
  
//Comentario Resultado Esperado Escenario 1
print(resultadoEscenario1);

// Escenario 2
                .
                .
                .
                
// Escenario 3 ..

Agregando nuevas condiciones en cada paso

Ejemplo de implementación


// Descripción User Story
// Escenario 1
  // Paso 1
  funcionPaso1(param1,param2,...);
  print(resultadoPaso1);
  // Paso 2
    //Paso 2a
    funcionPaso2a(param1,param2,...);
    print(resultadoPaso2a);
    //Paso 2b
    funcionPaso2b(param1,param2,...);
    print(resultadoPaso2b);
  // Paso 3 ..
//Comentario Resultado Esperado Escenario 1
print(resultadoEscenario1);
// Escenario 2
                .
                .
                .
// Escenario 3 ..

Espera un minuto..

No tengo tiempo para verificar si cada que se agrega un paso o condición, se rompe alguna funcionalidad

Necesito automatizar el proceso...

Necesito Pruebas Automáticas!!!

Ejemplo de implementación


// Descripción User Story
// Escenario 1
  // Paso 1
  funcionPaso1(param1,param2,...);
  if(resultadoPaso1 != resultadoEsperadoPaso1)
    print("Falló Escenario1 Paso1");
  // Paso 2
    //Paso 2a
    funcionPaso2a(param1,param2,...);
    if(resultadoPaso2a != resultadoEsperadoPaso2a)
      print("Falló Escenario1 Paso2a");
    //Paso 2b
    if(resultadoPaso2b != resultadoEsperadoPaso2b)
      print("Falló Escenario1 Paso2b");
                .
                .
                .
// Escenario 2 ..

Logramos cumplir con el objetivo. Celebración!!!!

Un momento.... Será que acabamos de inventar algo?

No realmente

Ya existe una metodología que sigue estos lineamientos...

Se llama Behaviour-Driven Development

Esta basada en Test-Driven Development

Fuente: http://diogoosorio.com/blog/entry/test-driven-development-tdd-using-phpunit

Behaviour-Driven Development

Fuente: http://www.testingexcellence.com/automated-testing-help-behavior-driven-testing/

Parte del principio de construir una prueba que guíe el desarrollo en base del comportamiento deseado

Estructura de la historia de usuario

Title (one line describing the story)

Narrative:
As a [role]
I want [feature]
So that [benefit]

Acceptance Criteria: (presented as Scenarios)

Scenario 1: Title
Given [context]
And [some more context]...
When  [event]
Then  [outcome]
And [another outcome]...

Scenario 2: ...

Fuente: http://dannorth.net/whats-in-a-story/

Ejemplo de historia de usuario

Story: Account Holder withdraws cash
As an Account Holder
I want to withdraw cash from an ATM
So that I can get money when the bank is closed

Scenario 1: Account has sufficient funds
Given the account balance is \$100
  And the card is valid
  And the machine contains enough money
When the Account Holder requests \$20
Then the ATM should dispense \$20
  And the account balance should be \$80
  And the card should be returned
  
Scenario 2: Account has insufficient funds
Given the account balance is \$10
  And the card is valid
  And the machine contains enough money
When the Account Holder requests \$20
Then the ATM should not dispense any money
  And the ATM should say there are insufficient funds
  And the account balance should be \$20
  And the card should be returned

Fuente: http://dannorth.net/whats-in-a-story/

Ejemplo de BDD - Parte 1

// Story: Account Holder withdraws cash
// As an Account Holder
// I want to withdraw cash from an ATM
// So that I can get money when the bank is closed

// Scenario 1: Account has sufficient funds

  // Given the account balance is \$100
  setAccountBalance(card,100);
  
  // And the card is valid
  setCardValidState(card,true);
  
  // And the machine contains enough money
  setMachineMoney(machine,1000000);
  
  

Ejemplo de BDD - Parte 2

// When the Account Holder requests \$20
accountRequest = 20;

// Then the ATM should dispense \$20
atmValue = getMoneyFromATM(accountRequest,card,machine);
if(atmValue==20) print("OK");
else print("Fail");

// And the account balance should be \$80
accountBalance = getCurrentBalance(card);
if(accountBalance==80) print("OK");
else print("Fail");

// And the card should be returned
if(isCardReturned(card) == true) print("OK");
else print("Fail");

Y qué me dices de la puesta en producción del sistema?

También se puede hacer automática

Integración Continua

¿Eso quiere decir que se debe integrar todo cada que se hace un cambio en el código?

Así es

Beneficios del uso de BDD y Continuos Integration

Comunicación entre los clientes y el personal técnico

Análisis de posibles soluciones - diseño ágil

Se reduce la afectación de código de otros desarrolladores

Aumento de calidad del producto

Validación directa de la historia del usuario

Facilidad para cambiar o actualizar módulos del sistema

Implementación e Integración Continua

Documentación Automática!!!

Entonces que nos hace falta ...

Cambiar el paradigma

Muchas gracias por su atención