Skip to content

Wildcard export ignores synthetic members generated from desugaring #10857

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
eloots opened this issue Dec 18, 2020 · 6 comments · Fixed by #10949
Closed

Wildcard export ignores synthetic members generated from desugaring #10857

eloots opened this issue Dec 18, 2020 · 6 comments · Fixed by #10949
Assignees
Milestone

Comments

@eloots
Copy link
Contributor

eloots commented Dec 18, 2020

Minimized code

Up-to Scala 3.0.0-M2, a wildcard export worked as expected: ALL members were exported, both singleton members as class case members:

object T:
  enum Command:
    case ResetSudokuDetailState
    case Update(cellUpdates: Int)
    case GetSudokuDetailState(z:Int)
  export Command._

val update = T.Update(cellUpdates = 5)

In Scala 3.0.0-M3, the above code exports ResetSudokuDetailState, but not Update and GetSudokuDetailState.

The workaround is to export all members explicitly:

object T:
  enum Command:
    case ResetSudokuDetailState
    case Update(cellUpdates: Int)
    case GetSudokuDetailState(z:Int)
  export Command.{ResetSudokuDetailState, Update, GetSudokuDetailState}

val update = T.Update(cellUpdates = 5)

Output

scala> object T:
     |   enum Command:
     |     case ResetSudokuDetailState
     |     case Update(cellUpdates: Int)
     |     case GetSudokuDetailState(z:Int)
     |   export Command._
     |
     | val update = T.Update(cellUpdates = 5)
8 |val update = T.Update(cellUpdates = 5)
  |             ^^^^^^^^
  |             value Update is not a member of object T

Expectation

Doing a wildcard export on an enum should export all members

@bishabosha
Copy link
Member

bishabosha commented Dec 22, 2020

I think this may have something to do with creator application changes, if you take a look suing -Xprint:typer cli option, the companion objects of enum cases were never exported, (I checked back to 0.25.0), just type aliases, so T.Update(cellUpdates = 5) was actually a creator application and not calling T.Update.apply.

@bishabosha
Copy link
Member

bishabosha commented Dec 22, 2020

more bad news, it seems you cant wildcard export definitions that are added after desugaring:

object T:
  object Command:
    case class Update(cellUpdates: Int)
  export Command._

in this example the synthetic companion object for Update is also not exported.

Will need to investigate if this is a fundamental issue with export desugaring at Namer or if there are just missing wildcard definitions being ignored

@bishabosha bishabosha changed the title A wildcard export of enum members doesn't export class case members Wildcard export ignores synthetic members generated from desugaring Dec 22, 2020
@eloots
Copy link
Contributor Author

eloots commented Dec 22, 2020

more bad news, it seems you cant wildcard export definitions that are added after desugaring

That's a pity... Using export to export all members of an enum makes it possible to take Scala 2 ADTs encoded with sealed traits; trivially encode them as Scala 3 enum's and leave any code that uses them unmodified.
Not having this work as it [accidentally] did prior to M3 means that code has to be changed at the use site.

@odersky
Copy link
Contributor

odersky commented Dec 26, 2020

It's a conscious decision not to export synthetic members. One positive aspect of this is that you can export all cases from an enum without also exporting the synthetic values etc machinery. I think we will stick to that.

@odersky odersky closed this as completed Dec 26, 2020
@bishabosha
Copy link
Member

@odersky would it be desirable to treat the non-(private/synthetic) symbols as names that can then be reinterpreted as an explicit selector, which would then pick up the companion object of case classes?

bishabosha added a commit to dotty-staging/dotty that referenced this issue Dec 29, 2020
a wildcard export will first search for all public and
non-synthetic members to add. Then once a valid member
is found, that name is then used to search for all
term or type members that use that name and are not
given or private.

As a consequence members like companion objects to
case classes will be exported alongside a type alias
to the case class
bishabosha added a commit to dotty-staging/dotty that referenced this issue Dec 29, 2020
a wildcard export will first search for all public and
non-synthetic members to add. Then once a valid member
is found, that name is then used to search for all
term or type members that use that name and are not
given or private.

As a consequence members like companion objects to
case classes will be exported alongside a type alias
to the case class
bishabosha added a commit to dotty-staging/dotty that referenced this issue Dec 29, 2020
a wildcard export will first search for all public and
non-synthetic members to add. Then once a valid member
is found, that name is then used to search for all
term or type members that use that name and are not
given or private.

As a consequence members like companion objects to
case classes will be exported alongside a type alias
to the case class
@odersky
Copy link
Contributor

odersky commented Jan 1, 2021

@bishabosha Yes, I think that could work. I.e. if one of a pair of type/term definitions with the same name is non-synthatic, the other is imported as well.

bishabosha added a commit to dotty-staging/dotty that referenced this issue Jan 12, 2021
a wildcard export will first search for all public and
non-synthetic members to add. Then once a valid member
is found, that name is then used to search for all
term or type members that use that name and are not
given or private.

As a consequence members like companion objects to
case classes will be exported alongside a type alias
to the case class
bishabosha added a commit that referenced this issue Jan 12, 2021
fix #10857: export from wildcard defs with same name as user declared ones
@Kordyjan Kordyjan modified the milestones: 3.0.0-RC1, 3.0.0 Aug 2, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging a pull request may close this issue.

5 participants