Forum: Ruby on Rails Confused over Model attrbutes and @ prefix

Announcement (2017-05-07): www.ruby-forum.com is now read-only since I unfortunately do not have the time to support and maintain the forum any more. Please see rubyonrails.org/community and ruby-lang.org/en/community for other Rails- und Ruby-related community platforms.
Joe (Guest)
on 2006-02-16 04:41
I'm confused about how attributes work in models. For example:

class Page < ActiveRecord::Base

  attr_accessor :body

  def foo
    id # works
    @id # won't work IIRC
    body # won't work
    @body #works
  end

end

Why doesn't everything work the same?

Joe
Dylan S. (Guest)
on 2006-02-16 04:47
(Received via mailing list)
somebody else can probably help you with a direct answer, but I think
"id"
is a reserved ActiveRecord attribute... but you'd probably want to check
the
docs.
Chris S. (Guest)
on 2006-02-16 04:53
Dylan S. wrote:
> somebody else can probably help you with a direct answer, but I think
> "id"
> is a reserved ActiveRecord attribute... but you'd probably want to check
> the
> docs.

I believe id is actually implemented as a method, because you can
override the primary key, but you still access it via "id".

"body" doesn't work because it could easily be a local variable in
method "foo", so you can use self.body I believe.  In fact, I think
self.id works as well.
Joe (Guest)
on 2006-02-16 04:57
Dylan S. wrote:
> somebody else can probably help you with a direct answer, but I think
> "id"
> is a reserved ActiveRecord attribute... but you'd probably want to check
> the
> docs.

It's not just 'id', but any other field that comes from the database.

Joe
Joe (Guest)
on 2006-02-16 05:13
Even more confused...


  def before_create
    self.file_extension = PAGE_FILE_EXTENSION # works
    file_extension = PAGE_FILE_EXTENSION # doesn't work
  end

  def body
    File.open(path, 'r').read if File.file?(path) # works
  end

  def path
    "#{CONTENT_PAGES}/#{id}.#{file_extension}" # works
  end

AAIIEEE!

Joe
Kent S. (Guest)
on 2006-02-16 05:26
(Received via mailing list)
On 2/15/06, Joe <removed_email_address@domain.invalid> wrote:
> Even more confused...
>
>
>   def before_create
>     self.file_extension = PAGE_FILE_EXTENSION # works
>     file_extension = PAGE_FILE_EXTENSION # doesn't work
>   end
>

The second assignment doesn't work simple because to Ruby you've just
declared a new variable file_extension which will go out of scope when
this method returns.

Kent.
www.datanoise.com
Tom M. (Guest)
on 2006-02-16 05:35
(Received via mailing list)
On Feb 15, 2006, at 7:13 PM, Joe wrote:

>   def before_create
>     self.file_extension = PAGE_FILE_EXTENSION # works
>     file_extension = PAGE_FILE_EXTENSION # doesn't work
>   end

Ok, I just ran into the same thing.

You can execute method via their name only, or self.method_name.

However, if you do assignment, it takes a straight name as a
local variable, that's why the second line in before_create
doesn't work, a local variable file_extension is getting set.

>   def body
>     File.open(path, 'r').read if File.file?(path) # works
>   end
>
>   def path
>     "#{CONTENT_PAGES}/#{id}.#{file_extension}" # works
>   end

Both reads, therefore they work.

--
-- Tom M.
Joe (Guest)
on 2006-02-16 05:35
Makes sense.

I guess in the path method, Ruby/Rails would first try to find a local
var 'file_extension', and if one didn't exist then it'd try accessing an
instance attribute/method?

>   def path
>     "#{CONTENT_PAGES}/#{id}.#{file_extension}" # works
>   end


Voodoo. I think there might be something to be said for requiring ()
after method calls, and referencing instance attributes with this
(self).

Joe
Guest (Guest)
on 2006-02-16 05:41
I think part of the reason for this confusion is that there doesn't seem
to be any clear explanation of when to use @attribute vs self.attribute.
This is also affected by class methods which people also seem to get
mixed up on.

I'm currently reading the Agile book and there is inconsistent usage of
self.attribute, @attribute and also self.class_method and
Class.class_method within various Model sample code. Other than the
explanation of defining class methods as self.method_name, there does
not appear to be any discussion of self vs. @

While the distinction seems to be much clearer with straight Ruby code,
it's unclear what is the proper usage within Rails with all the built-in
class methods and attributes from ActiveRecord
Pat M. (Guest)
on 2006-02-16 05:47
(Received via mailing list)
I'm not sure where the confusion is.  If you're using an AR object, it
automatically creates methods.  You never do something like
@attribute, unless that attribute isn't a database field.  My only
guess is that you're thinking of the Cart model, which is not an AR
class.  It's a straight Ruby class so you have to use the standard
Ruby syntax, no special methods are created.

Pat
Chris S. (Guest)
on 2006-02-16 05:48
Guest wrote:
> I think part of the reason for this confusion is that there doesn't seem
> to be any clear explanation of when to use @attribute vs self.attribute.
> This is also affected by class methods which people also seem to get
> mixed up on.
>
> I'm currently reading the Agile book and there is inconsistent usage of
> self.attribute, @attribute and also self.class_method and
> Class.class_method within various Model sample code. Other than the
> explanation of defining class methods as self.method_name, there does
> not appear to be any discussion of self vs. @
>
> While the distinction seems to be much clearer with straight Ruby code,
> it's unclear what is the proper usage within Rails with all the built-in
> class methods and attributes from ActiveRecord

It seems to me that using @ should be reserved for those slightly more
hidden values of a class, and use self for everything else.  I would
think using methods would be better in general because then if you can
make the change within that method (getter/setter).  That is what makes
overriding column accessors in AR so easy.
This topic is locked and can not be replied to.