Ensure we don’t trigger WartRemover warts in users’ code.

This commit is contained in:
Greg Pfeil 2016-09-21 11:27:10 -06:00
parent 2a75226fe5
commit 853947a46f
4 changed files with 23 additions and 12 deletions

View File

@ -74,8 +74,10 @@ lazy val commonSettings = Seq(
releaseCrossBuild := true,
releasePublishArtifactsAction := PgpKeys.publishSigned.value,
useGpg := true,
useGpgAgent := true
)
useGpgAgent := true,
wartremoverErrors in (Test, compile) ++= Seq(
Wart.ExplicitImplicitTypes,
Wart.ImplicitConversion))
lazy val root = project.in(file("."))
.settings(commonSettings: _*)

View File

@ -358,7 +358,13 @@ class TypeClassMacros(val c: Context) {
val tparams = List(eliminateVariance(tparam)) ++ liftedTypeArgs
val tparamNames = tparams.map(_.name)
val targetType = targetTypeTree(tparam, proper, liftedTypeArgs)
// Suppressing `ImplicitConversion` is probably necessary, but it should
// be possible to avoid `ExplicitImplicitTypes` (see
// puffnfresh/wartremover#226).
q"""
@java.lang.SuppressWarnings(scala.Array(
"org.wartremover.warts.ExplicitImplicitTypes",
"org.wartremover.warts.ImplicitConversion"))
implicit def $methodName[..$tparams](target: $targetType)(implicit tc: ${typeClass.name}[${tparam.name}]): $opsType[..$tparamNames] =
new $opsType[..$tparamNames] { val self = target; val $tcInstanceName = tc }
"""

View File

@ -6,7 +6,7 @@ import org.scalatest.{ WordSpec, Matchers }
// ensure that simulacrum works in projects that use that flag.
import java.lang.String
import scala.{ Any, Boolean, Either, Int, Left, Nil, Option, Right, Some }
import scala.Predef.{ ???, ArrowAssoc, identity, wrapString }
import scala.Predef.{ ???, identity, wrapString }
import scala.collection.immutable.List
import scala.util
@ -157,7 +157,7 @@ class TypeClassTest extends WordSpec with Matchers {
override def op(x: A): A = baz(x)
}
@typeclass trait Qux[A] extends Bar[A] with Baz[A] { def qux(x: A): A }
implicit val qint = new Qux[Int] {
implicit val qint: Qux[Int] = new Qux[Int] {
def bar(x: Int) = x
def baz(x: Int) = -x
def qux(x: Int) = x * 2
@ -292,7 +292,7 @@ class TypeClassTest extends WordSpec with Matchers {
"lifted type argument in return type is rewritten correctly" in {
@typeclass trait Foo[F[_]] { def toEither[A](fa: F[A]): Either[String, A] }
implicit val listFoo = new Foo[List] { def toEither[A](fa: List[A]) = if (fa.isEmpty) Left("empty") else Right(fa.head) }
implicit val listFoo: Foo[List] = new Foo[List] { def toEither[A](fa: List[A]) = if (fa.isEmpty) Left("empty") else Right(fa.head) }
import Foo.ops._
Nil.toEither shouldBe Left("empty")
}
@ -385,13 +385,15 @@ class TypeClassTest extends WordSpec with Matchers {
}
import typeClasses._
implicit val intBippoid = new Bippoid[Int] {
type Bippy = Dingo
def append(x: Int, y: Int) = x + y
def secretId = Dingo(5)
def fn(x: Bippy) = x.x
}
implicit val foldInstance = new Foldable[List] {
// NB: Having an explicit type here breaks the associated type usage.
implicit val intBippoid: Bippoid[Int] { type Bippy = Dingo } =
new Bippoid[Int] {
type Bippy = Dingo
def append(x: Int, y: Int) = x + y
def secretId = Dingo(5)
def fn(x: Bippy) = x.x
}
implicit val foldInstance: Foldable[List] = new Foldable[List] {
def reduce[A](fa: List[A])(f: (A, A) => A): A = fa reduceLeft f
}

View File

@ -2,3 +2,4 @@ addSbtPlugin("com.github.gseitz" % "sbt-release" % "1.0.0")
addSbtPlugin("com.jsuereth" % "sbt-pgp" % "1.0.0")
addSbtPlugin("org.scala-js" % "sbt-scalajs" % "0.6.12")
addSbtPlugin("com.typesafe" % "sbt-mima-plugin" % "0.1.8")
addSbtPlugin("org.wartremover" % "sbt-wartremover" % "1.1.1")