-
Notifications
You must be signed in to change notification settings - Fork 17.8k
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
cmd/go: automatic toolchain upgrades make the combination of go version
and go install <package>@<version>
confusing
#66518
Comments
|
To me, that would make it even more confusing. Please don't try to fix the opaque toolchain behavior by bolting on even more complexity. |
I would expect I see that your latest go.mod declares 1.22. When that's released users who build To put this another way, I think what makes this the most confusing is that we're crossing the 1.21 toolchain switching version boundary here with a 1.19 module, and a local 1.21 toolchain. This should be less confusing once we're on the other side of that boundary. |
But if we assume that tools support the last two versions of Go, then the latest release of my module will have a The behavior you describe is generally fine for most software written in Go, but not tools that operate on other Go code. |
Hm I think I still need to understand something. Now that 1.21 and 1.22 are the last two versions of Go, can we assume that everyone (that we support) has a version of Go that's capable of switching to a newer toolchain and build the tool using that newest toolchain? Will your tool work with 1.21 code if it's built with 1.22? |
Yes, but not vice versa. Is your point that with automatic tool switching, there is no reason to support older versions of Go, and that go-tools should always specify the latest version of Go in its
I don't want to be forced to depend on a newer version of Go for users to have an easier time |
First of all, I agree that the newly versioned world we live in is confusing, and I don't think we've done enough to mitigate that confusion. For example: the fact that However, with respect to forcing toolchain upgrades:
In other words, I am hopeful that in the future most tools can upgrade their toolchain requirements frequently. This will allow for faster iteration with the standard library, and will make it more likely that fixes or new APIs get upstreamed rather than worked around. In another world, it would have been nice for go/parser, go/types, etc. to live in a separate module, but it's too late for that, and forward compatibility provides a similar outcome. |
The toolchain directive is ignored when using
|
Indeed, I misunderstood the It it too late to change the behavior such that IMO it's not too late to change this behavior, since module authors can't be relying on version downgrading. |
Discussed this with @matloob, and here is my updated perspective :)
So I'm not sure there's anything we can do for this issue. I'm going to make sure gopls complains loudly and clearly when it is operating on code that it can't understand, including an instruction to reinstall @latest with |
The solution here if you need Go 1.22 code is to set something like 'go 1.22.0' in your go.mod.
This is a one-time event, and almost certainly staticcheck doesn't have any such bugs.
You could set
We work hard to ensure transition periods for new functionality like this. For example for the new AST alias node we added the node one release before we started using it (actually two but the plan was one). Our goal is that setting the go line to the oldest supported Go version is reasonable. I also agree that 'go version' could potentially print more information, but that will take some extra thought. |
Russ, this issue isn't about which version of Go Staticcheck needs per se, but about which version it gets built with when someone does The problem is that the user might have some old version of Go installed, which gets automatically upgraded to a newer version when they work in a module that requires said newer version, except when they As an extreme hypothetical, the user might have a local Go 1.21 and be working in a module that uses Go 1.40. Staticcheck, because it has great backwards compatibility, still can be built with Go 1.21. Built with Go 1.21, it can analyze Go 1.21 code. Built with Go 1.40, it can analyze Go 1.40 code. The user doesn't have to care about their local toolchain when building the module, thanks to automatic upgrading. But the moment the user To me, this contradicts the point of automatic upgrading. Below are individual responses to parts of your comment; I wrote them before I wrote the above text, so they're fairly redundant. Kept here for completeness sake.
I don't need Go 1.22 code, unless I am to analyze Go 1.22 code, to get the latest go/types. If I only have to analyze Go 1.21 code, then I only need Go 1.21.
I'm afraid we're going in circles. The suggestion was that I depend on the latest version of Go so that a user running an older version of Go, but working in a module requiring a newer version of Go, who uses
Yes, I can depend on Go 1.21 and already prepare for changes coming in Go 1.22. That's not what the problem is about, though.
That is very reasonable for the majority of Go code. For tools that work on Go code, it leads to the problem outlined above. |
VS Code Go project encountered the same problem golang/vscode-go#3168. The issue mentions Currently there are two different paths for users to influence on go's toolchain switch behavior during development.
Option 1) is the easiest and probably a better option between the two. With the option 1), users expect they are using the chosen go version when they run 'go' inside the module directory. Most go commands indeed meet the expectation: However, As @dominikh explained, this does not work nicely if the tool's module cannot set its go.mod to use the latest go version. I can think of various reasons the module that includes the tool cannot update their go.mod more aggressively. I understand that Then, I think this is a bug. The fix can be, I think, something similar to how
|
Hi, after discussing with @hyangah and with @rsc and @samthanawalla, we've decided to change the toolchain switching behavior for go install package@version and go run package@version: Currently it essentially runs in a new empty module and adds a dependency to package@version to that module. This would ensure that the go version used to install the toolchain is at least the version reported by running This has the same behavior proposed by @hyangah in #66518 (comment) I think this should clear up the confusion around running |
Go version
that's a good question!
Output of
go env
in your module/workspace:What did you do?
As the author of Staticcheck, I tell my users that to support Go 1.22 code, they have to build Staticcheck with Go 1.22. To assure me that they did, they show me this:
The problem is that the user's local toolchain is Go 1.21.8, but the module they're currently in is specifying
go 1.22.1
in its go.mod. Runninggo version
downloads and runs the newer toolchain, as doesgo install .
, butgo install honnef.co/[...]
does not.This is problematic in a multitude of ways.
That
go install
behaves this way is documented ingo help install
asThis, however, predates the automatic upgrades. In my experience, users who are aware of automatic upgrades think of it as "First,
go
downloads the specified toolchain, then it runs the subcommand", which is true in most, but not all cases.The issue I am filing is really a mix of two user reports, one from the perspective of a tool maintainer, and one from the perspective of a user. What they have in common is confusion over the effective Go version.
To avoid any confusion I've included a sample shell session demonstrating the current behavior.
The text was updated successfully, but these errors were encountered: