I was trying this piece of code:
// Get the Docker Configurations
def dockerConfForModule(moduleName: String): Dockerfile = {
val jarFile: File = (Compile / packageBin / sbt.Keys.`package`).value
val classpath = (Compile / managedClasspath).value
val mainclass = (Compile / packageBin / mainClass).value.getOrElse(sys.error("Expected exactly one main class"))
val jarTarget = s"/app/${jarFile.getName}"
// Make a colon separated classpath with the JAR file
val classpathString = classpath.files.map("/app/" + _.getName)
.mkString(":") + ":" + jarTarget
new Dockerfile {
// Base image
from("openjdk:8-jre")
// Add all files on the classpath
add(classpath.files, "/app/")
// Add the JAR file
add(jarFile, jarTarget)
// On launch run Java with the classpath and the main class
entryPoint("java", "-cp", classpathString, mainclass)
}
}
Which I'm calling as a function in one of my module like below:
// Define Sub Modules and its settings
lazy val cleanse = (project in file(MODULE_NAME_CLEANSE)).dependsOn(core)
.settings(
commonSettings,
enablingCoverageSettings,
name := MODULE_NAME_CLEANSE,
description := "Clean the incoming data for training purposes",
docker / dockerfile := dockerConfForModule(MODULE_NAME_CLEANSE)
)
.enablePlugins(DockerPlugin)
But this runs into an error:
/home/joesan/Projects/Private/ml-projects/housing-price-prediction-data-preparation/build.sbt:22: error: `value` can only be called on a task within a task definition macro, such as :=, +=, ++=, or Def.task.
val jarFile: File = (Compile / packageBin / sbt.Keys.`package`).value
^
/home/joesan/Projects/Private/ml-projects/housing-price-prediction-data-preparation/build.sbt:23: error: `value` can only be called on a task within a task definition macro, such as :=, +=, ++=, or Def.task.
val classpath = (Compile / managedClasspath).value
^
/home/joesan/Projects/Private/ml-projects/housing-price-prediction-data-preparation/build.sbt:24: error: `value` can only be called on a task within a task definition macro, such as :=, +=, ++=, or Def.task.
val mainclass = (Compile / packageBin / mainClass).value.getOrElse(sys.error("Expected exactly one main class"))
^
sbt.compiler.EvalException: Type error in expression
[error] sbt.compiler.EvalException: Type error in expression
[error] Use 'last' for the full log.
[warn] Project loading failed: (r)etry, (q)uit, (l)ast, or (i)gnore? (default: r)
What is wrong in what I'm trying?
Related
i need to add the base directory path to system property
lazy val bas = baseDirectory.value.getPath
initialize ~= { _ =>
System.setProperty( "report.path", bas+"/reports/l2report")
System.setProperty( "build-version", buildVersion)
}
build.sbt:111: error: `value` can only be used within a task or setting macro, such as :=, +=, ++=, Def.task, or Def.setting.
this error is coming build.sbt
I upgraded the sbt from sbt-0.13.16 to sbt-1.2.8 my following code is breaking
lazy val gruntDirectory = baseDirectory {
_ / "public"
}
unmanagedResourceDirectories in Assets += gruntDirectory { _ / "node_modules"}
here is the error i am getting
/build.sbt:131: error: No implicit for Append.Value[Seq[java.io.File], sbt.Def.Initialize[java.io.File]] found,
so sbt.Def.Initialize[java.io.File] cannot be appended to Seq[java.io.File]
unmanagedResourceDirectories in Assets += gruntDirectory { _ / "node_modules"}
^
[error] Type error in expression
Project loading failed: (r)etry, (q)uit, (l)ast, or (i)gnore?
how can i resolve this issue
You need to use .value to extract the value of a setting:
unmanagedResourceDirectories in Assets += baseDirectory.value / "public" / "node_modules"
If you want to define gruntDirectory for something else, you can do it like this:
lazy val gruntDirectory = Def.setting { baseDirectory.value / "public" }
unmanagedResourceDirectories in Assets += gruntDirectory.value / "node_modules"
Notice that you can use .value only on the right side of :=/+=/++=/~= assignments or inside Def.{setting, task, taskDyn, inputTask, inputTaskDyn}.
I am writing a SBT Auto Plugin. This is my build.sbt file
lazy val foo = (project in file(".")).settings(
name := "foo",
sbtPlugin := true,
organization := "com.foo",
crossScalaVersions = Seq("2.11.8", "2.12.4")
)
but I get the error
overloaded method value settings with alternatives:
(ss: sbt.Def.SettingsDefinition*)sbt.Project <and>
=> Seq[sbt.Def.Setting[_]]
cannot be applied to (sbt.Def.Setting[String], sbt.Def.Setting[Boolean], sbt.Def.Setting[String], crossScalaVersions: Seq[String])
lazy val foo = (project in file(".")).settings(
^
[error] sbt.compiler.EvalException: Type error in expression
[error] sbt.compiler.EvalException: Type error in expression
[error] Use 'last' for the full log.
Project loading failed: (r)etry, (q)uit, (l)ast, or (i
My objective is that when I do sbt publish I publish two jar files. one for scala 2.11 and other for scala 2.12
you have to give it like crossScalaVersions := Seq("2.11.8", "2.12.4") instead of crossScalaVersions = Seq("2.11.8", "2.12.4").
You can see more here Cross-Building a Project.
I am using xsbt-web-plugin with Sbt 0.13.2. If I add the following to build.sbt I can type "myTask" in the console and it works:
val myTask = taskKey[Unit]("My task.")
myTask := {
val (art, file) = packagedArtifact.in(Compile, packageWar).value
println("Artifact definition: " + art)
println("Packaged file: " + file.getAbsolutePath)
}
But why does this return an error if I type it in the Sbt console?
inspect compile:packageWar::packagedArtifact
Error message:
[error] Expected key
[error] Not a valid key: packageWar (similar: package, packageSrc, package-src)
[error] inspect compile:packageWar::packagedArtifact
[error] ^
For comparison, this one does work:
inspect compile:packageBin::packagedArtifact
Key parts of build.sbt:
tomcat()
name := "my-war"
scalaVersion := "2.10.4"
webappSrc in webapp := baseDirectory.value / "web"
webInfClasses in webapp := true
val myTask = taskKey[Unit]("My task.")
myTask := {
val (art, file) = packagedArtifact.in(Compile, packageWar).value
println("Artifact definition: " + art)
println("Packaged file: " + file.getAbsolutePath)
}
project/plugins.sbt:
addSbtPlugin("com.earldouglas" % "xsbt-web-plugin" % "1.0.0-M4")
(I'm only asking so that I can understand Sbt better, it's not actually causing a problem.)
You can get this info from package rather than packageWar:
> inspect compile:package::packagedArtifact
[info] Task: scala.Tuple2[sbt.Artifact, java.io.File]
[info] Description:
[info] Generates a packaged artifact, returning the Artifact and the produced File.
The packageWar task is set up indirectly using packageTaskSettings.
Is it possible to get the re-start (aka reStart) task to automatically run before I run the IntegrationTest target (it:test)?
I thought this would do it:
test <<= (test in IntegrationTest) dependsOn reStart
However, I'm getting this error:
build.sbt:54: error: not found: value reStart
test <<= (test in IntegrationTest) dependsOn reStart
^
[error] Type error in expression
By adding import Revolver._ I got a bit further, but it still fails. Now I get a more descriptive error, however:
build.sbt:55: error: type mismatch;
found : sbt.InputKey[spray.revolver.AppProcess]
required: sbt.Scoped.AnyInitTask
(which expands to) sbt.Def.Initialize[sbt.Task[T]] forSome { type T }
test in IntegrationTest <<= (test in IntegrationTest) dependsOn reStart
Is there a way to get around that?
You can define special TaskKey-typed task for that like this (working example):
lazy val reStart0 = TaskKey[AppProcess]("re-start-0")
lazy val emptyArgs = SettingKey[revolver.Actions.ExtraCmdLineOptions]("empty-args")
lazy val projectA = Project(
id = "hello-a",
base = file("./a"),
settings = Project.defaultSettings ++ Revolver.settings
).settings(
emptyArgs := revolver.Actions.ExtraCmdLineOptions(Nil, Nil),
reStart0 <<= {
(streams, Revolver.reLogTag, thisProjectRef, Revolver.reForkOptions, mainClass in Revolver.reStart, fullClasspath in Runtime, Revolver.reStartArgs, emptyArgs)
.map(revolver.Actions.restartApp)
.dependsOn(products in Compile)
}
)
lazy val projectB = Project(
id = "hello-b",
base = file("./b"),
settings = Project.defaultSettings ++ Revolver.settings ++ Defaults.itSettings)
.configs(IntegrationTest)
.settings(
test in (IntegrationTest) <<= (test in IntegrationTest).dependsOn(reStart0 in projectA)
)