diff --git a/build.sbt b/build.sbt index a877f64f2..2c4f88214 100644 --- a/build.sbt +++ b/build.sbt @@ -37,8 +37,8 @@ ThisBuild / publishTo := { val nexus = "https://oss.sonatype.org/" Some("releases" at nexus + "service/local/staging/deploy/maven2") } - ThisBuild / Test / classLoaderLayeringStrategy := ClassLoaderLayeringStrategy.Flat +ThisBuild / evictionErrorLevel := Level.Info def commonSettings: Seq[Setting[_]] = Def.settings( scalaVersion := scala3, diff --git a/core/src/main/scala/sbt/librarymanagement/ConfigurationExtra.scala b/core/src/main/scala/sbt/librarymanagement/ConfigurationExtra.scala index 73b8028ff..e5c18cd50 100644 --- a/core/src/main/scala/sbt/librarymanagement/ConfigurationExtra.scala +++ b/core/src/main/scala/sbt/librarymanagement/ConfigurationExtra.scala @@ -111,7 +111,7 @@ private[librarymanagement] abstract class ConfigurationExtra { } private[sbt] object ConfigurationMacro: - def configMacroImpl(name: Expr[String])(using Quotes): Expr[Configuration] = { + def configMacroImpl(name: Expr[String])(using Quotes): Expr[Configuration] = import quotes.reflect.* def enclosingTerm(sym: Symbol): Symbol = sym match @@ -128,7 +128,6 @@ private[sbt] object ConfigurationMacro: if enclosingValName.head.isLower then report.error("configuration id must be capitalized") val id = Expr(enclosingValName) '{ Configuration.of($id, $name) } - } end ConfigurationMacro private[librarymanagement] abstract class ConfigRefFunctions { diff --git a/core/src/main/scala/sbt/librarymanagement/ScalaArtifacts.scala b/core/src/main/scala/sbt/librarymanagement/ScalaArtifacts.scala index 82c454e24..3dc2b71c4 100644 --- a/core/src/main/scala/sbt/librarymanagement/ScalaArtifacts.scala +++ b/core/src/main/scala/sbt/librarymanagement/ScalaArtifacts.scala @@ -57,12 +57,12 @@ object ScalaArtifacts { def libraryDependency(version: String): ModuleID = libraryDependency(Organization, version) - def libraryDependency(org: String, version: String): ModuleID = { - if (isScala3(version)) - ModuleID(org, Scala3LibraryID, version).withCrossVersion(CrossVersion.binary) - else - ModuleID(org, LibraryID, version) - } + def libraryDependency(org: String, version: String): ModuleID = + if isScala3(version) then + ModuleID(org, Scala3LibraryID, version) + .withCrossVersion(CrossVersion.binary) + .platform(Platform.jvm) + else ModuleID(org, LibraryID, version).platform(Platform.jvm) private[sbt] def docToolDependencies( org: String, @@ -79,6 +79,7 @@ object ScalaArtifacts { ModuleID(org, ScaladocID, version) .withConfigurations(Some(Configurations.ScalaDocTool.name + "->default(compile)")) .withCrossVersion(CrossVersion.binary) + .platform(Platform.jvm) ) else Seq.empty @@ -91,6 +92,7 @@ object ScalaArtifacts { ModuleID(org, Scala3CompilerID, version) .withConfigurations(Some(Configurations.ScalaTool.name + "->default(compile)")) .withCrossVersion(CrossVersion.binary) + .platform(Platform.jvm) ) else Seq( @@ -99,9 +101,11 @@ object ScalaArtifacts { ) private[this] def scala2ToolDependency(org: String, id: String, version: String): ModuleID = - ModuleID(org, id, version).withConfigurations( - Some(Configurations.ScalaTool.name + "->default,optional(default)") - ) + ModuleID(org, id, version) + .withConfigurations( + Some(Configurations.ScalaTool.name + "->default,optional(default)") + ) + .platform(Platform.jvm) } object SbtArtifacts { diff --git a/core/src/test/scala/sbt/librarymanagement/ResolverExtraTest.scala b/core/src/test/scala/sbt/librarymanagement/ResolverExtraTest.scala index 6aba7ec05..09f9cc501 100644 --- a/core/src/test/scala/sbt/librarymanagement/ResolverExtraTest.scala +++ b/core/src/test/scala/sbt/librarymanagement/ResolverExtraTest.scala @@ -36,7 +36,7 @@ object ResolverExtraTest extends BasicTestSuite { // - Helper functions ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------------------------- def assertExpansion(input: String, expected: String) = - assert(Resolver.expandMavenSettings(input) == expected) + Predef.assert(Resolver.expandMavenSettings(input) == s"$expected") def env(name: String) = sys.env.getOrElse(name, "") def prop(name: String) = sys.props.getOrElse(name, "") diff --git a/ivy/src/main/contraband-scala/sbt/librarymanagement/ivy/IvyPaths.scala b/ivy/src/main/contraband-scala/sbt/librarymanagement/ivy/IvyPaths.scala index 574369bb0..74268a9d3 100644 --- a/ivy/src/main/contraband-scala/sbt/librarymanagement/ivy/IvyPaths.scala +++ b/ivy/src/main/contraband-scala/sbt/librarymanagement/ivy/IvyPaths.scala @@ -5,8 +5,8 @@ // DO NOT EDIT MANUALLY package sbt.librarymanagement.ivy final class IvyPaths private ( - val baseDirectory: java.io.File, - val ivyHome: Option[java.io.File]) extends Serializable { + val baseDirectory: String, + val ivyHome: Option[String]) extends Serializable { @@ -20,21 +20,21 @@ final class IvyPaths private ( override def toString: String = { "IvyPaths(" + baseDirectory + ", " + ivyHome + ")" } - private[this] def copy(baseDirectory: java.io.File = baseDirectory, ivyHome: Option[java.io.File] = ivyHome): IvyPaths = { + private[this] def copy(baseDirectory: String = baseDirectory, ivyHome: Option[String] = ivyHome): IvyPaths = { new IvyPaths(baseDirectory, ivyHome) } - def withBaseDirectory(baseDirectory: java.io.File): IvyPaths = { + def withBaseDirectory(baseDirectory: String): IvyPaths = { copy(baseDirectory = baseDirectory) } - def withIvyHome(ivyHome: Option[java.io.File]): IvyPaths = { + def withIvyHome(ivyHome: Option[String]): IvyPaths = { copy(ivyHome = ivyHome) } - def withIvyHome(ivyHome: java.io.File): IvyPaths = { + def withIvyHome(ivyHome: String): IvyPaths = { copy(ivyHome = Option(ivyHome)) } } object IvyPaths { - def apply(baseDirectory: java.io.File, ivyHome: Option[java.io.File]): IvyPaths = new IvyPaths(baseDirectory, ivyHome) - def apply(baseDirectory: java.io.File, ivyHome: java.io.File): IvyPaths = new IvyPaths(baseDirectory, Option(ivyHome)) + def apply(baseDirectory: String, ivyHome: Option[String]): IvyPaths = new IvyPaths(baseDirectory, ivyHome) + def apply(baseDirectory: String, ivyHome: String): IvyPaths = new IvyPaths(baseDirectory, Option(ivyHome)) } diff --git a/ivy/src/main/contraband-scala/sbt/librarymanagement/ivy/IvyPathsFormats.scala b/ivy/src/main/contraband-scala/sbt/librarymanagement/ivy/IvyPathsFormats.scala index 1db14727e..1483f1d91 100644 --- a/ivy/src/main/contraband-scala/sbt/librarymanagement/ivy/IvyPathsFormats.scala +++ b/ivy/src/main/contraband-scala/sbt/librarymanagement/ivy/IvyPathsFormats.scala @@ -11,8 +11,8 @@ implicit lazy val IvyPathsFormat: JsonFormat[sbt.librarymanagement.ivy.IvyPaths] __jsOpt match { case Some(__js) => unbuilder.beginObject(__js) - val baseDirectory = unbuilder.readField[java.io.File]("baseDirectory") - val ivyHome = unbuilder.readField[Option[java.io.File]]("ivyHome") + val baseDirectory = unbuilder.readField[String]("baseDirectory") + val ivyHome = unbuilder.readField[Option[String]]("ivyHome") unbuilder.endObject() sbt.librarymanagement.ivy.IvyPaths(baseDirectory, ivyHome) case None => diff --git a/ivy/src/main/contraband/lm-ivy.json b/ivy/src/main/contraband/lm-ivy.json index 383e17549..d6e90dc76 100644 --- a/ivy/src/main/contraband/lm-ivy.json +++ b/ivy/src/main/contraband/lm-ivy.json @@ -137,8 +137,8 @@ "target": "Scala", "type": "record", "fields": [ - { "name": "baseDirectory", "type": "java.io.File" }, - { "name": "ivyHome", "type": "java.io.File?" } + { "name": "baseDirectory", "type": "String" }, + { "name": "ivyHome", "type": "String?" } ] } ] diff --git a/ivy/src/main/scala/sbt/internal/librarymanagement/Ivy.scala b/ivy/src/main/scala/sbt/internal/librarymanagement/Ivy.scala index 5194a6a19..97bc40143 100644 --- a/ivy/src/main/scala/sbt/internal/librarymanagement/Ivy.scala +++ b/ivy/src/main/scala/sbt/internal/librarymanagement/Ivy.scala @@ -53,6 +53,7 @@ import ivyint.{ } import sjsonnew.JsonFormat import sjsonnew.support.murmurhash.Hasher +import sbt.librarymanagement.ModuleSettings final class IvySbt( val configuration: IvyConfiguration, @@ -125,10 +126,10 @@ final class IvySbt( IvySbt.loadURI(is, e.uri.getOrElse(sys.error("uri must be specified!"))) case i: InlineIvyConfiguration => val paths = getIvyPaths(i.paths) - is.setBaseDir(paths.baseDirectory) + is.setBaseDir(new File(paths.baseDirectory)) is.setVariable("ivy.checksums", i.checksums mkString ",") is.setVariable(ConvertResolver.ManagedChecksums, i.managedChecksums.toString) - paths.ivyHome foreach is.setDefaultIvyUserDir + paths.ivyHome.foreach { (h) => is.setDefaultIvyUserDir(new File(h)) } IvySbt.configureCache(is, i.resolutionCacheDir) IvySbt.setResolvers(is, i.resolvers, i.otherResolvers, configuration.updateOptions, log) IvySbt.setModuleConfigurations(is, i.moduleConfigurations, log) @@ -240,8 +241,8 @@ final class IvySbt( val moduleSettings: ModuleSettings = rawModuleSettings match { case ic: InlineConfiguration => - val icWithCross = IvySbt.substituteCross(ic) - if (appendSbtCrossVersion) IvySbt.appendSbtCrossVersion(icWithCross) + val icWithCross: ModuleSettings = IvySbt.substituteCross(ic) + if appendSbtCrossVersion then IvySbt.appendSbtCrossVersion(icWithCross) else icWithCross case m => m } @@ -717,31 +718,33 @@ private[sbt] object IvySbt { ) } - private def substituteCross(ic: InlineConfiguration): InlineConfiguration = { - ic.scalaModuleInfo match { - case None => ic - case Some(is) => substituteCross(ic, is.scalaFullVersion, is.scalaBinaryVersion, is.platform) + private def substituteCross(m: ModuleSettings): ModuleSettings = + m.scalaModuleInfo match { + case None => m + case Some(is) => substituteCross(m, is.scalaFullVersion, is.scalaBinaryVersion, is.platform) } - } private def substituteCross( - ic: InlineConfiguration, + m: ModuleSettings, scalaFullVersion: String, scalaBinaryVersion: String, platform: Option[String] - ): InlineConfiguration = { - val applyPlatform: ModuleID => ModuleID = substitutePlatform(platform) - val applyCross = CrossVersion(scalaFullVersion, scalaBinaryVersion) - val transform: ModuleID => ModuleID = (m: ModuleID) => applyCross(applyPlatform(m)) - def propagateCrossVersion(moduleID: ModuleID): ModuleID = { - val crossExclusions: Vector[ExclusionRule] = - moduleID.exclusions.map(CrossVersion.substituteCross(_, ic.scalaModuleInfo)) - transform(moduleID) - .withExclusions(crossExclusions) - } - ic.withModule(transform(ic.module)) - .withDependencies(ic.dependencies.map(propagateCrossVersion)) - .withOverrides(ic.overrides map transform) + ): ModuleSettings = { + m match + case ic: InlineConfiguration => + val applyPlatform: ModuleID => ModuleID = substitutePlatform(platform) + val applyCross = CrossVersion(scalaFullVersion, scalaBinaryVersion) + val transform: ModuleID => ModuleID = (m: ModuleID) => applyCross(applyPlatform(m)) + def propagateCrossVersion(moduleID: ModuleID): ModuleID = { + val crossExclusions: Vector[ExclusionRule] = + moduleID.exclusions.map(CrossVersion.substituteCross(_, ic.scalaModuleInfo)) + transform(moduleID) + .withExclusions(crossExclusions) + } + ic.withModule(transform(ic.module)) + .withDependencies(ic.dependencies.map(propagateCrossVersion)) + .withOverrides(ic.overrides map transform) + case m => m } private def substitutePlatform(platform: Option[String]): ModuleID => ModuleID = { @@ -750,16 +753,22 @@ private[sbt] object IvySbt { case "" | Platform.jvm => m case _ => m.withName(s"${m.name}_$platformName") (m: ModuleID) => - (platform, m.platformOpt) match - case (Some(p), None) => addSuffix(m, p) - case (_, Some(p)) => addSuffix(m, p) - case _ => m + m.crossVersion match + case _: Disabled => m + case _ => + (platform, m.platformOpt) match + case (Some(p), None) => addSuffix(m, p) + case (_, Some(p)) => addSuffix(m, p) + case _ => m } - private def appendSbtCrossVersion(ic: InlineConfiguration): InlineConfiguration = - ic.withModule(appendSbtCrossVersion(ic.module)) - .withDependencies(ic.dependencies.map(appendSbtCrossVersion)) - .withOverrides(ic.overrides.map(appendSbtCrossVersion)) + private def appendSbtCrossVersion(m: ModuleSettings): ModuleSettings = + m match + case ic: InlineConfiguration => + ic.withModule(appendSbtCrossVersion(ic.module)) + .withDependencies(ic.dependencies.map(appendSbtCrossVersion)) + .withOverrides(ic.overrides.map(appendSbtCrossVersion)) + case m => m private def appendSbtCrossVersion(mid: ModuleID): ModuleID = { val crossVersion = for { diff --git a/ivy/src/main/scala/sbt/internal/librarymanagement/IvyCache.scala b/ivy/src/main/scala/sbt/internal/librarymanagement/IvyCache.scala index 756fb0686..1184af117 100644 --- a/ivy/src/main/scala/sbt/internal/librarymanagement/IvyCache.scala +++ b/ivy/src/main/scala/sbt/internal/librarymanagement/IvyCache.scala @@ -106,7 +106,7 @@ class IvyCache(val ivyHome: Option[File]) { /** A minimal Ivy setup with only a local resolver and the current directory as the base directory. */ private def basicLocalIvy(lock: Option[xsbti.GlobalLock], log: Logger) = { val local = Resolver.defaultLocal - val paths = IvyPaths(new File("."), ivyHome) + val paths = IvyPaths(".", ivyHome.map(_.toString)) val conf = InlineIvyConfiguration() .withPaths(paths) .withResolvers(Vector(local)) diff --git a/ivy/src/main/scala/sbt/internal/librarymanagement/IvyInternalDefaults.scala b/ivy/src/main/scala/sbt/internal/librarymanagement/IvyInternalDefaults.scala index e2d558baf..59f88ffc1 100644 --- a/ivy/src/main/scala/sbt/internal/librarymanagement/IvyInternalDefaults.scala +++ b/ivy/src/main/scala/sbt/internal/librarymanagement/IvyInternalDefaults.scala @@ -21,7 +21,7 @@ object IvyInternalDefaults { opt.getOrElse(Logger.Null) def defaultIvyPaths: IvyPaths = - IvyPaths(defaultBaseDirectory, None) + IvyPaths(defaultBaseDirectory.toString, None) def getIvyPaths(opt: Option[IvyPaths]): IvyPaths = opt.getOrElse(defaultIvyPaths) diff --git a/ivy/src/test/scala/sbt/internal/librarymanagement/BaseIvySpecification.scala b/ivy/src/test/scala/sbt/internal/librarymanagement/BaseIvySpecification.scala index a8c326333..b37fbe886 100644 --- a/ivy/src/test/scala/sbt/internal/librarymanagement/BaseIvySpecification.scala +++ b/ivy/src/test/scala/sbt/internal/librarymanagement/BaseIvySpecification.scala @@ -71,7 +71,7 @@ trait BaseIvySpecification extends AbstractEngineSpec { val moduleConfs = Vector(ModuleConfiguration("*", chainResolver)) val resCacheDir = currentTarget / "resolution-cache" InlineIvyConfiguration() - .withPaths(IvyPaths(currentBase, Some(currentTarget))) + .withPaths(IvyPaths(currentBase.toString, Some(currentTarget.toString))) .withResolvers(resolvers) .withModuleConfigurations(moduleConfs) .withChecksums(Vector.empty) diff --git a/ivy/src/test/scala/sbt/internal/librarymanagement/CustomPomParserTest.scala b/ivy/src/test/scala/sbt/internal/librarymanagement/CustomPomParserTest.scala index e987b7c18..e9d5e8271 100644 --- a/ivy/src/test/scala/sbt/internal/librarymanagement/CustomPomParserTest.scala +++ b/ivy/src/test/scala/sbt/internal/librarymanagement/CustomPomParserTest.scala @@ -18,7 +18,7 @@ object CustomPomParserTest extends BasicTestSuite { withTemporaryDirectory { cacheDir => val repoUrl = getClass.getResource("/test-maven-repo") val local = MavenRepository("Test Repo", repoUrl.toExternalForm) - val paths = IvyPaths(new File("."), Some(cacheDir)) + val paths = IvyPaths(new File(".").toString, Some(cacheDir.toString)) val conf = InlineIvyConfiguration() .withPaths(paths) .withResolvers(Vector(local)) diff --git a/ivy/src/test/scala/sbt/internal/librarymanagement/ManagedChecksumsSpec.scala b/ivy/src/test/scala/sbt/internal/librarymanagement/ManagedChecksumsSpec.scala index b49c34b75..fb2bc687a 100644 --- a/ivy/src/test/scala/sbt/internal/librarymanagement/ManagedChecksumsSpec.scala +++ b/ivy/src/test/scala/sbt/internal/librarymanagement/ManagedChecksumsSpec.scala @@ -22,7 +22,7 @@ object ManagedChecksumsSpec extends BaseIvySpecification { val moduleConfs = Vector(ModuleConfiguration("*", chainResolver)) val resCacheDir = currentTarget / "resolution-cache" InlineIvyConfiguration() - .withPaths(IvyPaths(currentBase, Some(currentTarget))) + .withPaths(IvyPaths(currentBase.toString, Some(currentTarget.toString))) .withResolvers(resolvers) .withModuleConfigurations(moduleConfs) .withChecksums(Vector(Checksum)) diff --git a/ivy/src/test/scala/sbt/internal/librarymanagement/PlatformResolutionSpec.scala b/ivy/src/test/scala/sbt/internal/librarymanagement/PlatformResolutionSpec.scala index 2d40e0147..39cc3d8c7 100644 --- a/ivy/src/test/scala/sbt/internal/librarymanagement/PlatformResolutionSpec.scala +++ b/ivy/src/test/scala/sbt/internal/librarymanagement/PlatformResolutionSpec.scala @@ -27,6 +27,20 @@ object PlatformResolutionSpec extends BaseIvySpecification { ) } + test("sjs1 platform resolves % as JVM") { + cleanCache() + val m = module( + exampleModuleId("0.6.0"), + deps = Vector(junit), + Some(scala2_13), + platform = Some(sjs1), + ) + assert( + update(m).configurations.head.modules.map(_.toString).mkString + contains "junit:junit:4.13.1" + ) + } + test("None platform can specify .platform(sjs1) depenency") { cleanCache() val m = module( @@ -64,6 +78,7 @@ object PlatformResolutionSpec extends BaseIvySpecification { def exampleModuleId(v: String): ModuleID = ("com.example" % "foo" % v % Compile) def scopt = ("com.github.scopt" %% "scopt" % "4.1.0" % Compile) + def junit = ("junit" % "junit" % "4.13.1" % Compile) override val resolvers = Vector( Resolver.mavenCentral, ) diff --git a/project/Dependencies.scala b/project/Dependencies.scala index 1488f7d73..860be2f06 100644 --- a/project/Dependencies.scala +++ b/project/Dependencies.scala @@ -52,8 +52,8 @@ object Dependencies { val jsch = "com.github.mwiede" % "jsch" % "0.2.17" intransitive () val scalaReflect = Def.setting { "org.scala-lang" % "scala-reflect" % scalaVersion.value } val scalaCompiler = Def.setting { "org.scala-lang" % "scala-compiler" % scalaVersion.value } - val scalaXml = "org.scala-lang.modules" %% "scala-xml" % "2.1.0" - val scalaTest = "org.scalatest" %% "scalatest" % "3.2.10" + val scalaXml = "org.scala-lang.modules" %% "scala-xml" % "2.3.0" + val scalaTest = "org.scalatest" %% "scalatest" % "3.2.18" val scalaVerify = "com.eed3si9n.verify" %% "verify" % "1.0.0" val scalaCheck = "org.scalacheck" %% "scalacheck" % "1.15.3" val sjsonNewVersion = "0.14.0-M1"