mirror of https://github.com/sbt/sbt.git
Add support for packaging attribute in POMs
This commit is contained in:
parent
cc36407cc2
commit
b9895ce801
|
|
@ -145,7 +145,11 @@ lazy val core = crossProject
|
|||
import com.typesafe.tools.mima.core._
|
||||
import com.typesafe.tools.mima.core.ProblemFilters._
|
||||
|
||||
Seq()
|
||||
Seq(
|
||||
// Since 1.0.0-M10
|
||||
// New singleton object, problem for forward compatibility only
|
||||
ProblemFilters.exclude[MissingTypesProblem]("coursier.maven.MavenSource$")
|
||||
)
|
||||
}
|
||||
)
|
||||
.jvmSettings(
|
||||
|
|
|
|||
|
|
@ -45,8 +45,10 @@ object MavenRepository {
|
|||
"test" -> Seq("runtime")
|
||||
)
|
||||
|
||||
def defaultPublications(moduleName: String) = Seq(
|
||||
"compile" -> Publication(moduleName, "jar", "jar", ""),
|
||||
val defaultPackaging = "jar"
|
||||
|
||||
def defaultPublications(moduleName: String, packaging: String) = Seq(
|
||||
"compile" -> Publication(moduleName, packaging, MavenSource.typeExtension(packaging), ""),
|
||||
"docs" -> Publication(moduleName, "doc", "jar", "javadoc"),
|
||||
"sources" -> Publication(moduleName, "src", "jar", "sources")
|
||||
)
|
||||
|
|
@ -240,15 +242,22 @@ case class MavenRepository(
|
|||
|
||||
fetch(projectArtifact(module, version, versioningValue)).flatMap { str =>
|
||||
EitherT {
|
||||
F.point {
|
||||
(for {
|
||||
F.point[String \/ Project] {
|
||||
for {
|
||||
xml <- \/.fromEither(compatibility.xmlParse(str))
|
||||
_ <- if (xml.label == "project") \/-(()) else -\/("Project definition not found")
|
||||
proj <- Pom.project(xml)
|
||||
} yield proj.copy(
|
||||
configurations = defaultConfigurations,
|
||||
publications = defaultPublications(module.name)
|
||||
)): (String \/ Project)
|
||||
} yield {
|
||||
val packagingOpt = Pom.packagingOpt(xml)
|
||||
|
||||
proj.copy(
|
||||
configurations = defaultConfigurations,
|
||||
publications = defaultPublications(
|
||||
module.name,
|
||||
packagingOpt.getOrElse(defaultPackaging)
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -85,7 +85,7 @@ case class MavenSource(
|
|||
)
|
||||
}
|
||||
|
||||
overrideClassifiers match {
|
||||
val publications0 = overrideClassifiers match {
|
||||
case Some(classifiers) =>
|
||||
val classifiersSet = classifiers.toSet
|
||||
val publications = project.publications.collect {
|
||||
|
|
@ -93,25 +93,68 @@ case class MavenSource(
|
|||
p
|
||||
}
|
||||
|
||||
val publications0 =
|
||||
if (publications.isEmpty)
|
||||
classifiers.map { classifier =>
|
||||
Publication(dependency.module.name, "jar", "jar", classifier)
|
||||
}
|
||||
else
|
||||
publications
|
||||
|
||||
publications0.map(artifactWithExtra)
|
||||
// Unlike with Ivy metadata, Maven POMs don't list the available publications (~artifacts)
|
||||
// so we give a chance to any classifier we're given by returning some publications
|
||||
// no matter what, even if we're unsure they're available.
|
||||
if (publications.isEmpty)
|
||||
classifiers.map { classifier =>
|
||||
Publication(
|
||||
dependency.module.name,
|
||||
"jar",
|
||||
"jar",
|
||||
classifier
|
||||
)
|
||||
}
|
||||
else
|
||||
publications
|
||||
|
||||
case None =>
|
||||
Seq(
|
||||
artifactWithExtra(
|
||||
dependency.attributes.publication(
|
||||
|
||||
val publications =
|
||||
if (dependency.attributes.classifier.nonEmpty)
|
||||
// FIXME We're ignoring dependency.attributes.`type` in this case
|
||||
project.publications.collect {
|
||||
case (_, p) if p.classifier == dependency.attributes.classifier =>
|
||||
p
|
||||
}
|
||||
else if (dependency.attributes.`type`.nonEmpty)
|
||||
project.publications.collect {
|
||||
case (_, p) if p.`type` == dependency.attributes.`type` =>
|
||||
p
|
||||
}
|
||||
else
|
||||
project.publications.collect {
|
||||
case (_, p) if p.classifier.isEmpty =>
|
||||
p
|
||||
}
|
||||
|
||||
// See comment above
|
||||
if (publications.isEmpty) {
|
||||
val type0 = if (dependency.attributes.`type`.isEmpty) "jar" else dependency.attributes.`type`
|
||||
|
||||
Seq(
|
||||
Publication(
|
||||
dependency.module.name,
|
||||
dependency.attributes.`type`
|
||||
type0,
|
||||
MavenSource.typeExtension(type0),
|
||||
dependency.attributes.classifier
|
||||
)
|
||||
)
|
||||
)
|
||||
} else
|
||||
publications
|
||||
}
|
||||
|
||||
publications0.map(artifactWithExtra)
|
||||
}
|
||||
}
|
||||
|
||||
object MavenSource {
|
||||
|
||||
def typeExtension(`type`: String): String =
|
||||
`type` match {
|
||||
// see similar things in sbt-maven-resolver/src/main/scala/sbt/mavenint/MavenRepositoryResolver.scala in SBT 0.13.8
|
||||
case "eclipse-plugin" | "hk2-jar" | "orbit" | "scala-jar" | "jar" | "bundle" | "doc" | "src" => "jar"
|
||||
case other => other
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -115,6 +115,9 @@ object Pom {
|
|||
} yield Profile(id, activeByDefault, activation, deps, depMgmts, properties.toMap)
|
||||
}
|
||||
|
||||
def packagingOpt(pom: Node): Option[String] =
|
||||
text(pom, "packaging", "").toOption
|
||||
|
||||
def project(pom: Node): String \/ Project = {
|
||||
import Scalaz._
|
||||
|
||||
|
|
|
|||
|
|
@ -30,7 +30,7 @@ package object coursier {
|
|||
type Attributes = core.Attributes
|
||||
object Attributes {
|
||||
def apply(
|
||||
`type`: String = "jar",
|
||||
`type`: String = "",
|
||||
classifier: String = ""
|
||||
): Attributes =
|
||||
core.Attributes(`type`, classifier)
|
||||
|
|
|
|||
|
|
@ -2,6 +2,8 @@ package coursier
|
|||
|
||||
import java.util.GregorianCalendar
|
||||
|
||||
import coursier.maven.MavenSource
|
||||
|
||||
import sbt._
|
||||
|
||||
object ToSbt {
|
||||
|
|
@ -18,8 +20,9 @@ object ToSbt {
|
|||
def artifact(module: Module, artifact: Artifact): sbt.Artifact =
|
||||
sbt.Artifact(
|
||||
module.name,
|
||||
// FIXME Get these two from publications
|
||||
artifact.attributes.`type`,
|
||||
"jar",
|
||||
MavenSource.typeExtension(artifact.attributes.`type`),
|
||||
Some(artifact.attributes.classifier).filter(_.nonEmpty),
|
||||
Nil,
|
||||
Some(url(artifact.url)),
|
||||
|
|
|
|||
|
|
@ -7,6 +7,8 @@ import scala.async.Async.{ async, await }
|
|||
import coursier.Platform.fetch
|
||||
import coursier.test.compatibility._
|
||||
|
||||
import scala.concurrent.Future
|
||||
|
||||
object CentralTests extends TestSuite {
|
||||
|
||||
val repositories = Seq[Repository](
|
||||
|
|
@ -76,6 +78,21 @@ object CentralTests extends TestSuite {
|
|||
assert(result == expected)
|
||||
}
|
||||
|
||||
def ensureArtifactHasExtension(module: Module, version: String, extension: String): Future[Unit] = async {
|
||||
val dep = Dependency(module, version, transitive = false)
|
||||
val res = await(resolve(Set(dep)))
|
||||
|
||||
res.artifacts match {
|
||||
case Seq(artifact) =>
|
||||
assert(artifact.url.endsWith("." + extension))
|
||||
case other =>
|
||||
throw new Exception(
|
||||
s"Unexpected artifact list size: ${other.size}\n" +
|
||||
"Artifacts:\n" + other.map(" " + _).mkString("\n")
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
val tests = TestSuite {
|
||||
'logback{
|
||||
async {
|
||||
|
|
@ -86,8 +103,8 @@ object CentralTests extends TestSuite {
|
|||
rootDependencies = Set(dep),
|
||||
dependencies = Set(
|
||||
dep.withCompileScope,
|
||||
Dependency(Module("ch.qos.logback", "logback-core"), "1.1.3").withCompileScope,
|
||||
Dependency(Module("org.slf4j", "slf4j-api"), "1.7.7").withCompileScope))
|
||||
Dependency(Module("ch.qos.logback", "logback-core"), "1.1.3").withCompileScope.withJarAttributeType,
|
||||
Dependency(Module("org.slf4j", "slf4j-api"), "1.7.7").withCompileScope.withJarAttributeType))
|
||||
|
||||
assert(res == expected)
|
||||
}
|
||||
|
|
@ -101,8 +118,8 @@ object CentralTests extends TestSuite {
|
|||
rootDependencies = Set(dep),
|
||||
dependencies = Set(
|
||||
dep.withCompileScope,
|
||||
Dependency(Module("org.ow2.asm", "asm-tree"), "5.0.2").withCompileScope,
|
||||
Dependency(Module("org.ow2.asm", "asm"), "5.0.2").withCompileScope))
|
||||
Dependency(Module("org.ow2.asm", "asm-tree"), "5.0.2").withCompileScope.withJarAttributeType,
|
||||
Dependency(Module("org.ow2.asm", "asm"), "5.0.2").withCompileScope.withJarAttributeType))
|
||||
|
||||
assert(res == expected)
|
||||
}
|
||||
|
|
@ -173,6 +190,26 @@ object CentralTests extends TestSuite {
|
|||
"7.0.+"
|
||||
)
|
||||
}
|
||||
|
||||
'packaging - {
|
||||
* - {
|
||||
// random aar-based module found on Central
|
||||
ensureArtifactHasExtension(
|
||||
Module("com.yandex.android", "speechkit"),
|
||||
"2.5.0",
|
||||
"aar"
|
||||
)
|
||||
}
|
||||
|
||||
* - {
|
||||
// has packaging bundle - ensuring coursier gives its artifact the .jar extension
|
||||
ensureArtifactHasExtension(
|
||||
Module("com.google.guava", "guava"),
|
||||
"17.0",
|
||||
"jar"
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -21,7 +21,13 @@ object PomParsingTests extends TestSuite {
|
|||
</dependency>
|
||||
"""
|
||||
|
||||
val expected = \/-("" -> Dependency(Module("comp", "lib"), "2.1", attributes = Attributes(classifier = "extra")))
|
||||
val expected = \/-(
|
||||
"" -> Dependency(
|
||||
Module("comp", "lib"),
|
||||
"2.1",
|
||||
attributes = Attributes(classifier = "extra")
|
||||
).withJarAttributeType
|
||||
)
|
||||
|
||||
val result = Pom.dependency(xmlParse(depNode).right.get)
|
||||
|
||||
|
|
@ -90,7 +96,7 @@ object PomParsingTests extends TestSuite {
|
|||
None,
|
||||
Profile.Activation(Nil),
|
||||
Seq(
|
||||
"" -> Dependency(Module("comp", "lib"), "0.2")),
|
||||
"" -> Dependency(Module("comp", "lib"), "0.2").withJarAttributeType),
|
||||
Nil,
|
||||
Map.empty
|
||||
))
|
||||
|
|
@ -122,7 +128,7 @@ object PomParsingTests extends TestSuite {
|
|||
Profile.Activation(Nil),
|
||||
Nil,
|
||||
Seq(
|
||||
"test" -> Dependency(Module("comp", "lib"), "0.2")),
|
||||
"test" -> Dependency(Module("comp", "lib"), "0.2").withJarAttributeType),
|
||||
Map.empty
|
||||
))
|
||||
|
||||
|
|
|
|||
|
|
@ -4,6 +4,7 @@ package object test {
|
|||
|
||||
implicit class DependencyOps(val underlying: Dependency) extends AnyVal {
|
||||
def withCompileScope: Dependency = underlying.copy(configuration = "compile")
|
||||
def withJarAttributeType: Dependency = underlying.copy(attributes = underlying.attributes.copy(`type` = "jar"))
|
||||
}
|
||||
|
||||
implicit class ResolutionOps(val underlying: Resolution) extends AnyVal {
|
||||
|
|
|
|||
Loading…
Reference in New Issue