aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--examples/dotty-example/README.md3
-rw-r--r--examples/dotty-example/build/build.scala2
-rw-r--r--examples/dotty-example/src/Main.scala11
-rw-r--r--stage1/Stage1Lib.scala16
-rw-r--r--stage2/plugins/Dotty.scala172
-rw-r--r--test/simple-fixed/build/build.scala1
-rw-r--r--test/simple/build/build.scala1
-rw-r--r--test/test.scala30
8 files changed, 220 insertions, 16 deletions
diff --git a/examples/dotty-example/README.md b/examples/dotty-example/README.md
new file mode 100644
index 0000000..bc0f6b0
--- /dev/null
+++ b/examples/dotty-example/README.md
@@ -0,0 +1,3 @@
+Dotty example project compiling hello world with the next version of Scala.
+
+All you need to do to enable Dotty is `extends Dotty` in your build.scala .
diff --git a/examples/dotty-example/build/build.scala b/examples/dotty-example/build/build.scala
new file mode 100644
index 0000000..eb67d93
--- /dev/null
+++ b/examples/dotty-example/build/build.scala
@@ -0,0 +1,2 @@
+import cbt._
+class Build(val context: Context) extends Dotty
diff --git a/examples/dotty-example/src/Main.scala b/examples/dotty-example/src/Main.scala
new file mode 100644
index 0000000..1963b51
--- /dev/null
+++ b/examples/dotty-example/src/Main.scala
@@ -0,0 +1,11 @@
+object Main extends Foo("Hello Dotty - trait parameters, yay"){
+ def main(args: Array[String]) = {
+ println(hello)
+
+ // Sanity check the classpath: this won't run if the dotty jar is not present.
+ val x: Int => Int = z => z
+ x(1)
+ }
+}
+
+trait Foo(val hello: String)
diff --git a/stage1/Stage1Lib.scala b/stage1/Stage1Lib.scala
index bbb6f7b..c427b77 100644
--- a/stage1/Stage1Lib.scala
+++ b/stage1/Stage1Lib.scala
@@ -101,13 +101,19 @@ class Stage1Lib( val logger: Logger ) extends BaseLib{
} else ExitCode.Success
}
- def runMain(cls: String, args: Seq[String], classLoader: ClassLoader ): ExitCode = {
+ def runMain( cls: String, args: Seq[String], classLoader: ClassLoader, fakeInstance: Boolean = false ): ExitCode = {
+ import java.lang.reflect.Modifier
logger.lib(s"Running $cls.main($args) with classLoader: " ++ classLoader.toString)
trapExitCode{
- classLoader
- .loadClass(cls)
- .getMethod( "main", classOf[Array[String]] )
- .invoke( null, args.toArray.asInstanceOf[AnyRef] )
+ val c = classLoader.loadClass(cls)
+ val m = c.getMethod( "main", classOf[Array[String]] )
+ val instance =
+ if(!fakeInstance) null else c.newInstance
+ assert(
+ fakeInstance || (m.getModifiers & java.lang.reflect.Modifier.STATIC) > 0,
+ "Cannot run non-static method " ++ cls+".main"
+ )
+ m.invoke( instance, args.toArray.asInstanceOf[AnyRef] )
ExitCode.Success
}
}
diff --git a/stage2/plugins/Dotty.scala b/stage2/plugins/Dotty.scala
new file mode 100644
index 0000000..50255d5
--- /dev/null
+++ b/stage2/plugins/Dotty.scala
@@ -0,0 +1,172 @@
+package cbt
+import java.io.File
+import java.net.URL
+import java.nio.file.Files
+import java.nio.file.attribute.FileTime
+
+trait Dotty extends BaseBuild{
+ def dottyVersion: String = "0.1-20160926-ec28ea1-NIGHTLY"
+ def dottyOptions: Seq[String] = Seq()
+ override def scalaTarget: File = target ++ s"/dotty-$dottyVersion"
+
+ private lazy val dottyLib = new DottyLib(
+ logger, context.cbtHasChanged, context.paths.mavenCache,
+ context.classLoaderCache, dottyVersion = dottyVersion
+ )
+
+ private object compileCache extends Cache[Option[File]]
+ override def compile: Option[File] = compileCache{
+ dottyLib.compile(
+ needsUpdate || context.parentBuild.map(_.needsUpdate).getOrElse(false),
+ sourceFiles, compileTarget, compileStatusFile, compileClasspath,
+ dottyOptions
+ )
+ }
+
+ def doc: ExitCode =
+ dottyLib.doc(
+ sourceFiles, compileClasspath, docTarget, dottyOptions
+ )
+
+ def repl = dottyLib.repl(context.args, classpath)
+
+ override def dependencies = Resolver(mavenCentral).bind(
+ ScalaDependency( "org.scala-lang.modules", "scala-java8-compat", "0.8.0-RC7" )
+ )
+}
+
+class DottyLib(
+ logger: Logger,
+ cbtHasChanged: Boolean,
+ mavenCache: File,
+ classLoaderCache: ClassLoaderCache,
+ dottyVersion: String
+){
+ val lib = new Lib(logger)
+ import lib._
+
+ private def Resolver(urls: URL*) = MavenResolver(cbtHasChanged, mavenCache, urls: _*)
+ private lazy val dottyDependency = Resolver(mavenCentral).bindOne(
+ MavenDependency("ch.epfl.lamp","dotty_2.11",dottyVersion)
+ )
+
+ def repl(args: Seq[String], classpath: ClassPath) = {
+ consoleOrFail("Use `cbt direct repl` instead")
+ lib.runMain(
+ "dotty.tools.dotc.repl.Main",
+ Seq(
+ "-bootclasspath",
+ dottyDependency.classpath.string,
+ "-classpath",
+ classpath.string
+ ) ++ args,
+ dottyDependency.classLoader(classLoaderCache)
+ )
+ }
+
+ def doc(
+ sourceFiles: Seq[File],
+ dependencyClasspath: ClassPath,
+ docTarget: File,
+ compileArgs: Seq[String]
+ ): ExitCode = {
+ if(sourceFiles.isEmpty){
+ ExitCode.Success
+ } else {
+ docTarget.mkdirs
+ val args = Seq(
+ // FIXME: can we use compiler dependency here?
+ "-bootclasspath", dottyDependency.classpath.string, // FIXME: does this break for builds that don't have scalac dependencies?
+ "-classpath", dependencyClasspath.string, // FIXME: does this break for builds that don't have scalac dependencies?
+ "-d", docTarget.toString
+ ) ++ compileArgs ++ sourceFiles.map(_.toString)
+ logger.lib("creating docs for source files "+args.mkString(", "))
+ val exitCode = redirectOutToErr{
+ runMain(
+ "dotty.tools.dottydoc.api.java.Dottydoc",
+ args,
+ dottyDependency.classLoader(classLoaderCache),
+ fakeInstance = true // this is a hack as Dottydoc's main method is not static
+ )
+ }
+ System.err.println("done")
+ exitCode
+ }
+ }
+
+ def compile(
+ needsRecompile: Boolean,
+ files: Seq[File],
+ compileTarget: File,
+ statusFile: File,
+ classpath: ClassPath,
+ dottyOptions: Seq[String]
+ ): Option[File] = {
+
+ if(classpath.files.isEmpty)
+ throw new Exception("Trying to compile with empty classpath. Source files: " ++ files.toString)
+
+ if( files.isEmpty ){
+ None
+ }else{
+ if( needsRecompile ){
+ val start = System.currentTimeMillis
+
+ val _class = "dotty.tools.dotc.Main"
+ val dualArgs =
+ Seq(
+ "-d", compileTarget.toString
+ )
+ val singleArgs = dottyOptions.map( "-S" ++ _ )
+
+ val code =
+ try{
+ System.err.println("Compiling with Dotty to " ++ compileTarget.toString)
+ compileTarget.mkdirs
+ redirectOutToErr{
+ lib.runMain(
+ _class,
+ dualArgs ++ singleArgs ++ Seq(
+ "-bootclasspath", dottyDependency.classpath.string, // let's put cp last. It so long
+ "-classpath", classpath.string // let's put cp last. It so long
+ ) ++ files.map(_.toString),
+ dottyDependency.classLoader(classLoaderCache)
+ )
+ }
+ } catch {
+ case e: Exception =>
+ System.err.println(red("Dotty crashed. See https://github.com/lampepfl/dotty/issues. To reproduce run:"))
+ System.out.println(s"""
+java -cp \\
+${dottyDependency.classpath.strings.mkString(":\\\n")} \\
+\\
+${_class} \\
+\\
+${dualArgs.grouped(2).map(_.mkString(" ")).mkString(" \\\n")} \\
+\\
+${singleArgs.mkString(" \\\n")} \\
+\\
+-bootclasspath \\
+${dottyDependency.classpath.strings.mkString(":\\\n")} \\
+-classpath \\
+${classpath.strings.mkString(":\\\n")} \\
+\\
+${files.sorted.mkString(" \\\n")}
+"""
+ )
+ ExitCode.Failure
+ }
+
+ if(code == ExitCode.Success){
+ // write version and when last compilation started so we can trigger
+ // recompile if cbt version changed or newer source files are seen
+ write(statusFile, "")//cbtVersion.getBytes)
+ Files.setLastModifiedTime(statusFile.toPath, FileTime.fromMillis(start) )
+ } else {
+ System.exit(code.integer) // FIXME: let's find a better solution for error handling. Maybe a monad after all.
+ }
+ }
+ Some( compileTarget )
+ }
+ }
+}
diff --git a/test/simple-fixed/build/build.scala b/test/simple-fixed/build/build.scala
index 3f1ff66..42130ee 100644
--- a/test/simple-fixed/build/build.scala
+++ b/test/simple-fixed/build/build.scala
@@ -24,7 +24,6 @@ class Build(context: cbt.Context) extends BasicBuild(context){
sonatypeSnapshots
).bind(
"org.cvogt" %% "play-json-extensions" % "0.8.0",
- "org.tpolecat" %% "tut-core" % "0.4.2",
"ai.x" %% "lens" % "1.0.0"
)
)
diff --git a/test/simple/build/build.scala b/test/simple/build/build.scala
index b75d262..affe7f6 100644
--- a/test/simple/build/build.scala
+++ b/test/simple/build/build.scala
@@ -35,7 +35,6 @@ class Build(val context: cbt.Context) extends BaseBuild{
sonatypeSnapshots
).bind(
"org.cvogt" %% "play-json-extensions" % "0.8.0",
- "org.tpolecat" %% "tut-core" % "0.4.2",
"ai.x" %% "lens" % "1.0.0"
)
)
diff --git a/test/test.scala b/test/test.scala
index 4f0afcd..dfc35d0 100644
--- a/test/test.scala
+++ b/test/test.scala
@@ -147,20 +147,25 @@ object Main{
}
(
- Dependencies(
- Resolver( mavenCentral, bintray("tpolecat") ).bind(
- lib.ScalaDependency("org.tpolecat","tut-core","0.4.2", scalaMajorVersion="2.11")
- )
- ).classpath.strings
- ++
+ (
+ if(System.getenv("CIRCLECI") == null){
+ // tenporarily disable on circleci as it seems to have trouble reliably
+ // downloading from bintray
+ Dependencies(
+ Resolver( bintray("tpolecat") ).bind(
+ lib.ScalaDependency("org.tpolecat","tut-core","0.4.2", scalaMajorVersion="2.11")
+ )
+ ).classpath.strings
+ } else Nil
+ ) ++
Dependencies(
- Resolver(sonatypeReleases).bind(
- MavenDependency("org.cvogt","play-json-extensions_2.11","0.8.0")
+ Resolver( sonatypeReleases ).bind(
+ MavenDependency("org.cvogt","scala-extensions_2.11","0.5.1")
)
).classpath.strings
++
Dependencies(
- Resolver( mavenCentral, sonatypeSnapshots ).bind(
+ Resolver( mavenCentral ).bind(
MavenDependency("ai.x","lens_2.11","1.0.0")
)
).classpath.strings
@@ -193,6 +198,13 @@ object Main{
compile("../examples/scalajs-react-example/js")
compile("../examples/scalajs-react-example/jvm")
compile("../examples/multi-project-example")
+ if(sys.props("java.version").startsWith("1.7")){
+ System.err.println("\nskipping dotty tests on Java 7")
+ } else {
+ compile("../examples/dotty-example")
+ task("run","../examples/dotty-example")
+ task("doc","../examples/dotty-example")
+ }
task("fastOptJS","../examples/scalajs-react-example/js")
task("fullOptJS","../examples/scalajs-react-example/js")
compile("../examples/uber-jar-example")