2016-01-27 40 views
5

Sto usando il framework Spock per il test (versione 1.0-groovy-2.4). Junit offre questo option per eseguire un test specifico utilizzando la riga di comando (con Maven):Eseguire un test specifico in una singola classe di test con Spock and Maven

mvn -Dtest=TestCircle#mytest test 

Domanda: Come posso fare questo con Spock?

Questa versione ha una dipendenza Junit 4,12, si afferma nella documentazione Junit che questa funzione è supportata solo per Junit 4.x, fondamentalmente Spock deve proporre qualcosa di simile.

risposta

7

Dopo ulteriori indagini, la risposta è molto probabilmente: No, non è possibile richiamare metodi di prova specifici con Spock utilizzando tale funzione infallibile Plugin. Di seguito il motivo.

Dato il seguente test case Spock:

import spock.lang.Specification 

class HelloSpec extends Specification { 

    def hello = new Main(); 

    def sayHello() { 
     given: "A person's name is given as a method parameter." 
     def greeting = hello.sayHello("Petri"); 

     expect: "Should say hello to the person whose name is given as a method parameter" 
     greeting == "Hello Petri"; 

     println "hello from HelloSpec" 
    } 
} 

E data la seguente configurazione plug-in:

<plugin> 
    <groupId>org.codehaus.gmavenplus</groupId> 
    <artifactId>gmavenplus-plugin</artifactId> 
    <version>1.5</version> 
    <executions> 
     <execution> 
      <goals> 
       <goal>addTestSources</goal> 
       <goal>testCompile</goal> 
      </goals> 
     </execution> 
    </executions> 
    <configuration> 
     <sources> 
      <fileset> 
       <directory>${pom.basedir}/src/test/java</directory> 
       <includes> 
        <include>**/*.groovy</include> 
       </includes> 
      </fileset> 
     </sources> 
    </configuration> 
</plugin> 

<plugin> 
    <groupId>org.apache.maven.plugins</groupId> 
    <artifactId>maven-surefire-plugin</artifactId> 
    <version>2.18.1</version> 
    <configuration> 
     <includes> 
      <include>**/*Test.java</include> 
      <include>**/*Spec.java</include> 
     </includes> 
    </configuration> 
</plugin> 

funziona benissimo come parte del Maven test fase di esecuzione mvn clean test:

------------------------------------------------------- 
T E S T S 
------------------------------------------------------- 
Running com.sample.HelloSpec 
hello from HelloSpec 
Tests run: 1, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.314 sec - in com.sample.HelloSpec 

Anche in esecuzione mvn clean test -Dtest=HelloSpec ottieni esattamente lo stesso risultato di sopra, con successo.

Quindi, perché non è possibile eseguire un unico metodo?

Se eseguiamo il comando javap sul test del campione HelloSpec sopra otteniamo il seguente risultato:

Compiled from "HelloSpec.groovy" 
public class com.sample.HelloSpec extends spock.lang.Specification implements groovy.lang.GroovyObject { 
    public static transient boolean __$stMC; 
    public com.sample.HelloSpec(); 
    public void $spock_feature_0_0(); 
    protected groovy.lang.MetaClass $getStaticMetaClass(); 
    public groovy.lang.MetaClass getMetaClass(); 
    public void setMetaClass(groovy.lang.MetaClass); 
    public java.lang.Object invokeMethod(java.lang.String, java.lang.Object); 
    public java.lang.Object getProperty(java.lang.String); 
    public void setProperty(java.lang.String, java.lang.Object); 
    public java.lang.Object getHello(); 
    public void setHello(java.lang.Object); 
} 

Quindi, nel bytecode generato non esiste un metodo sayHello, perché Spock cambia nome metodi al fine di consentire spazi in loro. Quindi il nome del metodo che scrivi non è mai il vero nome del metodo come parte della classe compilata.

In questo caso, il nome del metodo è molto probabilmente $spock_feature_0_0, non qualcosa di veramente amichevole.

Questo è confermato anche in this answer e nei commenti di Peter Niederwieser, autore di Spock in realtà, quindi una fonte più affidabile.

Si potrebbe provare a eseguire le seguenti operazioni:

mvn clean test -Dtest=HelloSpec#*spock* 

che dovrebbe infatti corrispondere al vero nome del metodo, ma si sarebbe comunque un errore

------------------------------------------------------- 
T E S T S 
------------------------------------------------------- 
Running com.sample.HelloSpec 
Tests run: 1, Failures: 0, Errors: 1, Skipped: 0, Time elapsed: 0.007 sec <<< FAILURE! - in com.sample.HelloSpec 
initializationError(org.junit.runner.manipulation.Filter) Time elapsed: 0.006 sec <<< ERROR! 
java.lang.Exception: No tests found matching Method $spock_feature_0_0(com.sample.HelloSpec) from [email protected] 
    at org.junit.internal.requests.FilterRequest.getRunner(FilterRequest.java:35) 
    at org.apache.maven.surefire.junit4.JUnit4Provider.execute(JUnit4Provider.java:275) 
    at org.apache.maven.surefire.junit4.JUnit4Provider.executeWithRerun(JUnit4Provider.java:173) 
    at org.apache.maven.surefire.junit4.JUnit4Provider.executeTestSet(JUnit4Provider.java:149) 
    at org.apache.maven.surefire.junit4.JUnit4Provider.invoke(JUnit4Provider.java:128) 
    at org.apache.maven.surefire.booter.ForkedBooter.invokeProviderInSameClassLoader(ForkedBooter.java:203) 
    at org.apache.maven.surefire.booter.ForkedBooter.runSuitesInProcess(ForkedBooter.java:155) 
    at org.apache.maven.surefire.booter.ForkedBooter.main(ForkedBooter.java:103) 

Results : 

Tests in error: 
    Filter.initializationError » No tests found matching Method $spock_feature_0_... 

Tests run: 1, Failures: 0, Errors: 1, Skipped: 0  

Questo è probabilmente perché con l'invocazione diretta nome stiamo bypassando la colla tra JUnit e Spock e come tale l'esecuzione fallisce.

+0

Buona prova. Qui Spock sta pagando caro per le simpatiche convenzioni sui nomi che supporta. –

5

io uso:

Windows: mvn -Dtest="TestCircle#my test" test 
*Nix: mvn "-Dtest=TestCircle#my test" test 

Funziona perfettamente con infallibile 2.19.1 e JUnit 4.8.1. Il seguente è l'esempio di codice e l'output di esecuzione:

import spock.lang.Specification 

class HelloSpec extends Specification { 
    def sayHello() { 
     given: "A person's name is given as a method parameter." 
     def greeting = "Hello Petri"; 


     expect: "Should say hello to the person whose name is given as a method parameter" 
     greeting == "Hello Petri"; 

     println "hello from HelloSpec" 
    } 

    def sayHi() { 
     expect: 
     1==1 

     println "sayHi from HelloSpec" 

    } 

    def "say hi to spock"() { 
     expect: 
     true 
     println "say hi to spock from HelloSpec" 

    } 
} 

# mvn test "-Dtest = HelloSpeC# salutare Spock"

[INFO] Scanning for projects...                     
[INFO]                           
[INFO] ------------------------------------------------------------------------         
[INFO] Building Auto Test 1                    
[INFO] ------------------------------------------------------------------------         
[INFO]                           
[INFO] --- maven-resources-plugin:2.6:resources (default-resources) @ auto-test ---      
[INFO] Using 'UTF-8' encoding to copy filtered resources.               
[INFO] Copying 5 resources                      
[INFO]                           
[INFO] --- maven-compiler-plugin:2.5.1:compile (default-compile) @ auto-test ---       
[INFO] No sources to compile                      
[INFO]                           
[INFO] --- maven-resources-plugin:2.6:testResources (default-testResources) @ auto-test ---    
[INFO] Using 'UTF-8' encoding to copy filtered resources.               
[INFO] Copying 122 resources                      
[INFO]                           
[INFO] --- maven-compiler-plugin:2.5.1:testCompile (default-testCompile) @ auto-test ---     
[INFO] No sources to compile                      
[INFO]                           
[INFO] --- gmaven-plugin:1.4:testCompile (compile-test) @ auto-test ---         
[INFO] Compiled 42 Groovy classes                     
[INFO]                           
[INFO] --- maven-surefire-plugin:2.19.1:test (default-test) @ auto-test ---        

------------------------------------------------------- 
T E S T S            
------------------------------------------------------- 
Running HelloSpec          
say hi to spock from HelloSpec       
Tests run: 1, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.558 sec - in HelloSpec 

Results : 

Tests run: 1, Failures: 0, Errors: 0, Skipped: 0 

[INFO] ------------------------------------------------------------------------ 
[INFO] BUILD SUCCESS               
[INFO] ------------------------------------------------------------------------ 
[INFO] Total time: 17.169s              
[INFO] Finished at: Fri Jul 01 14:19:20 CST 2016        
[INFO] Final Memory: 31M/736M             
[INFO] ------------------------------------------------------------------------ 

# prova mvn "-Dtest = HelloSpeC# sayHi "

[INFO] Scanning for projects...                   
[INFO]                         
[INFO] ------------------------------------------------------------------------       
[INFO] Building Auto Test 1                  
[INFO] ------------------------------------------------------------------------       
[INFO]                         
[INFO] --- maven-resources-plugin:2.6:resources (default-resources) @ auto-test ---    
[INFO] Using 'UTF-8' encoding to copy filtered resources.            
[INFO] Copying 5 resources                    
[INFO]                         
[INFO] --- maven-compiler-plugin:2.5.1:compile (default-compile) @ auto-test ---    
[INFO] No sources to compile                   
[INFO]                         
[INFO] --- maven-resources-plugin:2.6:testResources (default-testResources) @ auto-test ---  
[INFO] Using 'UTF-8' encoding to copy filtered resources.            
[INFO] Copying 122 resources                   
[INFO]                         
[INFO] --- maven-compiler-plugin:2.5.1:testCompile (default-testCompile) @ auto-test ---  
[INFO] No sources to compile                   
[INFO]                         
[INFO] --- gmaven-plugin:1.4:testCompile (compile-test) @ auto-test ---       
[INFO] Compiled 42 Groovy classes                  
[INFO]                         
[INFO] --- maven-surefire-plugin:2.19.1:test (default-test) @ auto-test ---      

------------------------------------------------------- 
T E S T S            
------------------------------------------------------- 
Running HelloSpec          
sayHi from HelloSpec         
Tests run: 1, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.539 sec - in HelloSpec 

Results : 

Tests run: 1, Failures: 0, Errors: 0, Skipped: 0 

[INFO] ------------------------------------------------------------------------ 
[INFO] BUILD SUCCESS               
[INFO] ------------------------------------------------------------------------ 
[INFO] Total time: 12.187s              
[INFO] Finished at: Fri Jul 01 14:19:49 CST 2016        
[INFO] Final Memory: 31M/736M             
[INFO] ------------------------------------------------------------------------ 

# prova mvn" -Dtest = HelloSpe C# sayHello"

[INFO] Scanning for projects...                   
[INFO]                          
[INFO] ------------------------------------------------------------------------       
[INFO] Building Auto Test 1                  
[INFO] ------------------------------------------------------------------------ 
[INFO] 
[INFO] --- maven-resources-plugin:2.6:resources (default-resources) @ auto-test --- 
[INFO] Using 'UTF-8' encoding to copy filtered resources. 
[INFO] Copying 5 resources 
[INFO] 
[INFO] --- maven-compiler-plugin:2.5.1:compile (default-compile) @ auto-test --- 
[INFO] No sources to compile 
[INFO] 
[INFO] --- maven-resources-plugin:2.6:testResources (default-testResources) @ auto-test --- 
[INFO] Using 'UTF-8' encoding to copy filtered resources. 
[INFO] Copying 122 resources 
[INFO] 
[INFO] --- maven-compiler-plugin:2.5.1:testCompile (default-testCompile) @ auto-test --- 
[INFO] No sources to compile 
[INFO] 
[INFO] --- gmaven-plugin:1.4:testCompile (compile-test) @ auto-test --- 
[INFO] Compiled 42 Groovy classes 
[INFO] 
[INFO] --- maven-surefire-plugin:2.19.1:test (default-test) @ auto-test --- 

------------------------------------------------------- 
T E S T S 
------------------------------------------------------- 
Running HelloSpec 
hello from HelloSpec 
Tests run: 1, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.515 sec - in HelloSpec 

Results : 

Tests run: 1, Failures: 0, Errors: 0, Skipped: 0 

[INFO] ------------------------------------------------------------------------ 
[INFO] BUILD SUCCESS 
[INFO] ------------------------------------------------------------------------ 
[INFO] Total time: 11.170s 
[INFO] Finished at: Fri Jul 01 14:20:14 CST 2016 
[INFO] Final Memory: 31M/736M 
[INFO] ------------------------------------------------------------------------ 

Spero che questo aiuto.

+0

Fresco. Questo sembra smentire l'altra risposta che sosteneva che era impossibile. – MarkHu

+0

Mi chiedo se potessi farlo anche da Gradle. – MarkHu

+1

I miei test hanno utilizzato la versione '2.18.1' del' maven-surefire-plugin', le versioni più recenti ['2.19'] (https://issues.apache.org/jira/browse/SUREFIRE-745?jql=project% 20% 3D% 20SUREFIRE% 20AND% 20fixVersion% 20% 3D% 202.19% 20ORDER% 20BY% 20updated% 20DESC% 2C% 20priority% 20DESC% 2C% 20created% 20ASC) e ['2.19.1'] (https: // issues .apache.org/jira/browse/SUREFIRE-1185? JQL = progetto% 20% 3D% 20SUREFIRE% 20and% 20fixVersion% 20% 3D% 202.19.1% 20ORDER% 20BY% 20updated% 20DESC% 2C% 20priority% 20DESC% 2C % 20creato% 20ASC) apparentemente risolto diversi problemi sulla proprietà '-Dtest' che potrebbe spiegare perché ha funzionato per voi in' 2.19.1'. –