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

Make Mill commands require named CLI parameters by default #3431

Merged
merged 9 commits into from
Aug 29, 2024
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
.
  • Loading branch information
lihaoyi committed Aug 29, 2024
commit 1d0121f6d00562a394abce36edcfdc49973703b5
4 changes: 2 additions & 2 deletions example/depth/tasks/3-anonymous-tasks/build.sc
Original file line number Diff line number Diff line change
Expand Up @@ -32,10 +32,10 @@ def printFileData(fileName: String) = T.command {
> ./mill show helloFileData
"Hello"

> ./mill printFileData hello.txt
> ./mill printFileData --file-name hello.txt
Hello

> ./mill printFileData world.txt
> ./mill printFileData --file-name world.txt
World!

*/
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ object ModuleInitErrorTests extends IntegrationTestSuite {
test("rootCommand") {
// If we specify a target in the root module, we are not
// affected by the sub-modules failing to initialize
val res = eval(("rootCommand", "hello"))
val res = eval(("rootCommand", "-s", "hello"))
assert(res.isSuccess == true)
assert(res.out.contains("""Running rootCommand hello"""))
}
Expand All @@ -66,7 +66,7 @@ object ModuleInitErrorTests extends IntegrationTestSuite {
assert(fansi.Str(res.err).plainText.linesIterator.size < 20)
}
test("fooCommand") {
val res = eval(("foo.fooCommand", "hello"))
val res = eval(("foo.fooCommand", "-s", "hello"))
assert(res.isSuccess == false)
assert(fansi.Str(res.err).plainText.contains("""java.lang.Exception: Foo Boom"""))
assert(fansi.Str(res.err).plainText.linesIterator.size < 20)
Expand All @@ -77,7 +77,7 @@ object ModuleInitErrorTests extends IntegrationTestSuite {
assert(res.out.contains("""Running barTarget"""))
}
test("barCommand") {
val res = eval(("bar.barCommand", "hello"))
val res = eval(("bar.barCommand", "-s", "hello"))
assert(res.isSuccess == true)
assert(res.out.contains("""Running barCommand hello"""))
}
Expand All @@ -88,7 +88,7 @@ object ModuleInitErrorTests extends IntegrationTestSuite {
assert(fansi.Str(res.err).plainText.linesIterator.size < 20)
}
test("quxCommand") {
val res = eval(("bar.qux.quxCommand", "hello"))
val res = eval(("bar.qux.quxCommand", "-s", "hello"))
assert(res.isSuccess == false)
assert(fansi.Str(res.err).plainText.contains("""java.lang.Exception: Qux Boom"""))
assert(fansi.Str(res.err).plainText.linesIterator.size < 20)
Expand Down
30 changes: 25 additions & 5 deletions main/resolve/src/mill/resolve/Resolve.scala
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,14 @@ object Resolve {
val instantiated = ResolveCore
.instantiateModule0(baseModules, r.segments.init)
.flatMap { case (mod, rootMod) =>
instantiateCommand(rootMod, r, mod, args, nullCommandDefaults, allowPositionalCommandArgs)
instantiateCommand(
rootMod,
r,
mod,
args,
nullCommandDefaults,
allowPositionalCommandArgs
)
}

instantiated.map(Some(_))
Expand Down Expand Up @@ -216,7 +223,7 @@ trait Resolve[T] {
def resolve(
rootModule: BaseModule,
scriptArgs: Seq[String],
selectMode: SelectMode,
selectMode: SelectMode
): Either[String, List[T]] = {
resolve0(Seq(rootModule), scriptArgs, selectMode, false)
}
Expand All @@ -231,7 +238,7 @@ trait Resolve[T] {
def resolve(
rootModules: Seq[BaseModule],
scriptArgs: Seq[String],
selectMode: SelectMode,
selectMode: SelectMode
): Either[String, List[T]] = {
resolve0(rootModules, scriptArgs, selectMode, false)
}
Expand All @@ -247,7 +254,13 @@ trait Resolve[T] {
val resolved = groups.map { case (selectors, args) =>
val selected = selectors.map { case (scopedSel, sel) =>
resolveRootModule(baseModules, scopedSel).map { rootModuleSels =>
resolveNonEmptyAndHandle(args, rootModuleSels, sel, nullCommandDefaults, allowPositionalCommandArgs)
resolveNonEmptyAndHandle(
args,
rootModuleSels,
sel,
nullCommandDefaults,
allowPositionalCommandArgs
)
}
}

Expand Down Expand Up @@ -294,7 +307,14 @@ trait Resolve[T] {

resolved
.map(_.toSeq.sortBy(_.segments.render))
.flatMap(handleResolved(baseModules, _, args, sel, nullCommandDefaults, allowPositionalCommandArgs))
.flatMap(handleResolved(
baseModules,
_,
args,
sel,
nullCommandDefaults,
allowPositionalCommandArgs
))
}

private[mill] def deduplicate(items: List[T]): List[T] = items
Expand Down
10 changes: 6 additions & 4 deletions main/src/mill/main/MainModule.scala
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ object MainModule {
evaluator: Evaluator,
targets: Seq[String],
log: Logger,
watch0: Watchable => Unit,
watch0: Watchable => Unit
)(f: Seq[(Any, Option[(RunScript.TaskName, ujson.Value)])] => ujson.Value)
: Result[ujson.Value] = {

Expand Down Expand Up @@ -126,9 +126,11 @@ trait MainModule extends BaseModule0 {
* chosen is arbitrary.
*/

def path(evaluator: Evaluator,
@mainargs.arg(positional = true) src: String,
@mainargs.arg(positional = true) dest: String): Command[List[String]] =
def path(
evaluator: Evaluator,
@mainargs.arg(positional = true) src: String,
@mainargs.arg(positional = true) dest: String
): Command[List[String]] =
Target.command {
val resolved = Resolve.Tasks.resolve(
evaluator.rootModules,
Expand Down
9 changes: 7 additions & 2 deletions main/src/mill/main/RunScript.scala
Original file line number Diff line number Diff line change
Expand Up @@ -15,13 +15,18 @@ object RunScript {
def evaluateTasksNamed(
evaluator: Evaluator,
scriptArgs: Seq[String],
selectMode: SelectMode,
selectMode: SelectMode
): Either[
String,
(Seq[Watchable], Either[String, Seq[(Any, Option[(TaskName, ujson.Value)])]])
] = {
val resolved = mill.eval.Evaluator.currentEvaluator.withValue(evaluator) {
Resolve.Tasks.resolve(evaluator.rootModules, scriptArgs, selectMode, evaluator.allowPositionalCommandArgs)
Resolve.Tasks.resolve(
evaluator.rootModules,
scriptArgs,
selectMode,
evaluator.allowPositionalCommandArgs
)
}
for (targets <- resolved) yield evaluateNamed(evaluator, Agg.from(targets))
}
Expand Down
22 changes: 14 additions & 8 deletions main/test/src/mill/util/TestGraphs.scala
Original file line number Diff line number Diff line change
Expand Up @@ -133,21 +133,25 @@ class TestGraphs() {

object moduleInitError extends TestBaseModule {
def rootTarget = T { println("Running rootTarget"); "rootTarget Result" }
def rootCommand(@arg(positional = true) s: String) = T.command { println(s"Running rootCommand $s") }
def rootCommand(@arg(positional = true) s: String) =
T.command { println(s"Running rootCommand $s") }

object foo extends Module {
def fooTarget = T { println(s"Running fooTarget"); 123 }
def fooCommand(@arg(positional = true) s: String) = T.command { println(s"Running fooCommand $s") }
def fooCommand(@arg(positional = true) s: String) =
T.command { println(s"Running fooCommand $s") }
throw new Exception("Foo Boom")
}

object bar extends Module {
def barTarget = T { println(s"Running barTarget"); "barTarget Result" }
def barCommand(@arg(positional = true) s: String) = T.command { println(s"Running barCommand $s") }
def barCommand(@arg(positional = true) s: String) =
T.command { println(s"Running barCommand $s") }

object qux extends Module {
def quxTarget = T { println(s"Running quxTarget"); "quxTarget Result" }
def quxCommand(@arg(positional = true) s: String) = T.command { println(s"Running quxCommand $s") }
def quxCommand(@arg(positional = true) s: String) =
T.command { println(s"Running quxCommand $s") }
throw new Exception("Qux Boom")
}
}
Expand All @@ -159,7 +163,8 @@ class TestGraphs() {

object foo extends Module {
def fooTarget = T { println(s"Running fooTarget"); 123 }
def fooCommand(@arg(positional = true) s: String) = T.command { println(s"Running fooCommand $s") }
def fooCommand(@arg(positional = true) s: String) =
T.command { println(s"Running fooCommand $s") }
throw new Exception("Foo Boom")
}

Expand Down Expand Up @@ -515,9 +520,10 @@ object TestGraphs {
trait Cross2 extends mill.Cross.Module[String] with TaskModule {
def platform = crossValue
override def defaultCommandName(): String = "suffixCmd"
def suffixCmd(@arg(positional = true) suffix: String = "default"): Command[String] = T.command {
scalaVersion + "_" + platform + "_" + suffix
}
def suffixCmd(@arg(positional = true) suffix: String = "default"): Command[String] =
T.command {
scalaVersion + "_" + platform + "_" + suffix
}
}

}
Expand Down
2 changes: 1 addition & 1 deletion runner/src/mill/runner/MillBuildBootstrap.scala
Original file line number Diff line number Diff line change
Expand Up @@ -405,7 +405,7 @@ object MillBuildBootstrap {
def evaluateWithWatches(
rootModules: Seq[BaseModule],
evaluator: Evaluator,
targetsAndParams: Seq[String],
targetsAndParams: Seq[String]
): (Either[String, Seq[Any]], Seq[Watchable], Seq[Watchable]) = {
rootModules.foreach(_.evalWatchedValues.clear())
val evalTaskResult =
Expand Down
4 changes: 2 additions & 2 deletions runner/src/mill/runner/MillCliConfig.scala
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,7 @@ class MillCliConfig private (
doc =
""""""
)
val allowPositionalCommandArgs: Flag,
val allowPositionalCommandArgs: Flag
) {
override def toString: String = Seq(
"home" -> home,
Expand All @@ -151,7 +151,7 @@ class MillCliConfig private (
"color" -> color,
"disableCallgraphInvalidation" -> disableCallgraphInvalidation,
"metaLevel" -> metaLevel,
"allowPositionalCommandArgs" -> allowPositionalCommandArgs,
"allowPositionalCommandArgs" -> allowPositionalCommandArgs
).map(p => s"${p._1}=${p._2}").mkString(getClass().getSimpleName + "(", ",", ")")
}

Expand Down
Loading