Bug #14726
closedwrong message when superclass is not a Class
Description
クラス定義の際に親クラスとしてClass
でないものを与えるとTypeError
になりますが、その際にエラーメッセージに与えられたもののクラス名が表示されるため、メッセージだけ見ると何が間違ってるのかわけがわからなくなっています。
class C1; end
class C2 < C1.new; end #=> TypeError (superclass must be a Class (C1 given))
ここはクラス名ではなく与えられたオブジェクトそのものを表示すべきではないでしょうか?
Index: class.c
===================================================================
--- class.c (revision 63310)
+++ class.c (working copy)
@@ -221,7 +221,7 @@
{
if (!RB_TYPE_P(super, T_CLASS)) {
rb_raise(rb_eTypeError, "superclass must be a Class (%"PRIsVALUE" given)",
- rb_obj_class(super));
+ super);
}
if (RBASIC(super)->flags & FL_SINGLETON) {
rb_raise(rb_eTypeError, "can't make subclass of singleton class");
Index: vm_insnhelper.c
===================================================================
--- vm_insnhelper.c (revision 63310)
+++ vm_insnhelper.c (working copy)
@@ -3150,7 +3150,7 @@
if (VM_DEFINECLASS_HAS_SUPERCLASS_P(flags) && !RB_TYPE_P(super, T_CLASS)) {
rb_raise(rb_eTypeError,
"superclass must be a Class (%"PRIsVALUE" given)",
- rb_obj_class(super));
+ super);
}
vm_check_if_namespace(cbase);
Files
Updated by yugui (Yuki Sonoda) over 6 years ago
どちらかというと元の仕様のほうに賛成で、これはバグではないという認識です。Classオブジェクトを期待していたのにC1オブジェクトが来たというのはどちらも super
の属するクラスの話をしていて、そのパッチよりもバランスが取れています。
このエラーメッセージが分かりにくいのは冠詞が抜けているからではないでしょうか。
- rb_raise(rb_eTypeError, "superclass must be a Class (%"PRIsVALUE" given)",
+ rb_raise(rb_eTypeError, "superclass must be a Class (given a %"PRIsVALUE")",
Updated by yugui (Yuki Sonoda) over 6 years ago
ああ、補足ですが、super
の属するクラスではなく super
の文字列表現を表示するというパッチの案に対しては、誤ってmoduleを渡した場合が心配です。
そのmoduleをクラスだと思い込んでいると却って分かりづらいのではないでしょうか。
Updated by usa (Usaku NAKAMURA) over 6 years ago
なるほど、確かに冠詞があればインスタンスが来たとわかるのでいいかも。
私の案だとモジュールが来た時わかりにくいというのも納得です。
Updated by usa (Usaku NAKAMURA) over 6 years ago
……で、不定冠詞を付ける場合、例えばInteger
のインスタンスが来たらan
にしないといけないのでは、という問題が……。
Updated by yugui (Yuki Sonoda) over 6 years ago
なるほど、それは気づきませんでした。すると、こうでしょうか。
rb_raise(rb_eTypeError, "superclass must be a Class (given a(n) %"PRIsVALUE")",
Updated by mame (Yusuke Endoh) over 6 years ago
くだらないコメントです。英語がわかりませんが、"given a XXX" の語順は変な気がします。"a XXX given" でいいような?
Updated by duerst (Martin Dürst) over 6 years ago
mame (Yusuke Endoh) wrote:
くだらないコメントです。英語がわかりませんが、"given a XXX" の語順は変な気がします。"a XXX given" でいいような?
念のためぐたいれいをみたいですが、"given a(n) XXX" は大丈夫かもしれません。"was XXX" はもうちょっと短くて簡単なのかもしれません。
Updated by mame (Yusuke Endoh) over 6 years ago
duerst (Martin Dürst) wrote:
mame (Yusuke Endoh) wrote:
くだらないコメントです。英語がわかりませんが、"given a XXX" の語順は変な気がします。"a XXX given" でいいような?
念のためぐたいれいをみたいですが、"given a(n) XXX" は大丈夫かもしれません。"was XXX" はもうちょっと短くて簡単なのかもしれません。
具体例は TypeError (superclass must be a Class (given a(n) C1))
になると思います。(カッコが 3 重でくどいですね)
Updated by jeremyevans0 (Jeremy Evans) about 5 years ago
It looks like this error message has not been changed. Attached is a patch with a slightly more verbose and descriptive error message:
class C1; end
C2 < C1.new; end
# TypeError (superclass must be an instance of Class (given an instance of C1))
I think this avoids the a/an/a(n) issue, and it helps users learn that classes are instances of Class
, which is an important part of understanding Ruby's object model. Thoughts?
Updated by jeremyevans (Jeremy Evans) about 4 years ago
- Status changed from Open to Closed
Applied in changeset git|ce9beb9d20187c861462282460b998684759e5e7.
Improve error message when subclassing non-Class
Fixes [Bug #14726]