All Projects → lightbend → Mima

lightbend / Mima

Licence: apache-2.0
A tool for catching binary incompatibility in Scala

Programming Languages

scala
5932 projects

Projects that are alternatives of or similar to Mima

chuckwagon
a Scala/sbt AWS Lambda Toolkit
Stars: ✭ 29 (-91.59%)
Mutual labels:  sbt-plugin
sbt-ecr
An SBT plugin for managing Docker images within Amazon ECR.
Stars: ✭ 52 (-84.93%)
Mutual labels:  sbt-plugin
sbt-publish-more
📤 Publish artifacts to more than one repository
Stars: ✭ 21 (-93.91%)
Mutual labels:  sbt-plugin
sbt-flaky
Detect flaky tests with sbt
Stars: ✭ 35 (-89.86%)
Mutual labels:  sbt-plugin
sbt-scala-js-map
A Sbt plugin that configures source mapping for Scala.js projects hosted on Github
Stars: ✭ 30 (-91.3%)
Mutual labels:  sbt-plugin
sbt-codeartifact
An sbt plugin for publishing packages to AWS CodeArtifact.
Stars: ✭ 15 (-95.65%)
Mutual labels:  sbt-plugin
xsbt-webstart
A Webstart plugin for sbt
Stars: ✭ 12 (-96.52%)
Mutual labels:  sbt-plugin
Sbt Sonatype
A sbt plugin for publishing Scala/Java projects to the Maven central.
Stars: ✭ 265 (-23.19%)
Mutual labels:  sbt-plugin
sbt-ammonite-classpath
Export the classpath for Ammonite and Almond
Stars: ✭ 29 (-91.59%)
Mutual labels:  sbt-plugin
sbt-best-practice
Configure common build settings for a Scala project
Stars: ✭ 47 (-86.38%)
Mutual labels:  sbt-plugin
sbt-example
Run Scaladoc as unit tests
Stars: ✭ 30 (-91.3%)
Mutual labels:  sbt-plugin
sbt-elm
Scala Build Tool (SBT) plugin for the Elm programming language
Stars: ✭ 44 (-87.25%)
Mutual labels:  sbt-plugin
sbt-hepek
Sbt plugin for rendering Scala objects to files. And more!
Stars: ✭ 17 (-95.07%)
Mutual labels:  sbt-plugin
sbt-ethereum
An sbt-based solidity / scala development environment, and general command-line power tool, for Ethereum.
Stars: ✭ 97 (-71.88%)
Mutual labels:  sbt-plugin
sbt-assembly
Deploy über-JARs. Restart processes. (port of codahale/assembly-sbt)
Stars: ✭ 1,801 (+422.03%)
Mutual labels:  sbt-plugin
playwarts
WartRemover warts for Play Framework.
Stars: ✭ 23 (-93.33%)
Mutual labels:  sbt-plugin
sbt-jni
SBT Plugin to ease working with JNI
Stars: ✭ 110 (-68.12%)
Mutual labels:  sbt-plugin
Scala Clippy
Good advice for Scala compiler errors
Stars: ✭ 311 (-9.86%)
Mutual labels:  sbt-plugin
Soteria
Plugin to block compilation when unapproved dependencies are used or code styling does not comply.
Stars: ✭ 36 (-89.57%)
Mutual labels:  sbt-plugin
sbt-openapi-schema
Generate schema sources for Scala, Java and Elm from an openapi 3.0 spec.
Stars: ✭ 12 (-96.52%)
Mutual labels:  sbt-plugin

MiMa

MiMa (for "Migration Manager") is a tool for identifying binary incompatibilities in Scala libraries.

It's pronounced MEE-ma.

What it is?

MiMa can report binary modifications that may cause the JVM to throw a java.lang.LinkageError (or one of its subtypes, like AbstractMethodError) at runtime. Linkage errors are usually the consequence of modifications in classes/members signature.

MiMa compares all classfiles of two released libraries and reports all source of incompatibilities that may lead to a linkage error. MiMa provides you, the library maintainer, with a tool that can greatly automates and simplifies the process of ensuring the release-to-release binary compatibility of your libraries.

A key aspect of MiMa to be aware of is that it only looks for syntactic binary incompatibilities. The semantic binary incompatibilities (such as adding or removing a method invocation) are not considered. This is a pragmatic approach as it is up to you, the library maintainer, to make sure that no semantic changes have occurred between two binary compatible releases. If a semantic change occurred, then you should make sure to provide this information as part of the new release's change list.

In addition, it is worth mentioning that binary compatibility does not imply source compatibility, i.e., some of the changes that are considered compatible at the bytecode level may still break a codebase that depends on it. Interestingly, this is not an issue intrinsic to the Scala language. In the Java language binary compatibility does not imply source compatibility as well. MiMa focuses on binary compatibility and currently provides no insight into source compatibility.

