2014-04-24 9 views

risposta

21

ho trovato la seguente configurazione sourceSet per risolvere il problema:

sourceSets { 
    main { 
     scala { 
      srcDirs = ['src/main/scala', 'src/main/java'] 
     } 
     java { 
      srcDirs = [] 
     } 
} 

Questo perché il set fonte scala può includere sia java e fonti Scala.

+4

Se si desidera mantenere le origini Java e Scala in directory separate e si desidera che tutto il codice sia compilato in comune, questa è la soluzione corretta. Un'alternativa è quella di mantenere la configurazione di default e mettere il codice Java compilato in "src/main/scala', e il codice Java rimanente (se presente) in' src/main/java'. –

+0

Grazie. Ci chiediamo se il codice Java compilato con compileScala si comporti diversamente da quando compilato con compileJava. Supponiamo che usino lo stesso compilatore, quindi producano lo stesso bytecode sottostante, ma consentono il collegamento a scala sorgente. È corretto? – crizCraig

+1

La compilazione comune è controllata dal compilatore Scala, che è responsabile del richiamo del compilatore Java in questo caso. Il risultato dovrebbe essere generalmente lo stesso. Nota che dovrai configurare 'compileScala.options' piuttosto che' compileJava.options' per influenzare le opzioni di compilazione Java del codice Java compilato congiuntamente. (Le opzioni di compilazione di Scala sono controllate tramite 'compileScala.scalaCompileOptions'.) Probabilmente vorrai applicare qualsiasi configurazione di questo tipo a tutte le attività di compilazione (ad esempio' tasks.withType (ScalaCompile) {options ...} '). –

0

Se il codice java utilizza alcune librerie esterne come Lombok, l'uso del compilatore di scala per costruire la classe java avrà esito negativo, poiché il compilatore di scala non conosce le annotazioni.

La mia soluzione è di cambiare le dipendenze delle attività, effettuare la compilazione di Scala prima di Java.

tasks.compileJava.dependsOn compileScala 
tasks.compileScala.dependsOn.remove("compileJava") 

Ora il compito compileScala viene eseguito prima di compileJava, il gioco è fatto.

Se il codice Java dipende dal codice Scala, è necessario fare altri due passi,

  1. separata la cartella di output di Scala e Java,

    sourceSets { 
        main { 
         scala { 
          outputDir = file("$buildDir/classes/scala/main") 
         } 
         java { 
          outputDir = file("$buildDir/classes/java/main") 
         } 
        } 
    
  2. Aggiungere l'output Scala come una dipendenza per compileJava,

    dependencies { 
        compile files("$sourceSets.main.scala.outputDir") 
    } 
    
Problemi correlati