domingo, 25 de julio de 2010

Links del día: Mocks, Building tools

"Untestable" code - JMockit: bastante más fácil que con Surrogate. Hace falta Java 5 porque hace uso de la instrumentalización.

Gradle: Why? : Parece que Hibernate se pasa a Gradle como herramienta de construcción del proyecto. ¿Hora de cambiar?

viernes, 9 de julio de 2010

Sobreescribir métodos estáticos para testeo en Maven 2 usando Surrogate.

Creo que en inglés me habría quedado un título más correcto. Algo así como: 'Mocking static methods for testing in Maven 2 using Surrogate'.

El problema
El caso es que me encuentro con que la clase que quiero testear llama al método estático OpenCms.getRoleManager(). Además, el proyecto se construye con Maven 2 (ó 3), por lo que habrá que modificar el POM consiguientemente.

Esta es la clase:

package arm.opencms.accesscontrol;
import org.opencms.file.CmsObject;
import org.opencms.main.OpenCms;
import org.opencms.security.CmsRole; 

public class XmlContentAccessControl {

  private CmsRole ACCEPTED_ROLE=CmsRole.VFS_MANAGER;
  public boolean hasPermission(CmsObject cmsObject) {

    return OpenCms.getRoleManager.hasRole(cmsObject,ROLE);

  }
}

La solución más cabal: refactorizar

En lugar de adaptar nuestro código de prueba, podemos adaptar nuestro código principal para que sea más testeable. En este caso podemos declarar un atributo de la clase para almacenar un CmsRoleManager:

package arm.opencms.accesscontrol;
import org.opencms.file.CmsObject;
import org.opencms.security.CmsRoleManager;
import org.opencms.security.CmsRole; 

public class XmlContentAccessControl2 {

  private CmsRoleManager roleManager;   
    
  public XmlContentAccessControl(CmsRoleManager roleManager){
    this.roleManager=roleManager;
  }

  private CmsRole ACCEPTED_ROLE=CmsRole.VFS_MANAGER;
  public boolean hasPermission(CmsObject cmsObject) {

    return this.roleManager.hasRole(cmsObject,ROLE);

  }
}


Si refactorizar no es posible o deseable, una posible solución: Surrogate

Si la única salida es llamar al método estático, podemos usar el framework Surrogate, que, apoyándose en AspectJ, permite definir sustituciones de los métodos o de las clases principales en nuestro código de prueba. Una de sus funcionalidades es la de sobreescribir métodos estáticos.

Para nuestro ejemplo, usaremos el siguiente árbol de directorios con sus correspondientes contenidos:

/
|-src
| |-main
| | |-java
| | | |-arm/opencms/accesscontrol
| | |   |-XmlContentAccessControl.java
| | |-aspect
| |   |-OpenCmsStaticCalls.aj
| |-test
|   |-java
|     -arm/opencms/accesscontrol
|      |-TestAccessControl.java
|-test
|  |-lib
|    |-surrogate-core-1.0rc1.jar
|-pom.xml

Y el contenido de los ficheros:

pom.xml

