Skip to content
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

Settle on a way to migrate to future language versions #11270

Closed
odersky opened this issue Feb 1, 2021 · 4 comments · Fixed by #11355
Closed

Settle on a way to migrate to future language versions #11270

odersky opened this issue Feb 1, 2021 · 4 comments · Fixed by #11355
Assignees
Milestone

Comments

@odersky
Copy link
Contributor

odersky commented Feb 1, 2021

Current State

Version and migration options are controlled by -source, with possible values

3.0-migration, 3.0, 3.1-migration, 3.1

This can be given as a command line option, as -source <version>, or with a language import, as in

import language.`3.1`

The Problem

We are not at all sure whether everything enabled under -source 3.1 will actually ship in 3.1. We have allowed us great flexibility when to ship new minor versions. 3.1 could happen some months after 3.0 ships and we might still want to enable cross compiling for it, so that many of the deprecations and removals slated for 3.1 would have to wait. So we need a more flexible way to say a feature or deprecation is enabled in a future language version, without being fully precise which one.

Constraint

Any proposed solution has to allow controlling version and migration mode from the command line as well as through a language import.

Possible Solutions

  1. Keep the current scheme, but rename 3.1 and 3.1-migration to 3.x and 3.x-migration.
  2. Keep the current scheme but rename 3.1 and 3.1-migration to future and futureMigration. The language import would be
    import language.future
    import language.futureMigration
  3. Replace future source versions by a language import future and control migration through another language import migration. So instead of
    import language.`3.1-migration`
    it would be
    import language.{future, migration}
    and instead of -source 3.1-migration it would be -language:future,migration.
    This would mean we would also get rid of 3.0-migration as a separate source version, so instead of
    -source 3.0-migration we'd have -source 3.0 -language:migration. The -source argument would be
    redundant as long as default source is 3.0, but would be important if the default source version changed. One could also allow a command line option -migration as a shorthand for -language:migration.

Which alternative should we choose? Are there others to consider?

@odersky
Copy link
Contributor Author

odersky commented Feb 2, 2021

A discussion yesterday gave a slight preference for (2).

@propensive
Copy link
Contributor

I'm a bit sceptical that the language import would be helpful. If a team is writing some code, a reasonable development strategy would be to always target two compilers, one invoked with a future flag and the next one without the flag. But that's not possible if the future flag is embedded in the source code. That same source code couldn't be compiled on the newer compiler without enabling as-yet unknown future features.

It's also probably a useful constraint (particularly in a larger team) to know that the only way to "enable" new version-level features would be through the command invocation, and that individual team members shouldn't easily do this on a fine-grained basis.

And it might also be useful for cross-version testing of new releases of the Scala compiler to encourage a corpus of open-source code that doesn't have different meanings on different compilers.

@odersky
Copy link
Contributor Author

odersky commented Feb 2, 2021

There is typically no future compiler. We work with one compiler version only, and that as built in support for things we intend to ship in future versions of the language.

It's also probably a useful constraint (particularly in a larger team) to know that the only way to "enable" new version-level features would be through the command invocation, and that individual team members shouldn't easily do this on a fine-grained basis.

I have seen this argument made many times, but still disagree with it. IMO it's very important that we document what version of Scala we use in the source files themselves. Sort of like pragmas in Haskell.

@mpilquist
Copy link
Contributor

mpilquist commented Feb 6, 2021

We have a use case for language imports in http4s, where due to differences in implicit resolution, the Scala 3 macros need to be compiled with -source:3.0 but certain type projections need -source:3.0-migration. We'd be able to use -source:3.0-migration for the bulk of the source and use import language:3.0 in the macro files.

https://github.com/http4s/http4s/pull/4319/files/d039e0e754b477cb9b7158f63c71a3f3af3a3e29..43460b5cc10a9229195085a766fedcece816c775

@odersky odersky self-assigned this Feb 8, 2021
@odersky odersky added this to the 3.0.0-RC1 milestone Feb 8, 2021
@odersky odersky removed the discussion label Feb 8, 2021
@odersky odersky linked a pull request Feb 9, 2021 that will close this issue
@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
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

6 participants