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

Feature request: Bundler/GemsSpecifySemanticVersion #7669

Closed
ianfixes opened this issue Jan 24, 2020 · 11 comments
Closed

Feature request: Bundler/GemsSpecifySemanticVersion #7669

ianfixes opened this issue Jan 24, 2020 · 11 comments

Comments

@ianfixes
Copy link
Contributor

I'd like to enforce that gems in my Gemfile are all specified with a semantic version string -- e.g. the ~>1.7 in

  gem 'foobar_thing', '~>1.7'

My understanding is that there are no good reasons to omit this version specifier; the "worst case" that still counts as a best practice is to simply use a greater-than operator.

I have a basic implementation of this that doesn't choke on special cases like GitHub-based dependencies:

# Load all declared gems from gemfile
dependencies = Bundler::Definition.build('Gemfile', nil, nil).dependencies

# Separate git-based dependencies from others (proper processing between ref / version TBD)
git_deps, other_deps = dependencies.partition { |d| d.source.class == Bundler::Source::Git }

# Version of "0" is the default if unspecified
unversioned_deps = other_deps.select {|d| d.requirement.requirements[0][1].version == "0"}

# print results
puts "Github-based gems: #{git_deps.size}"
git_deps.map(&:name).sort.each { |n| puts "  #{n}" }
puts
puts "Gemfile gems without semver: #{unversioned_deps.size}"
unversioned_deps.map(&:name).sort.each { |n| puts "  #{n}" }

Is this something that could be added to the list of Bundler Cops?

@bbatsov
Copy link
Collaborator

bbatsov commented Feb 6, 2020

Yeah, I'd welcome a cop checking for this. PR welcome!

@Drenmi
Copy link
Collaborator

Drenmi commented Feb 6, 2020

Just to clarify, the cop is to ensure there is any version string?

One reason for omitting it is some teams commit to "continuous upgrades" and use bots to make PRs to upgrade gems as soon as new versions are released. 🙂

@ianfixes
Copy link
Contributor Author

ianfixes commented Feb 6, 2020

PR welcome

@bbatsov I did some digging and found https://docs.rubocop.org/en/latest/development/#add-a-new-cop but I'd appreciate your guidance on what you'd like me to name it (i.e. is the name suggested in this issue title the right one?). Also, I'm not sure where to find an example of a cop that only works on one type of file (or in this case, by running a single command against the project itself). Do I need to do anything special there?

the cop is to ensure there is any version string?

@Drenmi yes. The workflow you describe sounds like you would have this in your Gemfile:

gem 'rubocop'

Would it be a problem for you to have this instead?

gem 'rubocop', '>= 0.0.1'

I suppose you could always disable that cop for your own project.

@Drenmi
Copy link
Collaborator

Drenmi commented Feb 7, 2020

@ianfixes Not a problem per se, but there is a piece of information in there posing as if it's relevant when it is not, as it is just an arbitrary lowest version. 🙂

Most of our cops are configurable. It'd be great if the cop could be configured to enforce no version constraint, too.

@koic
Copy link
Member

koic commented Feb 7, 2020

One reason for omitting it is some teams commit to "continuous upgrades"

I completely agree with this opinion.
I think the new feature cop should be disabled by default. Preferably, only those users who need a version specification enable it.

@ianfixes
Copy link
Contributor Author

ianfixes commented Feb 7, 2020

It'd be great if the cop could be configured to enforce no version constraint, too.

I think this would be easy to accomplish. It had honestly never crossed my mind that "don't use version constraints" was a best practice on par with "use pessimistic version constraints".

I appreciate the feedback here, because worst case for me is that I start down the path of implementing something that has no chance of being accepted.

@waghanza
Copy link

Hi,

I always favor pessimistic version constraints, I have bots that ensure some upgrades, but with PR (and then a CI trigger).

It is out of the question, for me, to build some reliable services without any version constraints (at least on production group).

I'll be glad to create a cop that check for this, but

  • disable by default
  • allowing to specify gem groups
  • allow to specify format (I prefer X.Y.Z but some developers could prefer to specify only X.Y)

Regards,

@ianfixes
Copy link
Contributor Author

I'm stuck waiting on 3 things before I can work on a PR for this

  • an example of a cop that only works on one type of file (or in this case, by running a single command against the project itself)
  • guidance on what options the cop must support so as to allay the concerns in this thread
  • some idea of how to come up with file/line numbers given that gems can come from both Gemfile and *.gemspec

@stale
Copy link

stale bot commented Sep 13, 2020

This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contribution and understanding!

@stale stale bot added the stale Issues that haven't been active in a while label Sep 13, 2020
@ianfixes
Copy link
Contributor Author

Bump, please advise on what options this cop would have to support in order to be considered as a mergeable contribution

@stale stale bot removed the stale Issues that haven't been active in a while label Sep 14, 2020
@timlkelly
Copy link
Contributor

timlkelly commented Apr 21, 2021

@ianfixes I've recently added a custom cop that checks for this in a private repo. It doesn't support all of the use cases listed in this thread (checking.gemspec files and require the absence of a version declaration). That said, I don't think that's a huge lift to add.

I used GemComment as an example. I think that's a good place to look to. I would be happy to collaborate with the work I have so far.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

6 participants