mirror of https://github.com/sbt/sbt.git
Support for enhanced cross build suffix in dependencies. Closes #267
Overloading `%%` for library dependency to allow using a library built with an alternative version of Scala that is different from the Scala version used in the current build (but hopefully binary compatible). This is useful in cases, where the binary build of a dependency with the exact Scala version isn't yet available but an otherwise binary compatible build (maybe with a previous Scala release) is available.
This commit is contained in:
parent
a49c907146
commit
0270ac078f
|
|
@ -4,7 +4,7 @@
|
|||
package sbt
|
||||
package impl
|
||||
|
||||
import StringUtilities.{appendable,nonEmpty}
|
||||
import StringUtilities.nonEmpty
|
||||
|
||||
trait DependencyBuilders
|
||||
{
|
||||
|
|
@ -27,20 +27,21 @@ trait DependencyBuilders
|
|||
|
||||
final class GroupID private[sbt] (groupID: String)
|
||||
{
|
||||
def % (artifactID: String) = groupArtifact(artifactID, false)
|
||||
def %% (artifactID: String) = groupArtifact(artifactID, true)
|
||||
private def groupArtifact(artifactID: String, cross: Boolean) =
|
||||
def % (artifactID: String) = groupArtifact(artifactID, None)
|
||||
def %% (artifactID: String, crossVersion: String => String = identity) = groupArtifact(artifactID, Some(crossVersion))
|
||||
def %% (artifactID: String, alternatives: (String, String)*) = groupArtifact(artifactID, Some(Map(alternatives: _*) orElse { case s => s }))
|
||||
private def groupArtifact(artifactID: String, cross: Option[String => String]) =
|
||||
{
|
||||
nonEmpty(artifactID, "Artifact ID")
|
||||
new GroupArtifactID(groupID, artifactID, cross)
|
||||
}
|
||||
}
|
||||
final class GroupArtifactID private[sbt] (groupID: String, artifactID: String, crossVersion: Boolean)
|
||||
{
|
||||
final class GroupArtifactID private[sbt] (groupID: String, artifactID: String, crossVersion: Option[String => String])
|
||||
{
|
||||
def % (revision: String): ModuleID =
|
||||
{
|
||||
nonEmpty(revision, "Revision")
|
||||
ModuleID(groupID, artifactID, revision).cross(crossVersion)
|
||||
ModuleID(groupID, artifactID, revision).cross(!crossVersion.isEmpty, crossVersion.getOrElse(identity))
|
||||
}
|
||||
}
|
||||
final class ModuleIDConfigurable private[sbt] (moduleID: ModuleID)
|
||||
|
|
|
|||
|
|
@ -314,7 +314,7 @@ private object IvySbt
|
|||
as.map(art => substituteCross(art, cross))
|
||||
def substituteCross(m: ModuleID, cross: String): ModuleID =
|
||||
if(m.crossVersion)
|
||||
m.copy(name = crossName(m.name, cross), explicitArtifacts = substituteCrossA(m.explicitArtifacts, cross))
|
||||
m.copy(name = crossName(m.name, m.crossVersionRemap(cross)), explicitArtifacts = substituteCrossA(m.explicitArtifacts, cross))
|
||||
else
|
||||
m
|
||||
|
||||
|
|
|
|||
|
|
@ -205,7 +205,7 @@ object IvyActions
|
|||
report.allMissing flatMap { case (_, mod, art) => art.classifier.map { c => (restrictedCopy(mod, false), c) } } groupBy(_._1) map { case (mod, pairs) => (mod, pairs.map(_._2).toSet) }
|
||||
|
||||
private[this] def restrictedCopy(m: ModuleID, confs: Boolean) =
|
||||
ModuleID(m.organization, m.name, m.revision, crossVersion = m.crossVersion, extraAttributes = m.extraAttributes, configurations = if(confs) m.configurations else None)
|
||||
ModuleID(m.organization, m.name, m.revision, crossVersion = m.crossVersion, crossVersionRemap = m.crossVersionRemap, extraAttributes = m.extraAttributes, configurations = if(confs) m.configurations else None)
|
||||
private[this] def resolve(logging: UpdateLogging.Value)(ivy: Ivy, module: DefaultModuleDescriptor, defaultConf: String): (ResolveReport, Option[ResolveException]) =
|
||||
{
|
||||
val resolveOptions = new ResolveOptions
|
||||
|
|
@ -268,4 +268,4 @@ object IvyActions
|
|||
}
|
||||
|
||||
}
|
||||
final class ResolveException(val messages: Seq[String], val failed: Seq[ModuleID]) extends RuntimeException(messages.mkString("\n"))
|
||||
final class ResolveException(val messages: Seq[String], val failed: Seq[ModuleID]) extends RuntimeException(messages.mkString("\n"))
|
||||
|
|
|
|||
|
|
@ -9,14 +9,14 @@ import scala.xml.NodeSeq
|
|||
import org.apache.ivy.plugins.resolver.{DependencyResolver, IBiblioResolver}
|
||||
import org.apache.ivy.util.url.CredentialsStore
|
||||
|
||||
final case class ModuleID(organization: String, name: String, revision: String, configurations: Option[String] = None, isChanging: Boolean = false, isTransitive: Boolean = true, explicitArtifacts: Seq[Artifact] = Nil, exclusions: Seq[ExclusionRule] = Nil, extraAttributes: Map[String,String] = Map.empty, crossVersion: Boolean = false)
|
||||
final case class ModuleID(organization: String, name: String, revision: String, configurations: Option[String] = None, isChanging: Boolean = false, isTransitive: Boolean = true, explicitArtifacts: Seq[Artifact] = Nil, exclusions: Seq[ExclusionRule] = Nil, extraAttributes: Map[String,String] = Map.empty, crossVersion: Boolean = false, crossVersionRemap: String => String = identity)
|
||||
{
|
||||
override def toString =
|
||||
organization + ":" + name + ":" + revision +
|
||||
(configurations match { case Some(s) => ":" + s; case None => "" }) +
|
||||
(if(extraAttributes.isEmpty) "" else " " + extraString)
|
||||
def extraString = extraAttributes.map { case (k,v) => k + "=" + v } mkString("(",", ",")")
|
||||
def cross(v: Boolean) = copy(crossVersion = v)
|
||||
def cross(v: Boolean, verRemap: String => String = identity) = copy(crossVersion = v, crossVersionRemap = verRemap)
|
||||
// () required for chaining
|
||||
def notTransitive() = intransitive()
|
||||
def intransitive() = copy(isTransitive = false)
|
||||
|
|
@ -282,7 +282,7 @@ object Resolver
|
|||
def resolveAll(patterns: Seq[String]) = patterns.map(p => resolvePattern(base, p))
|
||||
Patterns(resolveAll(basePatterns.ivyPatterns), resolveAll(basePatterns.artifactPatterns), basePatterns.isMavenCompatible)
|
||||
}
|
||||
private[sbt] def resolvePattern(base: String, pattern: String): String =
|
||||
private[sbt] def resolvePattern(base: String, pattern: String): String =
|
||||
{
|
||||
val normBase = base.replace('\\', '/')
|
||||
if(normBase.endsWith("/") || pattern.startsWith("/")) normBase + pattern else normBase + "/" + pattern
|
||||
|
|
@ -423,14 +423,14 @@ object Artifact
|
|||
{
|
||||
import artifact._
|
||||
val classifierStr = classifier match { case None => ""; case Some(c) => "-" + c }
|
||||
val base = if(module.crossVersion) IvySbt.crossName(artifact.name, scalaVersion) else artifact.name
|
||||
val base = if(module.crossVersion) IvySbt.crossName(artifact.name, module.crossVersionRemap(scalaVersion)) else artifact.name
|
||||
base + "-" + module.revision + classifierStr + "." + artifact.extension
|
||||
}
|
||||
def cross(enable: Boolean, scalaVersion: String): String = if(enable) "_" + scalaVersion else ""
|
||||
|
||||
val classifierConfMap = Map(SourceClassifier -> Sources, DocClassifier -> Docs)
|
||||
val classifierTypeMap = Map(SourceClassifier -> SourceType, DocClassifier -> DocType)
|
||||
def classifierConf(classifier: String): Configuration = classifierConfMap.getOrElse(classifier, Optional)
|
||||
def classifierConf(classifier: String): Configuration = classifierConfMap.getOrElse(classifier, Optional)
|
||||
def classifierType(classifier: String): String = classifierTypeMap.getOrElse(classifier, DefaultType)
|
||||
def classified(name: String, classifier: String): Artifact =
|
||||
Artifact(name, classifierType(classifier), DefaultExtension, Some(classifier), classifierConf(classifier) :: Nil, None)
|
||||
|
|
@ -440,4 +440,4 @@ object ModuleConfiguration
|
|||
{
|
||||
def apply(org: String, resolver: Resolver): ModuleConfiguration = apply(org, "*", "*", resolver)
|
||||
def apply(org: String, name: String, resolver: Resolver): ModuleConfiguration = ModuleConfiguration(org, name, "*", resolver)
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue