railsチュートリアルまとめ2 Toyアプリケーション

# 個人的リマインド用
参考
[Ruby on Rails チュートリアル プロダクト開発の０→１を学ぼう](https://railstutorial.jp/)

## 2 Toyアプリケーション
### ユーザーのモデル設計
今回のToyAppはtwitterでいうツイート機能だけを兼ね備えたもの
モデルとしては、UserモデルとMicropostモデルの2つがある

**users**
id | integer
name | string
email | string

**microposts**
id | integer
content | text 
user_id | integer
※マイクロポストをユーザーと関連づける必要がある。そのため、マイクロポストの投稿者を記録するためのuser_idを追加する。

### Usersリソース
ここではユーザー用のデータモデルを、そのモデルを表示するためのWebインターフェイスに従って実装する。このデータモデルとWebインターフェイスは、組み合わさってUsersリソースとなり、ユーザーというものをHTTPプロトコル経由で自由に作成・取得・更新・削除できるオブジェクトとみなすことができるようになる。

↑このUsersリソースはscaffoldで簡単に作成できてしまう。
```
rails g(generate) scaffold User name:string email:string

idはRailsによって自動的に主キーとしてデータベースに追加される
```
続いてデータベースをマイグレート(後で説明)する必要がある。
```
rails db:migrate
```
### ユーザーページを探検する
|URL|アクション|用途|
|---|---|---|
|/uers|index|すべてのユーザーを一覧するページ|
|/users/1|show|id=1のユーザーを表示するページ|
|/users/new|new|新規ユーザーを作成するページ|
|/users/1/edit|edit|id=1のユーザーを編集するページ|

URL末尾に/usersだったり/users/newを追加することで対応したページを見ることができる

### MVCの挙動
1.ブラウザから「/users」というURLのリクエストをRailsサーバーに送信する。
2.「/users」リクエストは、Railsのルーティング機構（ルーター）によってUsersコントローラ内のindexアクションに割り当てられる。
3.indexアクションが実行され、そこからUserモデルに、「すべてのユーザーを取り出せ」（User.all）と問い合わせる。
4.Userモデルは問い合わせを受け、すべてのユーザーをデータベースから取り出す。
5.データベースから取り出したユーザーの一覧をUserモデルからコントローラに返す。
6.Usersコントローラは、ユーザーの一覧を@users変数（@はRubyのインスタンス変数を表す）に保存し、indexビューに渡す。
7.indexビューが起動し、ERB（Embedded RuBy: ビューのHTMLに埋め込まれているRubyコード）を実行して HTMLを生成（レンダリング）する。
8.コントローラは、ビューで生成されたHTMLを受け取り、ブラウザに返す。

2について、ユーザーからリクエストされたURLを、Usersリソースで使うコントローラのアクションに割り当てるためのコードは次のようになる。
```
config/routes.rb

Rails.application.routes.draw do
  resources :users ←この記述
  root 'users#index'　←これをすれば初期画面がUsersコントローラのindexアクションに
end
```

**REST (REpresentational State Transfer)**
インターネットそのものやWebアプリケーションなどの、分散・ネットワーク化されたシステムやアプリケーションを構築するためのアーキテクチャスタイルの1つ。RailsアプリケーションにおけるRESTは、アプリケーションを構成するコンポーネント(ユーザーやマイクロポストなど)を「リソース」としてモデル化することを指す。これらのリソースはCRUD操作と、4つの基本的なHTTPrequestメソッド(POST/GET/PATCH/DELETE)の両方に対応している。

|HTTPリクエストメソッド|URL|アクション|用途|
|---|---|---|---|
|GET|/users|index|すべてのユーザーを一覧するページ|
|GET|/users/1|show|id=1のユーザーを表示するページ|
|GET|/users/new|new|新規ユーザーを作成するページ|
|POST|/users|create|ユーザーを作成するアクション|
|GET|/users/1/edit|edit|id=1のユーザーを編集するページ|
|PATCH|/users/1|update|id=1のユーザーを更新するページ|
|DELETE|/users/1|destroy|id=1のユーザーを削除するページ|

```
app/controllers/users_controller.rb

class UsersController < ApplicationController
  .
  .
  .
  def index
    @users = User.all
  end
  .
  .
  .
end
```
上の記述により、Usersモデルからすべてのユーザーの一覧を取り出し(4)、@usersという変数に保存(5)する。User.allはActiveRecordというRubyライブラリのおかげで、簡単な記述に抑えられている。

**Viewへ**
@users変数にユーザー一覧が保存されると、コントローラはビューを呼び出す。ちなみに、@から始まる変数を**インスタンス変数**という。Railsコントローラ内で宣言したインスタンス変数はビューでも使えるようになる。

```
app/views/users/index.html.erb

<p style="color: green"><%= notice %></p>

<h1>Users</h1>

<div id="users">
  <% @users.each do |user| %>
    <%= render user %>
    <p>
      <%= link_to "Show this user", user %>
    </p>
  <% end %>
</div>

<%= link_to "New user", new_user_path %>
```
この場合@usersの一覧を1行ごとにHTMLに出力している

### マイクロポストを探検する
Usersリソースと同様にMicropostsリソースを作成
```
rails g scaffold Micropost content:text user_id:integer
```
```
rails db:migrate
```
ルートに追加(自動でされてる)
```
config/routes.rb

Rails.application.routes.draw do
  resources :microposts ←これ
  resources :users
  root 'users#index'
end
```
|HTTPリクエストメソッド|URL|アクション|用途|
|---|---|---|---|
|GET|/microposts|index|すべてのマイクロポストを一覧するページ|
|GET|/microposts/1|show|id=1のマイクロポストを表示するページ|
|GET|/microposts/new|new|マイクロポストを新規作成するページ|
|POST|/microposts|create|マイクロポストを作成するアクション|
|GET|/microposts/1/edit|edit|id=1のマイクロポストを編集するページ|
|PATCH|/microposts/1|update|id=1のマイクロポストを更新するページ|
|DELETE|/microposts/1|destroy|id=1のマイクロポストを削除するページ|

### マイクロポストをマイクロにする
コンテントに文字数制限を加える。こういうときはバリデーション(validation)を使って制限する。
```
app/models/micropost.rb

class Micropost < ApplicationRecord
  validates :content, length: { maximum: 140 }
end
```

### ユーザーはたくさんマイクロポストを持っている
異なるデータモデル同士の関連付け。ユーザーとマイクロモデルの関係は**1対多**
```
app/model/user.rb

class User < ApplicationRecord
  has_many :microposts ←1側
end
```
```
app/model/micropost.rb

class Micropost < ApplicationRecord
  belongs_to :user　←多側
  validates :content, length: { maximum: 140 }
end
```
今回はmicropostsテーブルにuser_idカラムを作成していたから、RailsとActiveRecordがマイクロポストとユーザーを関連づけることが可能になった。

**Railsコンソールでの操作**
```
rails c #コンソール起動

first_user = User.first #ユーザーモデルの一番目を変数に格納

first_user.microposts #一番目のユーザーのマイクロポストを表示

micropost = first_user.microposts.first #一番目のユーザーの一番目のマイクロポストを格納

micropost.user #そのマイクロポストがあるユーザーを表示
```

### 継承について
モデルの継承構造
User.Micropostモデル < ApplicationRecord
ApplicationRecord < ActiveRecord::Base(データベースのカラムをRubyのように扱える)