Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

addPluginSbtFile command #4211

Merged
merged 1 commit into from Jun 19, 2018
Merged
Changes from all commits
Commits
File filter...
Filter file types
Jump to…
Jump to file or symbol
Failed to load files and symbols.
+96 −11
Diff settings

Always

Just for now

@@ -83,7 +83,8 @@ $HelpCommand <regular expression>
List("-" + elem, "--" + elem)
}
(s.startsWith(EarlyCommand + "(") && s.endsWith(")")) ||
(levelOptions contains s)
(levelOptions contains s) ||
(s.startsWith("-" + AddPluginSbtFileCommand) || s.startsWith("--" + AddPluginSbtFileCommand))
}

val EarlyCommand = "early"
@@ -96,6 +97,14 @@ $HelpCommand <regular expression>
The order is preserved between all early commands, so `sbt "early(a)" "early(b)"` executes `a` and `b` in order.
"""

def addPluginSbtFileHelp = {
val brief =
(s"--$AddPluginSbtFileCommand=<file>", "Adds the given *.sbt file to the plugin build.")

This comment has been minimized.

Copy link
@nafg

nafg Jun 19, 2018

aren't most options with a single dash (at least in the help)?

This comment has been minimized.

Copy link
@eed3si9n

eed3si9n Jun 20, 2018

Author Member

The single line convention comes from Java, and since Java 9 is updating to more UNIX -- style, I am following the cargo cult.

Help(brief)
}

val AddPluginSbtFileCommand = "addPluginSbtFile"

def ReadCommand = "<"
def ReadFiles = " file1 file2 ..."
def ReadDetailed =
@@ -66,15 +66,42 @@ object BasicCommands {
private[this] def levelParser: Parser[String] =
Iterator(Level.Debug, Level.Info, Level.Warn, Level.Error) map (l => token(l.toString)) reduce (_ | _)

private[this] def addPluginSbtFileParser: Parser[File] = {
token(AddPluginSbtFileCommand) ~> (":" | "=" | Space) ~> (StringBasic).examples(
"/some/extra.sbt"
) map {
new File(_)
}
}

private[this] def addPluginSbtFileStringParser: Parser[String] = {
token(
token(AddPluginSbtFileCommand) ~ (":" | "=" | Space) ~ (StringBasic)
.examples("/some/extra.sbt") map {
case s1 ~ s2 ~ s3 => s1 + s2 + s3
}
)
}

private[this] def earlyParser: State => Parser[String] = (s: State) => {
val p1 = token(EarlyCommand + "(") flatMap (_ => otherCommandParser(s) <~ token(")"))
val p2 = token("-") flatMap (_ => levelParser)
val p3 = token("--") flatMap (_ => levelParser)
val p2 = (token("-") | token("--")) flatMap (_ => levelParser)
val p3 = (token("-") | token("--")) flatMap (_ => addPluginSbtFileStringParser)
p1 | p2 | p3
}

private[this] def earlyHelp = Help(EarlyCommand, EarlyCommandBrief, EarlyCommandDetailed)

/**
* Adds additional *.sbt to the plugin build.
* This must be combined with early command as: --addPluginSbtFile=/tmp/extra.sbt
*/
def addPluginSbtFile: Command = Command.arb(_ => addPluginSbtFileParser, addPluginSbtFileHelp) {
(s, extraSbtFile) =>
val extraFiles = s.get(BasicKeys.extraMetaSbtFiles).toList.flatten
s.put(BasicKeys.extraMetaSbtFiles, extraFiles :+ extraSbtFile)
}

def help: Command = Command.make(HelpCommand, helpBrief, helpDetailed)(helpParser)

def helpParser(s: State): Parser[() => State] = {
@@ -20,6 +20,13 @@ object BasicKeys {
"The location where command line history is persisted.",
40
)

val extraMetaSbtFiles = AttributeKey[Seq[File]](
"extraMetaSbtFile",
"Additional plugin.sbt files.",
10000
)

val shellPrompt = AttributeKey[State => String](
"shell-prompt",
"The function that constructs the command prompt from the current build state.",
@@ -216,6 +216,7 @@ object BuiltinCommands {
setLogLevel,
plugin,
plugins,
addPluginSbtFile,
writeSbtVersion,
notifyUsersAboutShell,
shell,
@@ -714,7 +714,8 @@ private[sbt] object Load {
createRoot,
uri,
config.pluginManagement.context,
Nil
Nil,
s.get(BasicKeys.extraMetaSbtFiles).getOrElse(Nil)
)
val loadedProjectsRaw = timed("Load.loadUnit: loadedProjectsRaw", log) {
loadProjects(initialProjects, !hasRootAlreadyDefined)
@@ -844,7 +845,8 @@ private[sbt] object Load {
makeOrDiscoverRoot: Boolean,
buildUri: URI,
context: PluginManagement.Context,
generatedConfigClassFiles: Seq[File]
generatedConfigClassFiles: Seq[File],
extraSbtFiles: Seq[File]
): LoadedProjects =
/*timed(s"Load.loadTransitive(${ newProjects.map(_.id) })", log)*/ {
// load all relevant configuration files (.sbt, as .scala already exists at this point)
@@ -869,7 +871,11 @@ private[sbt] object Load {
val autoPlugins: Seq[AutoPlugin] =
try plugins.detected.deducePluginsFromProject(p1, log)
catch { case e: AutoPluginException => throw translateAutoPluginException(e, p) }
val p2 = this.resolveProject(p1, autoPlugins, plugins, injectSettings, memoSettings, log)
val extra =
if (context.globalPluginProject) extraSbtFiles
else Nil
val p2 =
this.resolveProject(p1, autoPlugins, plugins, injectSettings, memoSettings, extra, log)
val projectLevelExtra =
if (expand) autoPlugins flatMap {
_.derivedProjects(p2) map { _.setProjectOrigin(ProjectOrigin.DerivedProject) }
@@ -888,7 +894,8 @@ private[sbt] object Load {
(root, rest, files, generated)
case DiscoveredProjects(None, rest, files, generated) => (p, rest, files, generated)
}
val (finalRoot, projectLevelExtra) = finalizeProject(root, files, true)
val (finalRoot, projectLevelExtra) =
finalizeProject(root, files, true)
(finalRoot, discovered ++ projectLevelExtra, generated)
}

@@ -910,11 +917,16 @@ private[sbt] object Load {
false,
buildUri,
context,
generated ++ generatedConfigClassFiles
generated ++ generatedConfigClassFiles,
Nil
)
case Nil if makeOrDiscoverRoot =>
log.debug(s"[Loading] Scanning directory ${buildBase}")
discover(AddSettings.defaultSbtFiles, buildBase) match {
val auto =
if (context.globalPluginProject)
AddSettings.seq(AddSettings.defaultSbtFiles, AddSettings.sbtFiles(extraSbtFiles: _*))
else AddSettings.defaultSbtFiles
discover(auto, buildBase) match {
case DiscoveredProjects(Some(root), discovered, files, generated) =>
log.debug(
s"[Loading] Found root project ${root.id} w/ remaining ${discovered.map(_.id).mkString(",")}"
@@ -935,7 +947,8 @@ private[sbt] object Load {
false,
buildUri,
context,
generated ++ generatedConfigClassFiles
generated ++ generatedConfigClassFiles,
Nil
)
// Here we need to create a root project...
case DiscoveredProjects(None, discovered, files, generated) =>
@@ -953,6 +966,7 @@ private[sbt] object Load {
false,
buildUri,
context,
Nil,
Nil
)
val otherGenerated = otherProjects.generatedConfigClassFiles
@@ -1014,6 +1028,7 @@ private[sbt] object Load {
* @param globalUserSettings All the settings contributed from the ~/.sbt/<version> directory
* @param memoSettings A recording of all loaded files (our files should reside in there). We should need not load any
* sbt file to resolve a project.
* @param extraSbtFiles Extra *.sbt files.
* @param log A logger to report auto-plugin issues to.
*/
private[sbt] def resolveProject(
@@ -1022,6 +1037,7 @@ private[sbt] object Load {
loadedPlugins: LoadedPlugins,
globalUserSettings: InjectSettings,
memoSettings: mutable.Map[File, LoadedSbtFile],
extraSbtFiles: Seq[File],
log: Logger
): Project =
timed(s"Load.resolveProject(${p.id})", log) {
@@ -1060,7 +1076,17 @@ private[sbt] object Load {
b ++ expandSettings(add)
}
}
expandSettings(AddSettings.allDefaults)
val auto =
if (extraSbtFiles.nonEmpty)
AddSettings.seq(
AddSettings.autoPlugins,
AddSettings.buildScalaFiles,
AddSettings.userSettings,
AddSettings.defaultSbtFiles,
AddSettings.sbtFiles(extraSbtFiles: _*),
)
else AddSettings.allDefaults
expandSettings(auto)
}
// Finally, a project we can use in buildStructure.
p.copy(settings = allSettings)
@@ -142,6 +142,7 @@ object SettingQueryTest extends org.specs2.mutable.Specification {
loadedPlugins,
injectSettings,
fileToLoadedSbtFileMap,
Nil,
state.log
)
}
Copy path View file
@@ -0,0 +1,14 @@
Adds `--addPluginSbtFile=<file>` command, which adds the given .sbt file to the plugin build.
Using this mechanism editors or IDEs can start a build with required plugin.

```
$ cat /tmp/extra.sbt
addSbtPlugin("com.eed3si9n" % "sbt-assembly" % "0.14.7")
$ sbt --addPluginSbtFile=/tmp/extra.sbt
...
sbt:helloworld> plugins
In file:/xxxx/hellotest/
...
sbtassembly.AssemblyPlugin: enabled in root
```
ProTip! Use n and p to navigate between commits in a pull request.
You can’t perform that action at this time.