diff --git a/stage2/BuildBuild.scala b/stage2/BuildBuild.scala index 5a311396..525f6c65 100644 --- a/stage2/BuildBuild.scala +++ b/stage2/BuildBuild.scala @@ -1,4 +1,5 @@ package cbt +import java.io.File import java.nio.file._ trait BuildBuild extends BaseBuild{ @@ -20,55 +21,27 @@ trait BuildBuild extends BaseBuild{ override def dependencies = super.dependencies :+ context.cbtDependency - def managedBuildDirectory: java.io.File = lib.realpath( projectDirectory.parent ) + def managedBuildDirectory: File = lib.realpath( projectDirectory.parent ) private object managedBuildCache extends Cache[BuildInterface] def managedBuild = managedBuildCache{ val managedBuildFile = projectDirectory++"/Build.scala" logger.composition("Loading build at "++managedContext.projectDirectory.toString) - val build = ( - if(managedBuildFile.exists){ - val contents = new String(Files.readAllBytes(managedBuildFile.toPath)) - val cbtUrl = ("cbt:"++GitDependency.GitUrl.regex++"#[a-z0-9A-Z]+").r - cbtUrl - .findFirstIn(contents) - .flatMap{ - url => - val Array(base,hash) = url.drop(4).split("#") - if(context.cbtHome.string.contains(hash)) - None - else Some{ - // Note: cbt can't use an old version of itself for building, - // otherwise we'd have to recursively build all versions since - // the beginning. Instead CBT always needs to build the pure Java - // Launcher in the checkout with itself and then run it via reflection. - val dep = new GitDependency(base, hash, Some("nailgun_launcher")) - val ctx = managedContext.copy( cbtHome = dep.checkout ) - dep.classLoader(classLoaderCache) - .loadClass( "cbt.NailgunLauncher" ) - .getMethod( "getBuild", classOf[AnyRef] ) - .invoke( null, ctx ) - } - }.getOrElse{ - try{ - classLoader(context.classLoaderCache) - .loadClass(lib.buildClassName) - .getConstructors.head - .newInstance(managedContext) - } catch { - case e: ClassNotFoundException if e.getMessage == lib.buildClassName => - throw new Exception("You need to define a class Build in Build.scala in: "+context.projectDirectory) - } - } - } else if( projectDirectory.listFiles.exists( _.getName.endsWith(".scala") ) ){ - throw new Exception( - "No file Build.scala (upper case) found in " ++ projectDirectory.getPath - ) - } else if( projectDirectory.getParentFile.getName == "build" ){ - new BasicBuild( managedContext ) with BuildBuild + val build = if (managedBuildFile.exists) { + managedBuildFrom(managedBuildFile) + } else if (projectDirectory.listFiles.exists(_.getName.endsWith(".scala"))) { + System.err.println("No file Build.scala (upper case) found in " ++ projectDirectory.getPath) + val backupBuildFile = projectDirectory ++ "/build.scala" + if (backupBuildFile.exists) { + System.err.println("Trying build.scala in " ++ projectDirectory.getPath) + managedBuildFrom(backupBuildFile) } else { - new BasicBuild( managedContext ) + throw new Exception("No file Build.scala (upper case) found in " ++ projectDirectory.getPath) } - ) + } else if (projectDirectory.getParentFile.getName == "build") { + new BasicBuild(managedContext) with BuildBuild + } else { + new BasicBuild(managedContext) + } try{ build.asInstanceOf[BuildInterface] } catch { @@ -76,6 +49,42 @@ trait BuildBuild extends BaseBuild{ throw new Exception("Your Build class needs to extend BaseBuild in: "+context.projectDirectory, e) } } + + private def managedBuildFrom(file: File): BuildInterface = { + val contents = new String(Files.readAllBytes(file.toPath)) + val cbtUrl = ("cbt:" ++ GitDependency.GitUrl.regex ++ "#[a-z0-9A-Z]+").r + cbtUrl + .findFirstIn(contents) + .flatMap { url => + val Array(base, hash) = url.drop(4).split("#") + if (context.cbtHome.string.contains(hash)) + None + else Some { + // Note: cbt can't use an old version of itself for building, + // otherwise we'd have to recursively build all versions since + // the beginning. Instead CBT always needs to build the pure Java + // Launcher in the checkout with itself and then run it via reflection. + val dep = new GitDependency(base, hash, Some("nailgun_launcher")) + val ctx = managedContext.copy(cbtHome = dep.checkout) + dep.classLoader(classLoaderCache) + .loadClass("cbt.NailgunLauncher") + .getMethod("getBuild", classOf[AnyRef]) + .invoke(null, ctx) + .asInstanceOf[BuildInterface] + } + } getOrElse { + try + classLoader(context.classLoaderCache) + .loadClass(lib.buildClassName) + .getConstructors.head + .newInstance(managedContext) + catch { + case e: ClassNotFoundException if e.getMessage == lib.buildClassName => + throw new Exception("You need to define a class Build in Build.scala in: " + context.projectDirectory) + } + }.asInstanceOf[BuildInterface] + } + override def triggerLoopFiles = super.triggerLoopFiles ++ managedBuild.triggerLoopFiles override def finalBuild: BuildInterface = if( context.projectDirectory == context.cwd ) this else managedBuild.finalBuild }