Skip to content

Fix pp when passed a empty ruby2_keywords-flagged hash as array element#2966

Merged
nurse merged 2 commits into
ruby:ruby_2_7from
jeremyevans:ruby-2-7-pp-ruby2_keywords_hash
Mar 31, 2020
Merged

Fix pp when passed a empty ruby2_keywords-flagged hash as array element#2966
nurse merged 2 commits into
ruby:ruby_2_7from
jeremyevans:ruby-2-7-pp-ruby2_keywords_hash

Conversation

@jeremyevans

Copy link
Copy Markdown
Contributor

This causes problems because the hash is passed to a block not
accepting keywords. Because the hash is empty and keyword flagged,
it is removed before calling the block. This doesn't cause an
ArgumentError because it is a block and not a lambda. Just like
any other block not passed required arguments, arguments not
passed are set to nil.

Issues like this are a strong reason not to have ruby2_keywords
by default.

Fixes [Bug #16519]

This backports 28d31ea and
0ea759e, but needed to be modified
for 2.7 as 2.7 will perform empty keyword to positional hash
conversion for required arguments, which will happen if "v" in the
seplist method is empty when yielded.

This causes problems because the hash is passed to a block not
accepting keywords.  Because the hash is empty and keyword flagged,
it is removed before calling the block.  This doesn't cause an
ArgumentError because it is a block and not a lambda.  Just like
any other block not passed required arguments, arguments not
passed are set to nil.

Issues like this are a strong reason not to have ruby2_keywords
by default.

Fixes [Bug ruby#16519]

This backports 28d31ea and
0ea759e, but needed to be modified
for 2.7 as 2.7 will perform empty keyword to positional hash
conversion for required arguments, which will happen if "v" in the
seplist method is empty when yielded.
Comment thread lib/pp.rb
yield(*v)
case v.last
when Hash
if Hash.ruby2_keywords_hash?(v.last)

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Doesn't Hash.ruby2_keywords_hash? allow any object?
If so it could be simplified to:

if Hash.ruby2_keywords_hash?(v.last)
  yield(*v, **{})
else
  yield(*v)
end

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

No, I tried that first.

@eregon eregon Mar 19, 2020

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Mmh, that's really unfortunate, I'll file an issue for it.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

@nurse nurse added this to the v2.7.1 milestone Mar 30, 2020
@nurse nurse added the 2.7.1 label Mar 30, 2020
@nurse nurse self-assigned this Mar 30, 2020
@nurse nurse merged commit bb93659 into ruby:ruby_2_7 Mar 31, 2020
@hsbt hsbt added the Backport label Sep 5, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants