diff --git a/src/reference/02-DetailTopics/03-Dependency-Management/03-Library-Management.md b/src/reference/02-DetailTopics/03-Dependency-Management/03-Library-Management.md deleted file mode 100644 index c4d608cb..00000000 --- a/src/reference/02-DetailTopics/03-Dependency-Management/03-Library-Management.md +++ /dev/null @@ -1,633 +0,0 @@ ---- -out: Library-Management.html ---- - - [Setup]: Setup.html - [Basic-Def]: Basic-Def.html - [Full-Def]: Full-Def.html - [Library-Dependencies]: Library-Dependencies.html - [Update-Report]: Update-Report.html - [Paths]: Paths.html - [Resolvers]: Resolvers.html - [Publishing]: Publishing.html - [Cross-Build]: Cross-Build.html - [Cached-Resolution]: Cached-Resolution.html - -Library Management ------------------- - -There's now a -[getting started page][Library-Dependencies] about -library management, which you may want to read first. - -*Documentation Maintenance Note:* it would be nice to remove the overlap -between this page and the getting started page, leaving this page with -the more advanced topics such as checksums and external Ivy files. - -### Introduction - -There are two ways for you to manage libraries with sbt: manually or -automatically. These two ways can be mixed as well. This page discusses -the two approaches. All configurations shown here are settings that go -directly in a [.sbt file][Basic-Def]. - -### Manual Dependency Management - -Manually managing dependencies involves copying any jars that you want -to use to the `lib` directory. sbt will put these jars on the classpath -during compilation, testing, running, and when using the interpreter. -You are responsible for adding, removing, updating, and otherwise -managing the jars in this directory. No modifications to your project -definition are required to use this method unless you would like to -change the location of the directory you store the jars in. - -To change the directory jars are stored in, change the `unmanagedBase` -setting in your project definition. For example, to use `custom_lib/`: - -```scala -unmanagedBase := baseDirectory.value / "custom_lib" -``` - -If you want more control and flexibility, override the `unmanagedJars` -task, which ultimately provides the manual dependencies to sbt. The -default implementation is roughly: - -```scala -Compile / unmanagedJars := (baseDirectory.value ** "*.jar").classpath -``` - -If you want to add jars from multiple directories in addition to the -default directory, you can do: - -```scala -Compile / unmanagedJars ++= { - val base = baseDirectory.value - val baseDirectories = (base / "libA") +++ (base / "b" / "lib") +++ (base / "libC") - val customJars = (baseDirectories ** "*.jar") +++ (base / "d" / "my.jar") - customJars.classpath -} -``` - -See [Paths][Paths] for more information on building up paths. - -### Automatic Dependency Management - -This method of dependency management involves specifying the direct -dependencies of your project and letting sbt handle retrieving and -updating your dependencies. - -sbt 1.3.0+ uses [Coursier](https://get-coursier.io/) to implement dependency management. -Until sbt 1.3.0, sbt has used Apache Ivy for ten years. Coursier does a good job -of keeping the compatibility, but some of the feature might be specific to Apache Ivy. -In those cases, you can use the following setting to switch back to Ivy: - -```scala -ThisBuild / useCoursier := false -``` - -#### Inline Declarations - -Inline declarations are a basic way of specifying the dependencies to be -automatically retrieved. They are intended as a lightweight alternative -to a full configuration using Ivy. - -##### Dependencies - -Declaring a dependency looks like: - -```scala -libraryDependencies += groupID % artifactID % revision -``` - -or - -```scala -libraryDependencies += groupID % artifactID % revision % configuration -``` - -See [configurations](#ivy-configurations) for details on configuration -mappings. Also, several dependencies can be declared together: - -```scala -libraryDependencies ++= Seq( - groupID %% artifactID % revision, - groupID %% otherID % otherRevision -) -``` - -If you are using a dependency that was built with sbt, double the first -`%` to be `%%`: - -```scala -libraryDependencies += groupID %% artifactID % revision -``` - -This will use the right jar for the dependency built with the version of -Scala that you are currently using. If you get an error while resolving -this kind of dependency, that dependency probably wasn't published for -the version of Scala you are using. See [Cross Build][Cross-Build] for details. - -Ivy can select the latest revision of a module according to constraints -you specify. Instead of a fixed revision like `"1.6.1"`, you specify -`"latest.integration"`, `"2.9.+"`, or `"[1.0,)"`. See the -[Ivy revisions](https://ant.apache.org/ivy/history/2.3.0/ivyfile/dependency.html#revision) -documentation for details. - -##### Resolvers - -sbt uses the standard Maven2 repository by default. - -Declare additional repositories with the form: - -```scala -resolvers += name at location -``` - -For example: - -```scala -libraryDependencies ++= Seq( - "org.apache.derby" % "derby" % "10.4.1.3", - "org.specs" % "specs" % "1.6.1" -) - -resolvers += "Sonatype OSS Snapshots" at "https://oss.sonatype.org/content/repositories/snapshots" -``` - -sbt can search your local Maven repository if you add it as a -repository: - -```scala -resolvers += "Local Maven Repository" at "file://"+Path.userHome.absolutePath+"/.m2/repository" -``` - -See [Resolvers][Resolvers] for details on defining other types of repositories. - -##### Override default resolvers - -`resolvers` configures additional, inline user resolvers. By default, -`sbt` combines these resolvers with default repositories (Maven Central -and the local Ivy repository) to form `externalResolvers`. To have more -control over repositories, set `externalResolvers` directly. To only -specify repositories in addition to the usual defaults, configure -`resolvers`. - -For example, to use the Sonatype OSS Snapshots repository in addition to -the default repositories, - -```scala -resolvers += "Sonatype OSS Snapshots" at "https://oss.sonatype.org/content/repositories/snapshots" -``` - -To use the local repository, but not the Maven Central repository: - -```scala -externalResolvers := Resolver.combineDefaultResolvers(resolvers.value.toVector, mavenCentral = false) -``` - -##### Override all resolvers for all builds - -The repositories used to retrieve sbt, Scala, plugins, and application -dependencies can be configured globally and declared to override the -resolvers configured in a build or plugin definition. There are two -parts: - -1. Define the repositories used by the launcher. -2. Specify that these repositories should override those in build - definitions. - -The repositories used by the launcher can be overridden by defining -`~/.sbt/repositories`, which must contain a `[repositories]` section -with the same format as the `Launcher` configuration file. For example: - -``` -[repositories] -local -my-maven-repo: https://example.org/repo -my-ivy-repo: https://example.org/ivy-repo/, [organization]/[module]/[revision]/[type]s/[artifact](-[classifier]).[ext] -``` - -A different location for the repositories file may be specified by the -`sbt.repository.config` system property in the sbt startup script. The -final step is to set `sbt.override.build.repos` to true to use these -repositories for dependency resolution and retrieval. - -##### Explicit URL - -If your project requires a dependency that is not present in a -repository, a direct URL to its jar can be specified as follows: - -```scala -libraryDependencies += "slinky" % "slinky" % "2.1" from "https://slinky2.googlecode.com/svn/artifacts/2.1/slinky.jar" -``` - -The URL is only used as a fallback if the dependency cannot be found -through the configured repositories. Also, the explicit URL is not -included in published metadata (that is, the pom or ivy.xml). - -##### Disable Transitivity - -By default, these declarations fetch all project dependencies, -transitively. In some instances, you may find that the dependencies -listed for a project aren't necessary for it to build. Projects using -the Felix OSGI framework, for instance, only explicitly require its main -jar to compile and run. Avoid fetching artifact dependencies with either -`intransitive()` or `notTransitive()`, as in this example: - -```scala -libraryDependencies += "org.apache.felix" % "org.apache.felix.framework" % "1.8.0" intransitive() -``` - -##### Classifiers - -You can specify the classifier for a dependency using the `classifier` -method. For example, to get the jdk15 version of TestNG: - -```scala -libraryDependencies += "org.testng" % "testng" % "5.7" classifier "jdk15" -``` - -For multiple classifiers, use multiple `classifier` calls: - -```scala -libraryDependencies += - "org.lwjgl.lwjgl" % "lwjgl-platform" % lwjglVersion classifier "natives-windows" classifier "natives-linux" classifier "natives-osx" -``` - -To obtain particular classifiers for all dependencies transitively, run -the `updateClassifiers` task. By default, this resolves all artifacts -with the `sources` or `javadoc` classifier. Select the classifiers to -obtain by configuring the `transitiveClassifiers` setting. For example, -to only retrieve sources: - -```scala -transitiveClassifiers := Seq("sources") -``` - -##### Exclude Transitive Dependencies - -To exclude certain transitive dependencies of a dependency, use the -`excludeAll` or `exclude` methods. The `exclude` method should be used -when a pom will be published for the project. It requires the -organization and module name to exclude. For example, - -```scala -libraryDependencies += - "log4j" % "log4j" % "1.2.15" exclude("javax.jms", "jms") -``` - -The `excludeAll` method is more flexible, but because it cannot be -represented in a pom.xml, it should only be used when a pom doesn't need -to be generated. For example, - -```scala -libraryDependencies += - "log4j" % "log4j" % "1.2.15" excludeAll( - ExclusionRule(organization = "com.sun.jdmk"), - ExclusionRule(organization = "com.sun.jmx"), - ExclusionRule(organization = "javax.jms") - ) -``` - -See [ModuleID](../api/sbt/librarymanagement/ModuleID.html) for API details. - -In certain cases a transitive dependency should be excluded from -all dependencies. This can be achieved by setting up `ExclusionRules` -in `excludeDependencies`. - -```scala -excludeDependencies ++= Seq( - // commons-logging is replaced by jcl-over-slf4j - ExclusionRule("commons-logging", "commons-logging") -) -``` - -##### Download Sources - -Downloading source and API documentation jars is usually handled by an -IDE plugin. These plugins use the `updateClassifiers` and -`updateSbtClassifiers` tasks, which produce an `Update-Report` -referencing these jars. - -To have sbt download the dependency's sources without using an IDE -plugin, add `withSources()` to the dependency definition. For API jars, -add `withJavadoc()`. For example: - -```scala -libraryDependencies += - "org.apache.felix" % "org.apache.felix.framework" % "1.8.0" withSources() withJavadoc() -``` - -Note that this is not transitive. Use the `update*Classifiers` tasks -for that. - -##### Extra Attributes - -[Extra attributes](https://ant.apache.org/ivy/history/2.3.0/concept.html#extra) -can be specified by passing key/value pairs to the `extra` method. - -To select dependencies by extra attributes: - -```scala -libraryDependencies += "org" % "name" % "rev" extra("color" -> "blue") -``` - -To define extra attributes on the current project: - -```scala -projectID := { - val previous = projectID.value - previous.extra("color" -> "blue", "component" -> "compiler-interface") -} -``` - -##### Inline Ivy XML - -sbt additionally supports directly specifying the configurations or -dependencies sections of an Ivy configuration file inline. You can mix -this with inline Scala dependency and repository declarations. - -For example: - -```scala -ivyXML := - - - - - -``` - -##### Ivy Home Directory - -By default, sbt uses the standard Ivy home directory location -`\${user.home}/.ivy2/`. This can be configured machine-wide, for use by -both the sbt launcher and by projects, by setting the system property -`sbt.ivy.home` in the sbt startup script (described in -[Setup][Setup]). - -For example: - -``` -java -Dsbt.ivy.home=/tmp/.ivy2/ ... -``` - -##### Checksums - -sbt -([through Ivy](https://ant.apache.org/ivy/history/latest-milestone/concept.html#checksum)) -verifies the checksums of downloaded files by default. It also publishes -checksums of artifacts by default. The checksums to use are specified by -the *checksums* setting. - -To disable checksum checking during update: - -```scala -update / checksums := Nil -``` - -To disable checksum creation during artifact publishing: - -```scala -publishLocal / checksums := Nil - -publish / checksums := Nil -``` - -The default value is: - -```scala -checksums := Seq("sha1", "md5") -``` - - - -##### Conflict Management - -The conflict manager decides what to do when dependency resolution -brings in different versions of the same library. By default, the latest -revision is selected. This can be changed by setting `conflictManager`, -which has type [ConflictManager](../api/sbt/librarymanagement/ConflictManager.html). -See the -[Ivy documentation](https://ant.apache.org/ivy/history/latest-milestone/settings/conflict-managers.html) -for details on the different conflict managers. For example, to specify -that no conflicts are allowed, - -```scala -conflictManager := ConflictManager.strict -``` - -With this set, any conflicts will generate an error. To resolve a -conflict, you must configure a dependency override, which is explained in a later section. - - - -##### Eviction warning - -The following direct dependencies will introduce a conflict on the akka-actor -version because banana-rdf requires akka-actor 2.1.4. - -```scala -libraryDependencies ++= Seq( - "org.w3" %% "banana-rdf" % "0.4", - "com.typesafe.akka" %% "akka-actor" % "2.3.7", -) -``` - -The default conflict manager will select the newer version of akka-actor, -2.3.7. This can be confirmed in the output of `show update`, which -shows the newer version as being selected and the older version as evicted. - -``` -> show update -[info] compile: - -[info] com.typesafe.akka:akka-actor_2.10 -[info] - 2.3.7 -... -[info] - 2.1.4 -... -[info] evicted: true -[info] evictedReason: latest-revision -... -[info] callers: org.w3:banana-rdf_2.10:0.4 -``` - -Furthermore, the binary version compatibility of the akka-actor 2.1.4 and 2.3.7 are not guaranteed since the second segment has bumped up. sbt 0.13.6+ detects this automatically and prints out the following warning: - -``` -[warn] There may be incompatibilities among your library dependencies. -[warn] Here are some of the libraries that were evicted: -[warn] * com.typesafe.akka:akka-actor_2.10:2.1.4 -> 2.3.7 -[warn] Run 'evicted' to see detailed eviction warnings -``` - -Since akka-actor 2.1.4 and 2.3.7 are not binary compatible, the only way to fix this is to downgrade your dependency to akka-actor 2.1.4, or upgrade banana-rdf to use akka-actor 2.3. - -##### Overriding a version - -For binary compatible conflicts, sbt provides dependency overrides. -They are configured with the -`dependencyOverrides` setting, which is a set of `ModuleIDs`. For -example, the following dependency definitions conflict because spark -uses log4j 1.2.16 and scalaxb uses log4j 1.2.17: - -```scala -libraryDependencies ++= Seq( - "org.spark-project" %% "spark-core" % "0.5.1", - "org.scalaxb" %% "scalaxb" % "1.0.0" -) -``` - -The default conflict manager chooses the latest revision of log4j, -1.2.17: - -``` -> show update -[info] compile: -[info] log4j:log4j:1.2.17: ... -... -[info] (EVICTED) log4j:log4j:1.2.16 -... -``` - -To change the version selected, add an override: - -```scala -dependencyOverrides += "log4j" % "log4j" % "1.2.16" -``` - -This will not add a direct dependency on log4j, but will force the -revision to be 1.2.16. This is confirmed by the output of `show update`: - -``` -> show update -[info] compile: -[info] log4j:log4j:1.2.16 -... -``` - -> **Note:** this is an Ivy-only feature and will not be included in a -> published pom.xml. - -##### Unresolved dependencies error - -Adding the following dependency to your project will result to an unresolved dependencies error of vpp 2.2.1: - -```scala -libraryDependencies += "org.apache.cayenne.plugins" % "maven-cayenne-plugin" % "3.0.2" -``` - -sbt 0.13.6+ will try to reconstruct dependencies tree when it fails to resolve a managed dependency. This is an approximation, but it should help you figure out where the problematic dependency is coming from. When possible sbt will display the source position next to the modules: - -``` -[warn] :::::::::::::::::::::::::::::::::::::::::::::: -[warn] :: UNRESOLVED DEPENDENCIES :: -[warn] :::::::::::::::::::::::::::::::::::::::::::::: -[warn] :: foundrylogic.vpp#vpp;2.2.1: not found -[warn] :::::::::::::::::::::::::::::::::::::::::::::: -[warn] -[warn] Note: Unresolved dependencies path: -[warn] foundrylogic.vpp:vpp:2.2.1 -[warn] +- org.apache.cayenne:cayenne-tools:3.0.2 -[warn] +- org.apache.cayenne.plugins:maven-cayenne-plugin:3.0.2 (/foo/some-test/build.sbt#L28) -[warn] +- d:d_2.10:0.1-SNAPSHOT -``` - -##### Cached resolution - -See [Cached resolution][Cached-Resolution] for performance improvement option. - -##### Publishing - -See [Publishing][Publishing] for how to publish your project. - - - -##### Configurations - -Ivy configurations are a useful feature for your build when you need -custom groups of dependencies, such as for a plugin. Ivy configurations -are essentially named sets of dependencies. You can read the -[Ivy documentation](https://ant.apache.org/ivy/history/2.3.0/tutorial/conf.html) -for details. - -The built-in use of configurations in sbt is similar to scopes in Maven. -sbt adds dependencies to different classpaths by the configuration that -they are defined in. See the description of -[Maven Scopes](https://maven.apache.org/guides/introduction/introduction-to-dependency-mechanism.html#Dependency_Scope) -for details. - -You put a dependency in a configuration by selecting one or more of its -configurations to map to one or more of your project's configurations. -The most common case is to have one of your configurations `A` use a -dependency's configuration `B`. The mapping for this looks like -`"A->B"`. To apply this mapping to a dependency, add it to the end of -your dependency definition: - -```scala -libraryDependencies += "org.scalatest" %% "scalatest" % "$example_scalatest_version$" % "test->compile" -``` - -This says that your project's `"test"` configuration uses `ScalaTest`'s -`"compile"` configuration. See the -[Ivy documentation](https://ant.apache.org/ivy/history/2.3.0/tutorial/conf.html) -for more advanced mappings. Most projects published to Maven -repositories will use the `"compile"` configuration. - -A useful application of configurations is to group dependencies that are -not used on normal classpaths. For example, your project might use a -`"js"` configuration to automatically download jQuery and then include -it in your jar by modifying `resources`. For example: - -```scala -val JS = config("js") hide - -ivyConfigurations += JS - -libraryDependencies += "jquery" % "jquery" % "3.2.1" % "js->default" from "https://code.jquery.com/jquery-3.2.1.min.js" - -Compile / resources ++= update.value.select(configurationFilter("js")) -``` - -The `config` method defines a new configuration with name `"js"` and -makes it private to the project so that it is not used for publishing. -See [Update Report][Update-Report] for more information on selecting -managed artifacts. - -A configuration without a mapping (no `"->"`) is mapped to `"default"` -or `"compile"`. The `->` is only needed when mapping to a different -configuration than those. The ScalaTest dependency above can then be -shortened to: - -```scala -libraryDependencies += "org.scalatest" %% "scalatest" % "$example_scalatest_version$" % "test" -``` - -##### Forcing a revision (Not recommended) - -**Note**: Forcing can create logical inconsistencies so it's no longer recommended. - -To say that we prefer the version we've specified over the version from -indirect dependencies, use `force()`: - -```scala -libraryDependencies ++= Seq( - "org.spark-project" %% "spark-core" % "0.5.1", - "log4j" % "log4j" % "1.2.14" force() -) -``` - -**Note:** this is an Ivy-only feature and cannot be included in a -published pom.xml. - -##### Known limitations - -Maven support is dependent on Coursier or Ivy's support for Maven POMs. Known issues -with this support: - -- Specifying `relativePath` in the `parent` section of a POM will - produce an error. -- Ivy ignores repositories specified in the POM. A workaround is to - specify repositories inline or in an Ivy `ivysettings.xml` file. - diff --git a/src/reference/SUMMARY.md b/src/reference/SUMMARY.md index 8324d52a..72e2803b 100644 --- a/src/reference/SUMMARY.md +++ b/src/reference/SUMMARY.md @@ -24,6 +24,7 @@ - [Caching](concepts/caching.md) - [Reference]() - [sbt](reference/sbt.md) + - [sbt update](reference/sbt-update.md) - [Cross building setup](reference/cross-building-setup.md) - [Remote cache setup](reference/remote-cache-setup.md) - [Recipes]() diff --git a/src/reference/appendix/glossary.md b/src/reference/appendix/glossary.md index a6867291..64a536d2 100644 --- a/src/reference/appendix/glossary.md +++ b/src/reference/appendix/glossary.md @@ -50,6 +50,20 @@ A system-level building block of sbt, often used to capture user interaction or The idea of building multiple targets from the same set of source file. This includes Scala cross building, targetting multiple versions of Scala releases; platform cross building, targetting JVM, Scala.JS, and Scala Native; and custom virtual axis like Spark versions. +D +- + +### Dependency resolution + +During library management, when multiple version candidates (e.g. `foo:2.2.0` and `foo:3.0.0`) are found for a library `foo` within a dependency graph, it is called a _dependency conflict_. The process of mediating the conflict into a single version is called _dependency resolution_. Often, this would result in the older version beging removed from the dependency graph, which is called an _eviction_ of `foo:2.2.0`. In some cases, an eviction is considered unsafe because the candidates are not replacable. See [sbt update](../reference/sbt-update.md). + +E +- + +### Eviction + +See [dependency resolution](#dependency-resolution). + V - diff --git a/src/reference/reference/sbt-update.md b/src/reference/reference/sbt-update.md new file mode 100644 index 00000000..b2371215 --- /dev/null +++ b/src/reference/reference/sbt-update.md @@ -0,0 +1,418 @@ + + [Coursier]: https://get-coursier.io/ + [Setup]: Setup.html + [Basic-Def]: Basic-Def.html + [Full-Def]: Full-Def.html + [Library-Dependencies]: ../guide/library-dependency-basics.md + [Update-Report]: Update-Report.html + [Paths]: Paths.html + [Resolvers]: Resolvers.html + [Publishing]: Publishing.html + [Cross-Build]: ../concepts/cross-building.md + [Cached-Resolution]: Cached-Resolution.html + +sbt update +========== + +See [library depdency basics][Library-Dependencies] in the Getting Started guide to learn about the basics. + +Synopsis +-------- + +`sbt --client update` + +Description +----------- + +sbt uses [Coursier][Coursier] to implement library management, +also known as a package manager in other ecosystems. +The general idea of library management is that you can specify external libraries you would +like to use in your subprojects, and the library management system would: +- Check if such versions exists in the listed repositories +- Look for the transitive dependencies (i.e. the libraries used by the libraries) +- Attempt to resolve version conflicts, if any +- Download the artifacts, such as JAR files, from the repositories + +### Dependencies + +Declaring a dependency looks like: + +```scala +libraryDependencies += groupID %% artifactID % revision +``` + +or + +```scala +libraryDependencies += groupID %% artifactID % revision % configuration +``` + + + +Also, several dependencies can be declared together: + +```scala +libraryDependencies ++= Seq( + groupID %% artifactID % revision, + groupID %% otherID % otherRevision +) +``` + +If you are using a dependency that was built with sbt, double the first +`%` to be `%%`: + +```scala +libraryDependencies += groupID %% artifactID % revision +``` + +This will use the right JAR for the dependency built with the version of +Scala that you are currently using. If you get an error while resolving +this kind of dependency, that dependency probably wasn't published for +the version of Scala you are using. See [Cross building][Cross-Build] for details. + + + +### `versionScheme` and eviction errors + +sbt allows library authors to declare the version semantics using the `versionScheme` setting: + +```scala +// Semantic Versioning applied to 0.x, as well as 1.x, 2.x, etc +versionScheme := Some(VersionScheme.EarlySemVer) +``` + +When Coursier finds multiple versions of a library, for example Cats Effect 2.x and Cats Effect 3.0.0-M4, +it often resolves the conflict by removing the older version from the graph. This process is colloquially called eviction, +like "Cats Effect 2.2.0 was evicted." + +This would work if the new tenant is binary compatible with Cats Effect 2.2.0. +In this case, the library authors have declared that they are _not_ binary compatible, so the eviction was actually unsafe. +An unsafe eviction would cause runtime issues such as `ClassNotFoundException`. Instead Coursier should've failed to resolve. + +```scala +lazy val use = project + .settings( + name := "use", + libraryDependencies ++= Seq( + "org.http4s" %% "http4s-blaze-server" % "0.21.11", + "org.typelevel" %% "cats-effect" % "3.0.0-M4", + ), + ) +``` + +sbt performs this secondary compatibility check after Coursier returns a candidate: + +``` +[error] stack trace is suppressed; run last use / update for the full output +[error] (use / update) found version conflict(s) in library dependencies; some are suspected to be binary incompatible: +[error] +[error] * org.typelevel:cats-effect_2.12:3.0.0-M4 (early-semver) is selected over {2.2.0, 2.0.0, 2.0.0, 2.2.0} +[error] +- use:use_2.12:0.1.0-SNAPSHOT (depends on 3.0.0-M4) +[error] +- org.http4s:http4s-core_2.12:0.21.11 (depends on 2.2.0) +[error] +- io.chrisdavenport:vault_2.12:2.0.0 (depends on 2.0.0) +[error] +- io.chrisdavenport:unique_2.12:2.0.0 (depends on 2.0.0) +[error] +- co.fs2:fs2-core_2.12:2.4.5 (depends on 2.2.0) +[error] +[error] +[error] this can be overridden using libraryDependencySchemes or evictionErrorLevel +``` + +This mechanism is called the _eviction error_. + +#### Opting out of the the eviction error + +If the library authors have declared the compatibility breakage, but if you want to ignore +the strict check (often for `scala-xml`), you can write this in `project/plugins.sbt` and `build.sbt`: + +```scala +libraryDependencySchemes += "org.scala-lang.modules" %% "scala-xml" % VersionScheme.Always +``` + +To ignore all eviction errors: + +```scala +evictionErrorLevel := Level.Info +``` + +### Resolvers + +sbt uses the standard Maven Central repository by default. Declare additional repositories with the form: + +```scala +resolvers += name at location +``` + +For example: + +```scala +libraryDependencies ++= Seq( + "org.apache.derby" % "derby" % "10.4.1.3", + "org.specs" % "specs" % "1.6.1" +) + +resolvers += "Sonatype OSS Snapshots" at "https://oss.sonatype.org/content/repositories/snapshots" +``` + +sbt can search your local Maven repository if you add it as a +repository: + +```scala +resolvers += Resolver.mavenLocal +``` + + + +#### Override default resolvers + +`resolvers` configures additional, inline user resolvers. By default, +`sbt` combines these resolvers with default repositories (Maven Central +and the local Ivy repository) to form `externalResolvers`. To have more +control over repositories, set `externalResolvers` directly. To only +specify repositories in addition to the usual defaults, configure +`resolvers`. + +For example, to use the Sonatype OSS Snapshots repository in addition to +the default repositories, + +```scala +resolvers += "Sonatype OSS Snapshots" at "https://oss.sonatype.org/content/repositories/snapshots" +``` + +To use the local repository, but not the Maven Central repository: + +```scala +externalResolvers := Resolver.combineDefaultResolvers(resolvers.value.toVector, mavenCentral = false) +``` + +#### Override all resolvers for all builds + +The repositories used to retrieve sbt, Scala, plugins, and application +dependencies can be configured globally and declared to override the +resolvers configured in a build or plugin definition. There are two +parts: + +1. Define the repositories used by the launcher. +2. Specify that these repositories should override those in build + definitions. + +The repositories used by the launcher can be overridden by defining +`~/.sbt/repositories`, which must contain a `[repositories]` section +with the same format as the `Launcher` configuration file. For example: + +``` +[repositories] +local +my-maven-repo: https://example.org/repo +my-ivy-repo: https://example.org/ivy-repo/, [organization]/[module]/[revision]/[type]s/[artifact](-[classifier]).[ext] +``` + +A different location for the repositories file may be specified by the +`sbt.repository.config` system property in the sbt startup script. The +final step is to set `sbt.override.build.repos` to true to use these +repositories for dependency resolution and retrieval. + +### Exclude Transitive Dependencies + +In certain cases a transitive dependency should be excluded from +all dependencies. This can be achieved by setting up `ExclusionRules` +in `excludeDependencies`. + +```scala +excludeDependencies ++= Seq( + // commons-logging is replaced by jcl-over-slf4j + ExclusionRule("commons-logging", "commons-logging") +) +``` + +To exclude certain transitive dependencies of a dependency, use the +`excludeAll` or `exclude` methods. The `exclude` method should be used +when a pom will be published for the project. It requires the +organization and module name to exclude. For example, + +```scala +libraryDependencies += + ("log4j" % "log4j" % "1.2.15").exclude("javax.jms", "jms") +``` + + + +### Explicit URL + +If your project requires a dependency that is not present in a +repository, a direct URL to its jar can be specified as follows: + +```scala +libraryDependencies += "slinky" % "slinky" % "2.1" from "https://slinky2.googlecode.com/svn/artifacts/2.1/slinky.jar" +``` + +The URL is only used as a fallback if the dependency cannot be found +through the configured repositories. Also, the explicit URL is not +included in published metadata (that is, the pom or ivy.xml). + +### Disable Transitivity + +By default, these declarations fetch all project dependencies, +transitively. In some instances, you may find that the dependencies +listed for a project aren't necessary for it to build. Projects using +the Felix OSGI framework, for instance, only explicitly require its main +jar to compile and run. Avoid fetching artifact dependencies with either +`intransitive()` or `notTransitive()`, as in this example: + +```scala +libraryDependencies += ("org.apache.felix" % "org.apache.felix.framework" % "1.8.0").intransitive() +``` + +### Classifiers + +You can specify the classifier for a dependency using the `classifier` +method. For example, to get the jdk15 version of TestNG: + +```scala +libraryDependencies += ("org.testng" % "testng" % "5.7").classifier("jdk15") +``` + +For multiple classifiers, use multiple `classifier` calls: + +```scala +libraryDependencies += + "org.lwjgl.lwjgl" % "lwjgl-platform" % lwjglVersion classifier "natives-windows" classifier "natives-linux" classifier "natives-osx" +``` + +To obtain particular classifiers for all dependencies transitively, run +the `updateClassifiers` task. By default, this resolves all artifacts +with the `sources` or `javadoc` classifier. Select the classifiers to +obtain by configuring the `transitiveClassifiers` setting. For example, +to only retrieve sources: + +```scala +transitiveClassifiers := Seq("sources") +``` + +### Download Sources + +Downloading source and API documentation jars is usually handled by an +IDE plugin. These plugins use the `updateClassifiers` and +`updateSbtClassifiers` tasks, which produce an `Update-Report` +referencing these jars. + +To have sbt download the dependency's sources without using an IDE +plugin, add `withSources()` to the dependency definition. For API jars, +add `withJavadoc()`. For example: + +```scala +libraryDependencies += + ("org.apache.felix" % "org.apache.felix.framework" % "1.8.0").withSources().withJavadoc() +``` + +Note that this is not transitive. Use the `update*Classifiers` tasks +for that. + + + +