diff --git a/core/src/main/scala/cats/data/OptionT.scala b/core/src/main/scala/cats/data/OptionT.scala index 106891bcbe..6b587d0dce 100644 --- a/core/src/main/scala/cats/data/OptionT.scala +++ b/core/src/main/scala/cats/data/OptionT.scala @@ -51,10 +51,10 @@ final case class OptionT[F[_], A](value: F[Option[A]]) { def subflatMap[B](f: A => Option[B])(implicit F: Functor[F]): OptionT[F, B] = transform(_.flatMap(f)) - def getOrElse(default: => A)(implicit F: Functor[F]): F[A] = + def getOrElse[B >: A](default: => B)(implicit F: Functor[F]): F[B] = F.map(value)(_.getOrElse(default)) - def getOrElseF(default: => F[A])(implicit F: Monad[F]): F[A] = + def getOrElseF[B >: A](default: => F[B])(implicit F: Monad[F]): F[B] = F.flatMap(value)(_.fold(default)(F.pure)) def collect[B](f: PartialFunction[A, B])(implicit F: Functor[F]): OptionT[F, B] = diff --git a/tests/src/test/scala/cats/tests/OptionTSuite.scala b/tests/src/test/scala/cats/tests/OptionTSuite.scala index d3b7eea447..32e3458fda 100644 --- a/tests/src/test/scala/cats/tests/OptionTSuite.scala +++ b/tests/src/test/scala/cats/tests/OptionTSuite.scala @@ -148,12 +148,23 @@ class OptionTSuite extends CatsSuite { } } + test("OptionT[Id, A].getOrElse consistent with Option.getOrElse, with respect to types") { + forAll { (o: Option[Int]) => + o.map(Right.apply).getOrElse(Left("error")) should === (OptionT[Id, Int](o).map(Right.apply).getOrElse("error".asLeft[Int])) + } + } + test("OptionT[Id, A].getOrElseF consistent with Option.getOrElse") { forAll { (o: Option[Int], i: Int) => o.getOrElse(i) should === (OptionT[Id, Int](o).getOrElseF(i)) } } + test("OptionT[Id, A].getOrElseF consistent with Option.getOrElse, with respect to types") { + forAll { (o: Option[Int]) => + o.map(Right.apply).getOrElse(Left("error")) should === (OptionT[Id, Int](o).map(Right.apply).getOrElseF("error".asLeft[Int])) + } + } test("OptionT[Id, A].collect consistent with Option.collect") { forAll { (o: Option[Int], f: Int => Option[String]) => val p = Function.unlift(f)