こんにちは!石田佳介です!
僕がインターン生として実務に入っていて、一つ気になったことがあったのです。
rubyのコードでこのようなコードを見たことがありませんか?
<div class="hoge">
<%= @books.each do |book| %>
<p><%= book.title %></p>
<p><%= book.body %></p>
<% end %>
</div>
この書き方って不自然じゃないですか?
rubyの公式のドキュメントにもこう書いてありました
xxx.yyy
オブジェクトのメソッド
公式ドキュメントのいう通りだとするならば、titleやbookはメソッドになるよなっておもったわけです。titleやbookってカラムじゃね?って思ったので、変だなって思いました。
そこで自分なりに調べてまとめましたので、この記事を読んで理解してみてください。
今回この謎を解決するためには、2つのものを理解しなければなりません。
①activerecord
②ゲッターとセッター
①activerecord
activerecordとはざっくりいうと、データベースから情報をとってくるとき、普通だったらSQLを使わないといけなません。でも、activerecordというもののおかげで、SQLをたたかなくても、直感的に、そしてrailsらしく簡単にデータベースの情報をとってくれるというものです。
コードでいうと、
User.all
User.find_by(params[:id])
こんな感じで、簡単なコードでデータベースから情報をとってこれるのは、activerecordのおかげなんです。
②セッターとゲッター
これを理解するためには、インスタンス変数の基本的な知識が必要になってきますので、上にあげたぼくの記事を読んでみてください。
そしてインスタンス変数は、基本的に定義されているクラス内でしか使えないんですね。
例えば
user.rb
@users = User.all
group.rb
@groups = @users.comment #適当に書いたので 、ご容赦ください。
このように、書くと書くとgroup.rbファイルで、エラーが起きるんですね。
これは、Ruby on Railsの規則で、インスタンス変数はそのクラス内でしか使えないというルールがあるんです。
でも、この例でいえば、「他のファイルで@usersを使いたいなー」ってなることがありますよね。
じゃあそんな時、どうしたらいいのか。それを解決してくれるのが、
セッターとゲッターです。
具体的にコードを見ていきましょう。
user.rb
class User
def initialize(name) #セッター
@name = name
end
def getName #ゲッター
@name
end
end
initializeメソッドに関しては、こちらのリンクを参考にしてみてください。
要は、newメソッドが呼び出されたときに、自動的にやってほしいメソッドのことです。
まず、セッターというのは、インスタンス変数をどのクラスでも使えるようにするための下準備をしていると考えてください。名前の通り、インスタンス変数をセッティングしているんです。
ゲッターでは、実際にセッティングされたものをゲットしているんです。ホント名前の通りです(笑)
バレーでもセッターがいるから、ポイントをゲッティングできるんですね!(僕は野球やってました)
このようにすることで、インスタンス変数をクラス外でも参照できるようになるんですね。
##activerecordとセッターとゲッターの関係性
今回の話の結論を最初にいいます。
activerecordにおいて、カラムのデータを取り出すために、カラム名と同じ名前のメソッドが自動で作成されている
ということです。
どういうことか?
先ほどの例でいえば、
user.rb
class User
def initialize(name) #セッター
@name = name
end
def getName #ゲッター
@name
end
end
これぜーんぶが、acctiverecordによって、カラム名と同じ名前のメソッドが自動的に作成されるんです。
だからこそ、
<div class="hoge">
<%= @books.each do |book| %>
<p><%= book.title %></p>
<p><%= book.body %></p>
<% end %>
</div>
この例でいうと、title、bodyなどのカラム名だとおもわれていたものが、
実はカラム名と同じメソッドをactiverecordが自動で作成していたからこそできたことだったのです。
activerecordはさすがですな!