Ruby 3.0 - 引数の数が間違っています (3 が指定され、1..2 が予想されます)
概要
uk_postcode gem を使用するプロジェクトがあります。次のようなバリデータクラスがあります。
class UkPostcodeValidator < ActiveModel::EachValidator
def validate_each(record, attribute, value)
postcode = UKPostcode.parse(value.to_s)
return if postcode.full_valid?
record.errors.add attribute, :invalid_uk_postcode, options
end
end
上記は Ruby 2.7.6 では正常に動作していましたが、Ruby 3.0.0 に更新する必要があります。これを実行すると、テストが壊れて次のエラーが発生します。
Failure/Error: record.errors.add attribute, :invalid_uk_postcode, options
ArgumentError:
wrong number of arguments (given 3, expected 1..2)
私のRubyとRailsの知識はまだ十分ではありませんが、オンラインでたくさん検索してさまざまなことを試した結果、record.errors.add属性、:invalid_uk_postcode、オプションをrecord.errors.add属性、:invalid_uk_postcode、optionsに変更することがわかりました。テストを修正します。したがって、最後の引数に を追加するとテストが修正され、検証が通常どおり動作するように見えます。これまで読んだことから、引数はより具体的である必要があり、**を追加することでキーワード引数になります(任意の型/値を取ることができると想定しています)が、私は専門家ではないので、 Ruby と Rails の専門家ではありますが、これを正しく理解するというよりは推測にすぎません。
誰かがもっと上手にガイドしてくれるでしょうか?上記の変更はこのように修正しても問題ないと思われますか?最後の引数に ** を追加するとエラーの問題が解決するのはなぜですか?
atm、どのオプションがどのようなことを指しているのか、そして将来的には何かを調べているのかわかりませんが、知っていて答えられる人はよろしくお願いします。ありがとう
オンラインでエラーを検索すると、Ruby の構文に変更があることがわかります。これを理解しようとしています。
解決策
キーワード引数が位置引数から完全に分離されるようになりました。
def new_style(name, **options)
end
new_style('John', {age: 10})
# Ruby 2.6: works
# Ruby 2.7: warns: Using the last argument as keyword parameters is deprecated; maybe ** should be added to the call
# Ruby 3.0: ArgumentError (wrong number of arguments (given 2, expected 1))
new_style('John', age: 10)
# => works
h = {age: 10}
new_style('John', **h)
# => works, ** is mandatory
add メソッドの定義は次のとおりです。
def add(attribute, type = :invalid, **options)
したがって、** なしでオプションにハッシュを渡すことは現在サポートされていません。代わりに、次のようにキーワード引数として直接渡すことができます。これが ** の動作です。
record.errors.add attribute, :invalid_uk_postcode, count: 25, other_attr: 'any text'
詳細な記事はこちら: https://www.ruby-lang.org/en/news/2019/12/12/separation-of-positional-and-keyword-arguments-in-ruby-3-0/