<project xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://maven.apache.org/POM/4.0.0"
xsi:schemalocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
 <modelversion>4.0.0</modelversion>
 <groupid>arm.opencms</groupid>
 <artifactid>arm.opencms.accesscontrol</artifactid>
 <name>AccessControl</name>

 <dependencies>
  <dependency>
   <groupid>org.opencms</groupid>
   <artifactid>opencms</artifactid>
   <version>7.5.2</version>
  </dependency>
  
  <dependency>
   <groupid>junit</groupid>
   <artifactid>junit</artifactid>
   <version>4.8.1</version>
   <scope>test</scope>
  </dependency>
  <dependency>
   <groupid>org.jmock</groupid>
   <artifactid>jmock-junit4</artifactid>
   <version>2.5.1</version>
   <scope>test</scope>
  </dependency>
  
  <dependency>
   <groupid>net.sourceforge.surrogate</groupid>
   <artifactid>surrogate-core</artifactid>
   <version>1.0rc1</version>
   <scope>test</scope>  
  </dependency>
  <dependency>
     <groupid>org.aspectj</groupid>
     <artifactid>aspectjtools</artifactid>
     <version>1.6.7</version>
     <scope>test</scope>
  </dependency>
  <dependency>
   <groupid>org.aspectj</groupid>
   <artifactid>aspectjrt</artifactid>
   <version>1.6.7</version>
   
  </dependency>  
  <dependency>
   <groupid>mockobjects</groupid>
   <artifactid>mockobjects-core</artifactid>
   <version>0.09</version>
   <scope>test</scope>
  </dependency>  
 </dependencies> 
 <build>
 <plugins>
        <plugin>
            
            <artifactid>maven-install-plugin</artifactid>               
            <executions>
                <execution>
                    <id>install-javabridge-javabridge</id>
                    <phase>initialize</phase>
                    <goals>
                        <goal>install-file</goal>
                    </goals>
                    <configuration>
                        <file>test/lib/surrogate-core-1.0rc1.jar</file>
                        <groupid>net.sourceforge.surrogate</groupid>
                        <artifactid>surrogate-core</artifactid>
                        <packaging>jar</packaging>
                        <version>1.0rc1</version>
                    </configuration>
                </execution>
            </executions>
        </plugin>
 <plugin>
           <groupid>org.codehaus.mojo</groupid>
           <artifactid>aspectj-maven-plugin</artifactid>
           <version>1.3</version>
           <configuration>
  <compliancelevel>1.5</compliancelevel>
      <aspectdirectory>src/test/aspect</aspectdirectory>
    </configuration>
           <executions>
              <execution>
                 <goals>
                   <goal>compile</goal>
                 </goals>
              </execution>
           </executions>
        </plugin>           
    </plugins> 
  </build>
</project>

La biblioteca Surrogate no está disponible en ningún repositorio público, por lo que la instalamos durante la inicialización como vimos en un post anterior. También se usa el plugin de AspectJ, para compilar el aspecto OpenCmsStaticCalls.aj .


TestAccessControl.java

@RunWith(JMock.class)
public class XmlContentAccessControlTest {
        
    private Mockery context = new JUnit4Mockery() {{
 setImposteriser(ClassImposteriser.INSTANCE);
    }};

    CmsObject mockCmsObject=context.mock(CmsObject.class);
    CmsRoleManager mockRoleManager=context.mock(CmsRoleManager.class);
    
    @Test
    public void testHasPermissionOnTab()throws NoSuchMethodException, CmsRoleViolationException {

 SurrogateManager mm = SurrogateManager.getInstance();
 mm.reset();
 //OpenCms.getRoleManager() -> mockRoleManager
 MockMethod mockGetRoleManager = mm.addMockMethod(new MockMethod(OpenCms.class, "getRoleManager"));
 mockGetRoleManager.addReturnValue(mockRoleManager);
 
 context.checking(new Expectations() {{

     allowing(mockRoleManager).hasRole(with(is(mockCmsObject)),
                                (CmsRole)with(allOf(an(CmsRole.class),hasProperty("roleName", is("VFS_MANAGER")))));
      will(returnValue(true));
 }});
 
 XmlContentAccessControl accessControl=new XmlContentAccessControl();
 
 assertTrue(accessControl.hasPermission(mockCmsObject));
    }


OpenCmsStaticCalls.aj

aspect OpenCmsStaticCalls extends net.sf.surrogate.core.SurrogateCalls {
 /**
  * Implementation of the mock pointcut
   */
 protected pointcut mockPointcut() :
 (
  call(* org.opencms.main.OpenCms.*(..))
    );                             
} 

lunes, 5 de julio de 2010

Torneo de Kayak-Polo Internacional de Horb 2010

El 3 de julio se celebró el Torneo de Kayak-Polo Internacional de Horb, en la ciudad de Horb am Neckar. Participaron 6 equipos masculinos y una cifra similar de equipos infantiles y cadete. El ganador fue el KSC Mannheim.

Como se puede observar en la marca de agua, he robado la foto vilmente de www.kanupolo-villingen.de.

martes, 22 de junio de 2010

Hoguera


Tomada junto al lago Edersee

domingo, 13 de junio de 2010

Aquí falta algo...

