question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Can't override trait contextual parameters

See original GitHub issue

Compiler version

3.2.0-RC2

Minimized code

import cats.syntax.all.*
import cats.*

trait Newtype[Src](using
    val show: Show[Src]
):
  opaque type Type = Src
  given Show[Type] = show
  inline final def apply(x: Src): Type = x
  extension (self: Type) inline final def value: Src = self

transparent trait BigDecimalNewtype(using
    override val show: Show[BigDecimal] = Show.show(_.underlying.toPlainString)
) extends Newtype[BigDecimal]:
  extension (src: Type)
    def setPrecision(precision: Int): Type =
      apply(src.value.round(java.math.MathContext(precision)))

type Price = Price.Type
object Price extends BigDecimalNewtype

val a = Price(BigDecimal("12000")).setPrecision(3)

// bug? This should print 12000
Show[Price].show(a)

Show.show[BigDecimal](_.underlying.toPlainString).show(a.value)

https://scastie.scala-lang.org/P9LgB5vBS4OdaUVCaH8X2A

Output

1.20E+4: scala.Predef.String
12000: scala.Predef.String

Expectation

12000: scala.Predef.String
12000: scala.Predef.String

Issue Analytics

  • State:open
  • Created a year ago
  • Comments:6 (1 by maintainers)

github_iconTop GitHub Comments

3reactions
mbovelcommented, Jul 15, 2022

Same example without cats dependency:

trait Show[T] extends Show.ContravariantShow[T]:
  def show(t: T): String

object Show:
  def apply[T](using instance: Show[T]): Show[T] = instance

  def show[A](f: A => String): Show[A] =
    new Show[A]:
      def show(a: A): String = f(a)

  trait ContravariantShow[-T] extends Serializable:
    def show(t: T): String

given catsStdShowForBigDecimal: Show[BigDecimal] with
  def show(t: BigDecimal) = t.toString()

trait Newtype[Src](using val show: Show[Src]):
  opaque type Type = Src
  given Show[Type] = show
  inline final def apply(x: Src): Type = x
  extension (self: Type) inline final def value: Src = self

transparent trait BigDecimalNewtype(using
    override val show: Show[BigDecimal] = Show.show(_.underlying.toPlainString)
) extends Newtype[BigDecimal]:
  extension (src: Type)
    def setPrecision(precision: Int): Type =
      apply(src.value.round(java.math.MathContext(precision)))

object Price extends BigDecimalNewtype
type Price = Price.Type

@main def main() =
  val a = Price(BigDecimal("12000")).setPrecision(3)

  // bug? This should print 12000
  println(Show[Price].show(a))

  println(Show.show[BigDecimal](_.underlying.toPlainString).show(a.value))
1reaction
oderskycommented, Jul 18, 2022

@Swoorup I think it would help to boil this down more and point out exactly what code is wrong. It would help to print the program with -Xprint:typer and say what does not match expectations.

The way I see it (the example is too complicated to say for sure without more digging) you think that the default argument of show in BigDecimalNewType should be used. But it isn’t because there is a given that can be supplied, namely the given Show[Type] in NewType. So this looks as expected to me.

Read more comments on GitHub >

github_iconTop Results From Across the Web

Scala - Overriding trait method using a sub context bound ...
I need to restrict AuthTraderObject to Trader user since only trader pays tax. Please, how is this override possible? scala · traits ·...
Read more >
why traits cannot have type parameters with context bounds
just have a error saying 'traits cannot have type parameters with context ... I'd like for the trait method to override a method...
Read more >
Traits | Tour of Scala
Classes and objects can extend traits, but traits cannot be instantiated ... Then implement any abstract members of the trait using the override...
Read more >
How to call an overridden trait function - Freek.dev
The trait function can be overridden simply by defining a function with the same name in the class. class MyClass { use MyTrait; ......
Read more >
Service Container - The PHP Framework For Web Artisans
Binding Basics; Binding Interfaces To Implementations; Contextual Binding; Binding Primitives; Binding Typed Variadics; Tagging; Extending Bindings.
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found