==========
Publishing
==========

This page describes how to publish your project. Publishing consists of
uploading a descriptor, such as an Ivy file or Maven POM, and artifacts,
such as a jar or war, to a repository so that other projects can specify
your project as a dependency.

The :key:`publish` action is used to publish your project to a remote
repository. To use publishing, you need to specify the repository to
publish to and the credentials to use. Once these are set up, you can
run :key:`publish`.

The :key:`publishLocal` action is used to publish your project to a local
Ivy repository. You can then use this project from other projects on the
same machine.

Define the repository
---------------------

To specify the repository, assign a repository to :key:`publishTo` and
optionally set the publishing style. For example, to upload to Nexus:

::

    publishTo := Some("Sonatype Snapshots Nexus" at "https://oss.sonatype.org/content/repositories/snapshots")

To publish to a local repository:

::


     publishTo := Some(Resolver.file("file",  new File( "path/to/my/maven-repo/releases" )) )

Publishing to the users local maven repository:

::


     publishTo := Some(Resolver.file("file",  new File(Path.userHome.absolutePath+"/.m2/repository")))

If you're using Maven repositories you will also have to select the
right repository depending on your artifacts: SNAPSHOT versions go to
the /snapshot repository while other versions go to the /releases
repository. Doing this selection can be done by using the value of the
:key:`version` SettingKey:

::

    publishTo := {
      val nexus = "https://oss.sonatype.org/"
      if (version.value.trim.endsWith("SNAPSHOT")) 
        Some("snapshots" at nexus + "content/repositories/snapshots") 
      else
        Some("releases"  at nexus + "service/local/staging/deploy/maven2")
    }

Credentials
-----------

There are two ways to specify credentials for such a repository. The
first is to specify them inline:

::

    credentials += Credentials("Sonatype Nexus Repository Manager", "nexus.scala-tools.org", "admin", "admin123")

The second and better way is to load them from a file, for example:

::

    credentials += Credentials(Path.userHome / ".ivy2" / ".credentials")

The credentials file is a properties file with keys `realm`, `host`,
`user`, and `password`. For example:

.. code-block:: text

    realm=Sonatype Nexus Repository Manager
    host=nexus.scala-tools.org
    user=admin
    password=admin123

Cross-publishing
----------------

To support multiple incompatible Scala versions, enable cross building
and do `+ publish` (see :doc:`Cross-Build`). See :doc:`Resolvers` for other
supported repository types.

Published artifacts
-------------------

By default, the main binary jar, a sources jar, and a API documentation
jar are published. You can declare other types of artifacts to publish
and disable or modify the default artifacts. See the :doc:`Artifacts` page
for details.

Modifying the generated POM
---------------------------

When :key:`publishMavenStyle` is `true`, a POM is generated by the
:key:`makePom` action and published to the repository instead of an Ivy
file. This POM file may be altered by changing a few settings. Set
:key:`pomExtra` to provide XML (`scala.xml.NodeSeq`) to insert directly
into the generated pom. For example:

::

    pomExtra :=
    <licenses>
      <license>
        <name>Apache 2</name>
        <url>http://www.apache.org/licenses/LICENSE-2.0.txt</url>
        <distribution>repo</distribution>
      </license>
    </licenses>

:key:`makePom` adds to the POM any Maven-style repositories you have
declared. You can filter these by modifying :key:`pomRepositoryFilter`,
which by default excludes local repositories. To instead only include
local repositories:

::

    pomIncludeRepository := { (repo: MavenRepository) => 
      repo.root.startsWith("file:")
    }

There is also a :key:`pomPostProcess` setting that can be used to
manipulate the final XML before it is written. It's type is
`Node => Node`.

::

    pomPostProcess := { (node: Node) =>
        ...
    }

Publishing Locally
------------------

The :key:`publishLocal` command will publish to the local Ivy repository.
By default, this is in `${user.home}/.ivy2/local`. Other projects on
the same machine can then list the project as a dependency. For example,
if the SBT project you are publishing has configuration parameters like:

::

    name := 'My Project'
    organization := 'org.me'
    version := '0.1-SNAPSHOT'

Then another project can depend on it:

::

    libraryDependencies += "org.me" %% "my-project" % "0.1-SNAPSHOT"

The version number you select must end with `SNAPSHOT`, or you must
change the version number each time you publish. Ivy maintains a cache,
and it stores even local projects in that cache. If Ivy already has a
version cached, it will not check the local repository for updates,
unless the version number matches a `changing
pattern <http://ant.apache.org/ivy/history/2.3.0/concept.html#change>`_,
and `SNAPSHOT` is one such pattern.
