2009-11-03 6 views
9

¿Cómo prueba una unidad que se generó un nuevo hilo para una tarea ejecutable cuando se usa un ExecutorService?¿Cómo probar la unidad de que ExecutorService genera un nuevo hilo para la tarea?

Básicamente, tengo un grupo de subprocesos estáticos para mi aplicación.

public static final ExecutorService executorService = Executors.newCachedThreadPool(); 

me gustaría utilizar este grupo de subprocesos para los mis pruebas de unidad, en lugar de burlarse de uno o inyectar un nuevo grupo de subprocesos, ya que los diferentes grupos de subprocesos pueden alterar drásticamente el comportamiento de mi solicitud (frente fijo en caché frente a programado, etc.); Quiero asegurarme de que pruebo el comportamiento de la aplicación con su grupo de subprocesos en tiempo de ejecución.

El grupo de subprocesos en caché parece funcionar mejor para mí. El problema es que, dado que es estático y los subprocesos se guardan en caché durante 60 segundos, solo la primera prueba generará un nuevo subproceso en el grupo, mientras que las pruebas subsiguientes reutilizarán ese subproceso. código de prueba

Unidad:

public void testDoCallExecutesTaskInAnotherThread() {  
    final Client client = this.createClient(); 
    final ThreadPoolExecutor threadPoolExecutor = (ThreadPoolExecutor) client.getExecutorService(); // gets the static thread pool 
    final int initPoolSize = threadPoolExecutor.getPoolSize(); 
    final Response response = client.doCall(); 
    Assert.assertEquals(initPoolSize + 1, threadPoolExecutor.getPoolSize()); 
} 

consejos sobre cómo conseguir este trabajo, u otro enfoque sería apreciada por completo.

+0

¿Por qué le importa si el cliente realiza la llamada en un hilo separado? Veo que me preocupo por cosas como "¿cuánto tiempo lleva esto?" o "esta operación responde correctamente a una interrupción". Pero tal como está, esta parece ser una aplicación pobre de pruebas unitarias. – erickson

+0

Buena pregunta. Este cliente en particular debe ejecutar una llamada al servicio web asincrónicamente para que no contenga el objeto que lo utiliza, un problema de rendimiento en mi aplicación. No estoy esperando una respuesta, solo quiero asegurarme de que la tarea que realiza una llamada al servicio web se genere de forma asíncrona. –

+0

Eso es lo que pensé. Entonces, lo que realmente debes probar es si "mantiene [s] el objeto que lo usa". Es decir, ¿cuánto tiempo lleva? Puedo implementar doCall de tal manera que demore dos días en regresar, pero todavía hace que el ejecutor cree otro hilo; su prueba de unidad aún pasaría, aunque su criterio sea violado. – erickson

Respuesta

19

Mock la ThreadFactory:

ThreadFactory mock = new CustomObservableThreadFactory(); 
    ExecutorService executorService = Executors.newCachedThreadPool(mock); 
  1. inyectar el ExecutorService en la clase bajo prueba como de costumbre
  2. pero el uso de un encargo ThreadFactory para crear ThreadPool caché: El ThreadFactory se llamará siempre un nuevo hilo será llamado. Luego puede rastrear estas instancias como lo desee, por ejemplo, con un oyente o contador.
Cuestiones relacionadas