# Funciones del ciclo de vida (callbacks) de JUnit 5


Al realizar pruebas con Testcontainers, se desea iniciar los contenedores requeridos antes de ejecutar cualquier prueba y eliminarlos después. Puedes usar los métodos de callback del ciclo de vida de JUnit 5 `@BeforeAll` y `@AfterAll` para esto:

```java
package com.testcontainers.demo;

import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertTrue;

import java.util.List;
import java.util.Optional;
import org.junit.jupiter.api.AfterAll;
import org.junit.jupiter.api.BeforeAll;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.testcontainers.postgresql.PostgreSQLContainer;

class CustomerServiceWithLifeCycleCallbacksTest {

  static PostgreSQLContainer postgres = new PostgreSQLContainer(
    "postgres:16-alpine"
  );

  CustomerService customerService;

  @BeforeAll
  static void startContainers() {
    postgres.start();
  }

  @AfterAll
  static void stopContainers() {
    postgres.stop();
  }

  @BeforeEach
  void setUp() {
    customerService =
    new CustomerService(
      postgres.getJdbcUrl(),
      postgres.getUsername(),
      postgres.getPassword()
    );
    customerService.deleteAllCustomers();
  }

  @Test
  void shouldCreateCustomer() {
    customerService.createCustomer(new Customer(1L, "George"));

    Optional<Customer> customer = customerService.getCustomer(1L);
    assertTrue(customer.isPresent());
    assertEquals(1L, customer.get().id());
    assertEquals("George", customer.get().name());
  }

  @Test
  void shouldGetCustomers() {
    customerService.createCustomer(new Customer(1L, "George"));
    customerService.createCustomer(new Customer(2L, "John"));

    List<Customer> customers = customerService.getAllCustomers();
    assertEquals(2, customers.size());
  }
}
```

Esto es lo que hace el código:

- `PostgreSQLContainer` se declara como un **campo estático** (static field). El contenedor se inicia antes de todas las pruebas y se detiene después de todas las pruebas de esta clase.
- `@BeforeAll` inicia el contenedor, `@AfterAll` lo detiene.
- `@BeforeEach` inicializa `CustomerService` con los parámetros JDBC del contenedor y elimina todas las filas para proporcionar una base de datos limpia a cada prueba.

Observaciones clave:

- Debido a que el contenedor es un **campo estático**, se comparte entre todos los métodos de prueba de la clase. Puedes declararlo como un campo no estático y usar `@BeforeEach`/`@AfterEach` para iniciar un nuevo contenedor por prueba, pero esto no se recomienda ya que consume muchos recursos.
- Incluso sin detener explícitamente el contenedor en `@AfterAll`, Testcontainers utiliza el [contenedor Ryuk](https://github.com/testcontainers/moby-ryuk) para limpiar los contenedores automáticamente cuando la JVM finaliza.