Usage

MiMa's sbt plugin supports sbt 1.x only. (Use v0.3.0 for sbt 0.13.x.)

To use it add the following to your project/plugins.sbt file:

addSbtPlugin("com.typesafe" % "sbt-mima-plugin" % "0.8.1")

Add the following to your build.sbt file:

mimaPreviousArtifacts := Set("com.example" %% "my-library" % "1.2.3")

and run mimaReportBinaryIssues to see something like the following:

[info] Found 4 potential binary incompatibilities
[error]  * method rollbackTransactionResource()resource.Resource in object resource.Resource does not have a   correspondent in new version
[error]  * method now()scala.util.continuations.ControlContext in trait resource.ManagedResourceOperations does not    have a correspondent in old version
[error]  * abstract method now()scala.util.continuations.ControlContext in interface resource.ManagedResource does not have a correspondent in old version
[error]  * method rollbackTransactionResource()resource.Resource in trait resource.MediumPriorityResourceImplicits does not have a correspondent in new version
[error] {file:/home/jsuereth/project/personal/scala-arm/}scala-arm/*:mima-report-binary-issues: Binary compatibility check failed!
[error] Total time: 15 s, completed May 18, 2012 11:32:29 AM

Filtering binary incompatibilities

When MiMa reports a binary incompatibility that you consider acceptable, such as a change in an internal package, you need to use the mimaBinaryIssueFilters setting to filter it out and get mimaReportBinaryIssues to pass, like so:

import com.typesafe.tools.mima.core._

mimaBinaryIssueFilters ++= Seq(
  ProblemFilters.exclude[MissingClassProblem]("com.example.mylibrary.internal.Foo"),
)

You may also use wildcards in the package and/or the top Problem parent type for such situations:

mimaBinaryIssueFilters ++= Seq(
  ProblemFilters.exclude[Problem]("com.example.mylibrary.internal.*"),
)

IncompatibleSignatureProblem

Most MiMa checks (DirectMissingMethod, IncompatibleResultType, IncompatibleMethType, etc) are against the "method descriptor", which is the "raw" type signature, without any information about generic parameters.

The IncompatibleSignature check compares the Signature, which includes the full signature including generic parameters. This can catch real incompatibilities, but also sometimes triggers for a change in generics that would not in fact cause problems at run time. Notably, it will warn when updating your project to scala 2.12.9+ or 2.13.1+, see this issue for details.

You can opt-in to this check by setting:

import com.typesafe.tools.mima.plugin.MimaKeys._

ThisBuild / mimaReportSignatureProblems := true

Setting different mimaPreviousArtifacts

From time to time you may need to set mimaPreviousArtifacts according to some conditions. For instance, if you have already ported your project to Scala 2.13 and set it up for cross-building to Scala 2.13, but still haven't cut a release, you may want to define mimaPreviousArtifacts according to the Scala version, with something like:

mimaPreviousArtifacts := {
  if (CrossVersion.partialVersion(scalaVersion.value) == Some((2, 13)))
    Set.empty
  else
    Set("com.example" %% "my-library" % "1.2.3")
}

or perhaps using some of sbt 1.2's new API:

import sbt.librarymanagement.{ SemanticSelector, VersionNumber }

mimaPreviousArtifacts := {
  if (VersionNumber(scalaVersion.value).matchesSemVer(SemanticSelector(">=2.13")))
    Set.empty
  else
    Set("com.example" %% "my-library" % "1.2.3")
}

Make mimaReportBinaryIssues not fail

The setting mimaFailOnNoPrevious defaults to true and will make mimaReportBinaryIssues fail if mimaPreviousArtifacts hasn't been set.

To make mimaReportBinaryIssues not fail you may want to do one of the following:

  • set mimaPreviousArtifacts on all the projects that should be checking their binary compatibility
  • avoid calling mimaPreviousArtifacts when binary compatibility checking isn't needed
  • set mimaFailOnNoPrevious := false on specific projects that want to opt-out (alternatively disablePlugins(MimaPlugin))
  • set ThisBuild / mimaFailOnNoPrevious := false, which disables it build-wide, effectively reverting back to the previous behaviour

Setting mimaPreviousArtifacts when name contains a "."

To refer to the project name in mimaPreviousArtifacts, use moduleName rather than name, like

mimaPreviousArtifacts := Set(organization.value %% moduleName.value % "0.1.0")

Unlike name, moduleName escapes characters like ., and is the name actually used by publish and publishLocal to publish your project. It's also the value your users should use when adding your project to their dependencies.

Note that the project description data, including the texts, logos, images, and/or trademarks, for each open source project belongs to its rightful owner. If you wish to add or remove any projects, please contact us at [email protected].