Skip to content
This repository has been archived by the owner on Nov 30, 2024. It is now read-only.

[bugfix] Properly detect kwargs hashes vs optional positional args #594

Closed
wants to merge 5 commits into from

Conversation

malcolmohare
Copy link
Contributor

@malcolmohare malcolmohare commented Feb 25, 2024

Attempting to fix https://github.com/rspec/rspec-expectations/issues/1451

Refactor has_kw_args_in?:

  • try to use positional parameter information to determine whether a hash is kw_args
  • try to leverage information passed by the ruby2_keywords annotation
  • fallback to inspection of keyword args to determine if they look valid or not

Added backwards compatible ruby2_keywords wrapping to the necessary methods (valid? and error_for) in the spec files like so:
ruby2_keywords(:valid?) if respond_to?(:ruby2_keywords, true)

Also needed to modify how args are passed to the MSV split_args so that the special kwargs markings are not lost.

@pirj

This comment was marked as resolved.

@malcolmohare malcolmohare force-pushed the rspec-expectation-1451 branch from 0645cdf to 2b4d422 Compare February 25, 2024 13:51
@malcolmohare malcolmohare force-pushed the rspec-expectation-1451 branch from d61bf73 to c0ea86c Compare February 25, 2024 14:01
@malcolmohare malcolmohare requested a review from pirj February 25, 2024 14:03
@malcolmohare malcolmohare force-pushed the rspec-expectation-1451 branch from 990054f to 6eb38eb Compare February 26, 2024 19:03
@malcolmohare malcolmohare force-pushed the rspec-expectation-1451 branch 2 times, most recently from 75432d1 to fd1dbb6 Compare February 27, 2024 15:56
@malcolmohare
Copy link
Contributor Author

Fully backwards compatible, just need to fix 3.2 and up. The behavior of ruby2_keywords changed between 3.1 and 3.2: https://rubyreferences.github.io/rubychanges/3.2.html#keyword-argument-separation-leftovers

Comment on lines 306 to 311
def initialize(signature, args=[])
@signature = signature
@non_kw_args, @kw_args = split_args(*args)
@non_kw_args, @kw_args = split_args(args.clone)
@min_non_kw_args = @max_non_kw_args = @non_kw_args
@arbitrary_kw_args = @unlimited_args = false
end
Copy link
Contributor Author

@malcolmohare malcolmohare Feb 27, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

something had to change here. Splatting the args meant the special marking for the kwargs hash gets lost. This doesnt happen to functions with the ruby2_keywords... except it won't apply here because this function doesn't take the *args input. So either the args array is cloned (which persists the special flagging) or the input to this function needs to swap to using *args. I figured cloning was the less obtrusive change. The split_args function is private so changing its signature was not something that has compatibility concerns.

@JonRowe
Copy link
Member

JonRowe commented Nov 30, 2024

Apologies I never got round to looking at this, I've migrated it over to the monorepo as rspec/rspec#121 I'm hoping to do a big refactoring of keyword argument support with RSpec 4 dropping older ruby support.

@JonRowe JonRowe closed this Nov 30, 2024
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants