¿Por qué Mockito no se burla de los métodos estáticos?

Leí algunos hilos aquí sobre métodos estáticos, y creo que entiendo los problemas que puede causar el mal uso / uso excesivo de métodos estáticos. Pero realmente no llegué al fondo de por qué es difícil burlarse de los métodos estáticos.

Sé que otros marcos de burla, como PowerMock, pueden hacer eso, pero ¿por qué no puede Mockito?

Leí este artículo , pero el autor parece estar religioso en contra de la palabra static , tal vez es mi pobre entendimiento.

Una explicación / enlace fácil sería genial.

Creo que la razón puede ser que las bibliotecas de objetos falsos suelen crear simulaciones creando clases dinámicamente en tiempo de ejecución (usando cglib ). Esto significa que implementan una interfaz en tiempo de ejecución (eso es lo que hace EasyMock si no me equivoco), o heredan de la clase para simular (eso es lo que hace Mockito si no me equivoco). Ambos enfoques no funcionan para miembros estáticos, ya que no puede anularlos utilizando la herencia.

La única manera de burlarse de la estática es modificar el código de byte de una clase en tiempo de ejecución, lo que supongo que es un poco más complicado que la herencia.

Esa es mi conjetura, por lo que vale …

Si necesita simular un método estático, es un buen indicador de un mal diseño. Usualmente, se burla de la dependencia de su clase bajo prueba. Si su clase bajo prueba se refiere a un método estático, como java.util.Math # sin, por ejemplo, significa que la clase bajo prueba necesita exactamente esta implementación (de precisión vs. velocidad, por ejemplo). Si desea abstraerse de una implementación concreta de seno, probablemente necesite una Interfaz (¿verá dónde va esto?).

En serio, creo que es un olor codicioso si también tienes que burlarte de los métodos estáticos.

  • ¿Métodos estáticos para acceder a la funcionalidad común? -> Usa una instancia singleton e inyecta eso
  • ¿Código de terceros? -> Envuélvalo en su propia interfaz / delegado (y si es necesario, conviértalo en un singleton, también)

La única vez que esto me parece exagerado, es libs como Guava, pero no deberías necesitar burlarte de este tipo porque es parte de la lógica … (cosas como Iterables.transform (..))
De esta forma, su propio código permanece limpio, puede simular todas sus dependencias de una manera limpia y tiene una capa de protección contra las dependencias externas. He visto PowerMock en práctica y todas las clases para las que lo necesitábamos estaban mal diseñadas. También la integración de PowerMock ocasionó a veces serios problemas
(ej. https://code.google.com/p/powermock/issues/detail?id=355 )

PD: Lo mismo vale para los métodos privados, también. No creo que las pruebas deban conocer los detalles de los métodos privados. Si una clase es tan compleja que tienta a burlarse de los métodos privados, es probable que sea una señal para dividir esa clase …

Mockito devuelve objetos pero estático significa “nivel de clase, no nivel de objeto” Entonces mockito dará excepción de puntero nulo para estático.

En algunos casos, los métodos estáticos pueden ser difíciles de probar, especialmente si es necesario burlarse de ellos, razón por la cual la mayoría de los marcos de burla no los admiten. Encontré que esta publicación de blog es muy útil para determinar cómo simular clases y métodos estáticos.