class Person < ActiveRecord::Base
validates_presence_of :first_name
end
validates_presence_of is a method call that is
specified outside of any method in class Person.
Could someone explain what the invocation model is
for that statement that is not bound to any method
within a class (i.e. when is that statement executed?)
Could someone explain what the invocation model is
for that statement that is not bound to any method
within a class (i.e. when is that statement executed?)
It’s the same, in the abstract, as the invocation model generally: a
“bareword”-style method is automatically invoked on the current
default object, self. At the outer level of a class definition, self
is the class object itself. So what you’re seeing is a call to a
class method.
Here’s a little X-ray of what’s going on:
class SomeClass
def self.do_something
puts “Hi!”
end
end
class C < SomeClass
puts “self right now is #{self}.” # self right now is C.
do_something # Hi!
end
There are more nuances but that’s the basic scenario.
Hmm validates_presence_of method is not “outside any method” in class
Person actually. Most probably (i.e taking into account rails meta
magic), validates_presence_of is a class method, which is defined in
class ActiveRecord::Base.
So, when Person class inherits ActiveRecord::Base class it also inherits
method validates_presence_of and above mentioned line invokes the method
with argument :first_name.
class Foobar
def self.sayfoo arg
puts “You said #{arg}”
end
end
class Baz < Foobar
sayfoo :rubyrocks
end
Output #=> “You said rubyrocks”
Unlike C++, where you can have class or instance methods of a class(i.e
static or normal methods of class) defined outside class definition, in
Ruby its always inside class.
Thanks Hemant. However, as I mentioned in my last reply, it is not clear
to me what triggers the execution of a statement such as “sayfoo
:rubyrocks” in your example. When the class is loaded, when an instance
is created, ???
Thanks.
P.
Hemant K. wrote:
On Thu, 2007-01-11 at 13:01 +0900, Paul S. wrote:
Hmm validates_presence_of method is not “outside any method” in class
Person actually. Most probably (i.e taking into account rails meta
magic), validates_presence_of is a class method, which is defined in
class ActiveRecord::Base.
So, when Person class inherits ActiveRecord::Base class it also inherits
method validates_presence_of and above mentioned line invokes the method
with argument :first_name.
class Foobar
def self.sayfoo arg
puts “You said #{arg}”
end
end
class Baz < Foobar
sayfoo :rubyrocks
end
Output #=> “You said rubyrocks”
Unlike C++, where you can have class or instance methods of a class(i.e
static or normal methods of class) defined outside class definition, in
Ruby its always inside class.
However, it is still not clear to me when these statements are invoked.
In your example, what triggers the execution of the 2 statements?
class C < SomeClass
puts “self right now is #{self}.” # self right now is C.
do_something # Hi!
end
When the class is loaded, when an instance of that class is created?
Is this similar to a static initialization block in Java?
P.
Could someone explain what the invocation model is
for that statement that is not bound to any method
within a class (i.e. when is that statement executed?)
It’s the same, in the abstract, as the invocation model generally: a
“bareword”-style method is automatically invoked on the current
default object, self. At the outer level of a class definition, self
is the class object itself. So what you’re seeing is a call to a
class method.
Here’s a little X-ray of what’s going on:
class SomeClass
def self.do_something
puts “Hi!”
end
end
class C < SomeClass
puts “self right now is #{self}.” # self right now is C.
do_something # Hi!
end
There are more nuances but that’s the basic scenario.
Thanks Hemant. However, as I mentioned in my last reply, it is not clear
to me what triggers the execution of a statement such as “sayfoo
:rubyrocks” in your example. When the class is loaded, when an instance
is created, ???
Thanks.
On a broader perspective, we can say when the class is loaded, when you
define a class like this in your code:
class Baz < Foobar
sayfoo :rubyrocks
end
An object called Baz starts to exist in current Runtime, which is an
instance of class Class.
So, when method sayfoo gets invoked when object Baz is created or in
other words, we can say when class is loaded.
When the class is loaded, when an instance of that class is created?
Is this similar to a static initialization block in Java?
P.
Hemant may have already answered your question, but as an aside the
easiest way to check these things in Ruby is to use irb to test:
irb(main):001:0> class A
irb(main):002:1> def self.doit
irb(main):003:2> puts “hi”
irb(main):004:2> end
irb(main):005:1> end
=> nil
irb(main):006:0> class B < A
irb(main):007:1> puts “self: #{self}”
irb(main):008:1> doit
irb(main):009:1> end
self: B
hi
=> nil
irb(main):010:0> A.new
=> #<A:0x340fe4>
irb(main):011:0> B.new
=> #<B:0x33aab8>
Does that make it clearer? doit only gets run when the B class is
defined, not when an instance is created.
class Foo
puts “Inside Foo on line 4”
def bar
puts “Running #bar method (line 6)”
end
puts “All done with #{self} (line 8)”
end
Even more enlightening, add two lines:
class Foo
puts “Inside Foo on line 4”
p self.instance_methods(false)
def bar
puts “Running #bar method (line 7)”
end
p self.instance_methods(false)
puts “All done with #{self} (line 10)”
end
However, it is still not clear to me when these statements are invoked.
In your example, what triggers the execution of the 2 statements?
[snip]
When the class is loaded, when an instance of that class is created?
Is this similar to a static initialization block in Java?
Instead of asking and waiting for an answer, perhaps just try running
the following code:
puts “Line 1”
class Foo
puts “Inside Foo on line 4”
def bar
puts “Running #bar method (line 6)”
end
puts “All done with #{self} (line 8)”
end
to me what triggers the execution of a statement such as "sayfoo
:rubyrocks" in your example.
When the class is loaded, when
yes, when class is first loaded or redefined.
an instance is created, ???
no, otherwise it gets executed many times per instance (assumming of
course you just want it to run once You can use initialize() if you
want something invoked per instance-iation.
btw, you can monitor behavior using irb and debug. but in case you doubt
if they do some magic, you can also do tracing. try putting the ff code
at the beginning of the program you want to observe,