 ... y seguro que soy el único por aquí que se ha dado cuenta del detalle.

martes, 25 de mayo de 2010

Un par de funcionalidades de Maven 2

Utilizar artefactos que no están en ningún repositorio

Un problema recurrente en Maven 2 es cómo usar y versionar artefactos que no hay en ningún repositorio público. Se pueden instalar en el repositorio local, o en el privado de la empresa, pero si quieres distribuir el código fuente, éste no va a compilar sin hacer ciertos pasos previos. Una forma de solucionar esto es lo que propongo aquí, y es guardar los jars necesarios en el directorio lib del proyecto que los necesita e instalarlos en el repositorio local durante la fase 'initialize' usando el plugin 'maven-install-plugin'. En mi caso me hizo falta para incluir en mi aplicación el puente PHP/Java.

    <plugins>
        <plugin>
            <!-- Install the JavaBridge JARs in the local maven repository : JavaBridge -->
            <artifactId>maven-install-plugin</artifactId>               
           
<executions>
                <execution>
                    <id>install-javabridge-javabridge</id>
                    <phase>initialize</phase>
                    <goals>
                        <goal>install-file</goal>
                    </goals>
                    <configuration>
                        <file>lib/JavaBridge.jar</file>
                        <groupId>net.sourceforge.phpjavabridge</groupId>
                        <artifactId>JavaBridge</artifactId>
                        <packaging>jar</packaging>
                        <version>${phpjavabridge.version}</version>
                    </configuration>
                </execution>
            </executions>
        </plugin>
    </plugins>
    <properties>
        <phpjavabridge.version>6.1.2.1</phpjavabridge.version>
    </properties>


versions:set 

Existe una plugin en Maven para aumentar la versión en todos los módulos de un proyecto multimódulo. Estas son las llamadas que utilizo:

mvn versions:set -DnewVersion=1.2
mvn versions:commit

domingo, 23 de mayo de 2010

Una pala Galasport me ha durado menos de 5 meses

En este blog le quiero hacer un hueco también al Kayak-polo, un deporte de equipo con balón en el que los jugadores van montados en kayak. En esta ocasión inaugural para quejarme de que se me ha roto la pértiga de mi pala Galasport Contact tras usarla desde febrero, y no intensivamente. La rotura se produjo cuando recibí un golpe de balón en el centro de la pértiga. Se me han roto ya muchas palas jugando a esto, pero siempre habían durado más de un año, incluso cuando jugaba con mayor frecuencia. Aquí pongo un par de fotos del resultado:



Jardín exótico de la Universidad de Hohenheim

La universidad de Hohenheim, en Stuttgart, tiene un jardín inglés con numerosas plantas exóticas. Este jardín pertenece realmente al palacio de Hohenheim.


¡Hay plantas muy raras en este sitio!

sábado, 22 de mayo de 2010

Kulinarischer Weinweg en Kernen-Stetten

Del 22 al 24 de mayo se celebra en Kernen-Stetten el 'Kulinarischer Weinweg' ('Camino culinario del vino', digamos), en el que se mezcla el andar un poquito por los viñedos alrededor del castillo Yburg y el tomarse un vino y alguna cosilla de comer.

Foto: Los viñedos y una de las zonas de venta de vino y viandas.

Foto: El castillo Yburg

En el siguiente link hay más fotos de la edición del 2005, para hacerse una idea de qué va el tema: http://www.weinweg.de/Sites/BilderKW05.htm.

viernes, 21 de mayo de 2010

Cómo eliminar los caracteres ^M en vi

Hoy me ha vuelto a pasar que varios ficheros de configuración de mi aplicación web que acababa de subir al servidor Linux desde Windows tenían todas las líneas acabadas en un carácter representado como ^M. Posiblemente retorno de carro o nueva línea, nunca me acuerdo de cual. Google me ha dirigido rápidamente a tropecientos sitios con la solución que buscaba. Lo que he hecho es escribir el comando ':%s/^M//g' en VI. Con esto desaparecerán. Para escribir la ^M correctamente hay que pulsar primero ctrl+V y luego ctrl+M.


Via: http://www.tech-recipes.com/rx/150/remove-m-characters-at-end-of-lines-in-vi/ 

Y aquí hay una serie de posibles soluciones al mismo problema:http://www.computing.net/answers/unix/remove-m-from-file/6031.html

Stadtmauerrundgang

Como no tengo nada que contar, aquí dejo una foto hecha hace tiempo en la muralla de Waiblingen

Primer Post de Potoblof

Este es el primer, y hasta ahora último post en Potoblof.



Foto: La Selva No Tan Negra (Y no tan selva)