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

RFC: obey user specific dist-tag #607

Open
wants to merge 2 commits into
base: main
Choose a base branch
from
Open

RFC: obey user specific dist-tag #607

wants to merge 2 commits into from

Conversation

gemwuu
Copy link

@gemwuu gemwuu commented Jun 29, 2022

When running npm install pkg@latest-1, npm should provide a way to save latest-1 into package.json.

References

@MondoGao
Copy link

MondoGao commented Jun 29, 2022

Personally speaking, saving a special dist-tag to package.json doesn't seem a good idea to me.
"beta" or "beta-2" can be acceptable, but what if "latest"? It could point to any version of the package, and it's extremely unpredictable without lockfile.

@gemwuu
Copy link
Author

gemwuu commented Jun 29, 2022

Personally speaking, saving a special dist-tag to package.json doesn't seem a good idea to me. "beta" or "beta-2" can be acceptable, but what if "latest"? It could point to any version of the package, and it's extremely unpredictable without lockfile.

Normally, installing a pkg simply using npm i pkg and saving the semantic version(say ^1.1.2) into package.json are safe, compatible and reasonable. The same behavior runs predictable when using npm i pkg@latest too.

But what if I want a latest tag in my package.json? For now, the only way is to manually change the ^1.1.2 to latest. Of course, latest may not be a proper and normal case, latest-x would be much better.

This RFC is to meet the requirement above. If I want a pkg@latest-x in my package.json, I can use npm i pkg@latest-x --save-tag to clarify my intention. If I want a semantic version of pkg@latest-x, then I shall use npm i pkg@latest-x

@ljharb
Copy link
Contributor

ljharb commented Jun 29, 2022

It’s very true that saving any tag - not just latest - will open the user up to silent breaking changes, which is why saving anything but a semver range to package.json is a bad practice.

What is your use case where you need to depend on the tag, but can’t depend on a semver range based on what it resolves to?

@wesleytodd
Copy link

What is your use case where you need to depend on the tag, but can’t depend on a semver range based on what it resolves to?

Automated prereleases for PRs is my use case. We have a tool which publishes on PRs with a generated prerelease and a dist-tag to track it. So you can say "I want to depend on the work happening in this pr, even it if is changed". Today you need to manually edit the package.json, instead I would like my automated tooling to comment on the pr with "to test this, run npm i pkg@pr-tag --save-tag".

Additionally, I think there is very little difference between * and latest in that it allows a user to opt into possibly breaking changes, so I am not sure there is any new risk here.

@wesleytodd
Copy link

And to be clear, I do not think it is a best practice to do * or latest or any dist tag in a production app or library. But again, it is already possible and frowned upon so this opens new UX while not introducing new risk of misuse.

@killagu
Copy link

killagu commented Jul 4, 2022

@ljharb We know */latest is bad practice, but in same case, we trust the tag, like dev tag or stable tag. So let we have the choice to use --save-tag or not

@ljharb
Copy link
Contributor

ljharb commented Jul 4, 2022

Why do you trust the tag? There's the same lack of guarantee as latest has.

@killagu
Copy link

killagu commented Jul 4, 2022

Because the tag is generate by myself or platform i trust.

@killagu
Copy link

killagu commented Jul 4, 2022

In the pre-release scenario,semver may not works well. If I have two dev branch, foo and bar, I'll release two version, 1.0.0-foo.alpha.0 and 1.0.0-bar.alpha.0. If ^1.0.0-foo.alpha.0 save to the package.json, 1.0.0-bar.alpha.0 will install. So in this case should save dust-tag to package.json.

It's just for the test case, at last should release the latest version and modify the package.json.

@ljharb
Copy link
Contributor

ljharb commented Jul 4, 2022

Having multiple release channels on the same major, let alone minor and patch, seems like an untenable use of semver to me.

@killagu
Copy link

killagu commented Jul 5, 2022

The bug fix/new feature will release in a new version, but not know in dev stage. Do we have best practice for this scenario?

@ljharb
Copy link
Contributor

ljharb commented Jul 5, 2022

I'm not sure what you mean. If you have a bugfix, it's a patch; if it's a new feature, it's a minor; and if you don't want people to get those freely, then bump the major so they don't.

@gemwuu
Copy link
Author

gemwuu commented Jul 5, 2022

Let me try to get this straight. There are several popular npm packages that are not obey SEMVER rules, such as TypeScript (read more), Runing npm i typescript and saving the typescript@^4.7.4 won't always be safe for my project. The solution to this situation will be using patch versions, which npm doesn't support for now.

This RFC provides a best practice, if these prerequisites below are met, (take TypeScript for example):

  1. TypeScript add dist-tags for each incompatible minor or patch versions, like tag-47 for 4.7.xtag-48 for 4.8.x etc.
  2. npm provides a way to save tag if this is actually I want, like --save-tag.

The best practice of using TypeScript should be npm i typescript@tag-47 --save-tag, because only this way can I prevent my project from ci/cd failures when typescript team publishs 4.9.x and break some features I'm using.

FYI @ljharb @wesleytodd

@ljharb
Copy link
Contributor

ljharb commented Jul 5, 2022

No, the best practice for TS (and react) is to use ~, not ^.

@SchulteMarkus
Copy link

SchulteMarkus commented May 28, 2024

I'm with @gemwuu.

  1. Having "devDependencies": {"nx": "canary" in the package.json is working fine as time of writing (NPM v10.8.0) (at least once, initially)
  2. If you care about breaking/major changes, I wonder why NPM supports "devDependencies": {"nx": "*" (in the package.json) as time of writing

From my point of view, as (1) and (2) are given, it would be just consequent to do as this RFC suggests.

@ljharb
Copy link
Contributor

ljharb commented May 28, 2024

"x supports y" is never a defense or endorsement for using y.

@SchulteMarkus
Copy link

"x supports y" is never a defense or endorsement for using y.

I had muesli for breakfast today.

@ljharb
Copy link
Contributor

ljharb commented May 28, 2024

? my comment was a direct response to your point 2 in your comment. Why the nonsequitur?

@SchulteMarkus
Copy link

? my comment was a direct response to your point 2 in your comment. Why the nonsequitur?

The comment is not concrete, it does not contribute to the further development of the discussion

@ljharb
Copy link
Contributor

ljharb commented May 29, 2024

@SchulteMarkus it's quite concrete. You said

If you care about breaking/major changes, I wonder why NPM supports "devDependencies": {"nx": "*" (in the package.json) as time of writing

as an implication that because npm supports it, one should draw a conclusion from it. My reply was that npm's support for it is irrelevant to what one should do or should not do.

@SchulteMarkus
Copy link

SchulteMarkus commented May 31, 2024

as an implication that because npm supports it, one should draw a conclusion from it. My reply was that npm's support for it is irrelevant to what one should do or should not do.

Good software has few surprises - and I agree with @gemwuu that the current behaviour is surprising. To support major updates via ‘*’ on the one hand, and to exclude ‘latest’ on the other (because it would also bring major updates with it) is consequently wrong.

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 this pull request may close these issues.

6 participants