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

Reference (compile-time type is Object+) error on Crystal 1.2.0+ #11787

Open
jwoertink opened this issue Jan 31, 2022 · 2 comments
Open

Reference (compile-time type is Object+) error on Crystal 1.2.0+ #11787

jwoertink opened this issue Jan 31, 2022 · 2 comments

Comments

@jwoertink
Copy link
Contributor

I have this code that works fine on Crystal 1.1.1, but on 1.2.0 I get a compile-time error

Showing last frame. Use --error-trace for full trace.

error in line 23
Error: undefined method 'name' for Reference (compile-time type is Object+)

I know there's some weirdness around using Object so generically, so in this case, changing it to Enumerable(Thing) fixes the error. However, my actual app is a bit more complicated of a fix.

class Thing
  property name : String
  
  def initialize(@name : String)
  end
end
 
class Decorator
  include Enumerable(Object)
  
  def initialize(@things : Array(Thing))
  end
  
  def each
  	@things.each do |t|
      yield t
    end
  end
end
 
dec = Decorator.new([Thing.new("foo")])
 
pp dec.find {|t| t.name == "foo" }

I'm ok with closing this out if this is intended, but I wanted to make sure it was at least reported just in case.

@Blacksmoke16 Blacksmoke16 added kind:regression Something that used to correctly work but no longer works topic:compiler and removed kind:bug labels Jan 31, 2022
@straight-shoota
Copy link
Member

I'd definitely say there are some weird things about this.

For example, I don't know how Enumerable(Object) was even working. I'd expected some error such as can't use Object as generic type argument or can't use Object as a Proc argument type. Both should be triggered by Enumerable(Object).

@HertzDevil
Copy link
Contributor

HertzDevil commented Feb 9, 2022

i believe generic modules are allowed to use type arguments that aren't usable as the type of a variable; for example Comparable(Array) is okay, even though a variable cannot have the type Array, because Comparable(T) only uses T in non-block parameter restrictions.

Enumerable(Object) indeed should still be disallowed because of #each(& : T ->). It is by sheer coincidence the code worked before 1.2.0, and methods that return an Array(T) would still break.

@HertzDevil HertzDevil added kind:bug and removed kind:regression Something that used to correctly work but no longer works labels Feb 9, 2022
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

4 participants