Search code examples
scalatypeclasssimulacrum

Type mismatch in typeclass definition using simulacrum


I have a hard time defining the following typeclass:

@typeclass trait ElementIterator[It[_]] {
  def record[Item[Element], Element <: ElementT, Ctx >: Context[ElementT]]
  (iterator: It[Item[Element]],
   name: String,
   what: RefExpr[Ctx, Any])
  (implicit ctxLike: ContextLike[Item],
   withVariables: WithVariables[Item[Element]]
  ): It[Item[Element]]
}

I get the following error:

Error:(11, 4) type mismatch;
 found   : sre.task.Core.WithVariables[Item[A]]
 required: sre.task.Core.WithVariables[Item[Element]]
 Note: implicit value elementIteratorForIterator is not applicable here because it comes after the application point and it lacks an explicit result type
  @typeclass trait ElementIterator[It[_]] {

I am not sure what happens here. It seems to me when Element is used in the implicit parameter list it will be freshly assigned to a new type variable A instead of matching it with the one in iterators type.

What I really want is to have is a WithVariables with the same type parameter as It.

What is really happening here? Is this a bug?


Solution

  • This is most likely a limitation of simulacrum. Consider filing a bug report on github. A workaround is to disable the generation of the ops.

    @typeclass trait ElementIterator[It[_]] {
      @noop def record[Item[Element], Element <: ElementT, Ctx >: Context[ElementT]]
      (iterator: It[Item[Element]],
       name: String,
       what: RefExpr[Ctx, Any])
      (implicit ctxLike: ContextLike[Item],
       withVariables: WithVariables[Item[Element]]
      ): It[Item[Element]]
    }