13
12

More than 5 years have passed since last update.

あとでもっかい試す用 - Ruby on Rails 4.0 チュートリアル - 第五章

Last updated at Posted at 2013-08-30

Ruby on Rails チュートリアル 実例を使ってRailsを学ぼう 第5章を見ながらやったことを、あとでもう一度できるようにまとめます!!第五章!!

  • Bootstrap
  • パーシャル
  • Railsのルーティング
  • Asset Pipeline
  • Sass
  • RSpecリファクタリング

準備

$ git checkout -b filling-in-layout

ナビゲーションをつける

レイアウトファイルを修正

$ subl app/views/layouts/application.html.erb

<!DOCTYPE html>
<html>
  <head>
    <title><%= full_title(yield(:title)) %></title>
    <%= stylesheet_link_tag "application", media: "all",
                                           "data-turbolinks-track" => true %>
    <%= javascript_include_tag "application", "data-turbolinks-track" => true %>
    <%= csrf_meta_tags %>
    <!--[if lt IE 9]>
    <script src="http://html5shim.googlecode.com/svn/trunk/html5.js"></script>
    <![endif]-->
  </head>
  <body>
    <header class="navbar navbar-fixed-top navbar-inverse">
      <div class="navbar-inner">
        <div class="container">
          <%= link_to "sample app", '#', id: "logo" %>
          <nav>
            <ul class="nav pull-right">
              <li><%= link_to "Home",    '#' %></li>
              <li><%= link_to "Help",    '#' %></li>
              <li><%= link_to "Sign in", '#' %></li>
            </ul>
          </nav>
        </div>
      </div>
    </header>
    <div class="container">
      <%= yield %>
    </div>
  </body>
</html>

Homeページを修正

<div class="center hero-unit">
  <h1>Welcome to the Sample App</h1>

  <h2>
    This is the home page for the
    <a href="http://railstutorial.jp/">Ruby on Rails Tutorial</a>
    sample application.
  </h2>

  <%= link_to "Sign up now!", '#', class: "btn btn-large btn-primary" %>
</div>

<%= link_to image_tag("rails.png", alt: "Rails"), 'http://rubyonrails.org/' %>

画像をダウンロード

$ cd app/assets/images/
$ wget http://rubyonrails.org/images/rails.png
$ cd ../../..

bootstrapとカスタムCSS

Gemfileにbootstrap-sassを追加する。

$ subl Gemfile

 gem 'rails', '4.0.0'
+gem 'bootstrap-sass', '2.3.2.0'

 group :development, :test do
 gem 'sqlite3', '1.3.7'

bundle インストール

$ bundle install

Asset Pipelineと互換性を持つ為の設定をする。

$ subl config/application.rb

     # The default locale is :en and all translations from config/locales/*.rb,yml are auto loaded.
     # config.i18n.load_path += Dir[Rails.root.join('my', 'locales', '*.    {rb,yml}').to_s]
     # config.i18n.default_locale = :de
+
+    config.assets.precompile += %w(*.png *.jpg *.jpeg *.gif)
   end
 end


カスタムCSSを追加する為のファイルを作成する

$ touch app/assets/stylesheets/custom.css.scss
$ subl app/assets/stylesheets/custom.css.scss

+ @import "bootstrap";

さらにカスタムCSSを修正

$ subl app/assets/stylesheets/custom.css.scss

@import "bootstrap";

/* universal */

html {
  overflow-y: scroll;
}

body {
  padding-top: 60px;
}

section {
  overflow: auto;
}

textarea {
  resize: vertical;
}

.center {
  text-align: center;
}

.center h1 {
  margin-bottom: 10px;
}


/* typography */

h1, h2, h3, h4, h5, h6 {
  line-height: 1;
}

h1 {
  font-size: 3em;
  letter-spacing: -2px;
  margin-bottom: 30px;
  text-align: center;
}

h2 {
  font-size: 1.2em;
  letter-spacing: -1px;
  margin-bottom: 30px;
  text-align: center;
  font-weight: normal;
  color: #999;
}

p {
  font-size: 1.1em;
  line-height: 1.7em;
}

/* header */

#logo {
  float: left;
  margin-right: 10px;
  font-size: 1.7em;
  color: #fff;
  text-transform: uppercase;
  letter-spacing: -1px;
  padding-top: 9px;
  font-weight: bold;
  line-height: 1;
}

#logo:hover {
  color: #fff;
  text-decoration: none;
}

パーシャル (partial)

レイアウトファイルの内容を別ファイルに分ける。

$ subl app/views/layouts/_shim.html.erb

<!--[if lt IE 9]>
<script src="http://html5shim.googlecode.com/svn/trunk/html5.js"></script>
<![endif]-->

ヘッダーをパーシャルで定義。

$ subl app/views/layouts/_header.html.erb

<header class="navbar navbar-fixed-top navbar-inverse">
  <div class="navbar-inner">
    <div class="container">
      <%= link_to "sample app", '#', id: "logo" %>
      <nav>
        <ul class="nav pull-right">
          <li><%= link_to "Home",    '#' %></li>
          <li><%= link_to "Help",    '#' %></li>
          <li><%= link_to "Sign in", '#' %></li>
        </ul>
      </nav>
    </div>
  </div>
</header>

フッターも。

$ subl app/views/layouts/_footer.html.erb

<footer class="footer">
  <small>
    <a href="http://railstutorial.jp/">Rails Tutorial</a>
    by Michael Hartl
  </small>
  <nav>
    <ul>
      <li><%= link_to "About",   '#' %></li>
      <li><%= link_to "Contact", '#' %></li>
      <li><a href="http://news.railstutorial.jp/">News</a></li>
    </ul>
  </nav>
</footer>

レイアウトファイルにパーシャルを適用

$ subl app/views/layouts/application.html.erb

<!DOCTYPE html>
<html>
  <head>
    <title><%= full_title(yield(:title)) %></title>
    <%= stylesheet_link_tag "application", media: "all",
                                           "data-turbolinks-track" => true %>
    <%= javascript_include_tag "application", "data-turbolinks-track" =>    true %>
    <%= csrf_meta_tags %>
    <%= render 'layouts/shim' %>
  </head>
  <body>
    <%= render 'layouts/header' %>
    <div class="container">
      <%= yield %>
      <%= render 'layouts/footer' %>
    </div>
  </body>
</html>

フッターの見た目を良くする。CSS修正。

$subl app/assets/stylesheets/custom.css.scss

/* footer */

footer {
  margin-top: 45px;
  padding-top: 5px;
  border-top: 1px solid #eaeaea;
  color: #999;
}

footer a {
  color: #555;
}

footer a:hover {
  color: #222;
}

footer small {
  float: left;
}

footer ul {
  float: right;
  list-style: none;
}

footer ul li {
  float: left;
  margin-left: 10px;
}

SassとAsset Pipeline

アセットディレクトリ

  • app/assets: 現在のアプリケーション固有のアセット
  • lib/assets: あなたの開発チームによって作成されたライブラリ用のアセット
  • vendor/assets: サードパーティのアセット

マニフェストファイル

アセットファイルをどのように一つにするのかをRailsに伝える。

app/assets/stylesheets/application.css

プリプロセッサエンジン

coffeeスクリプト, scss, erbをコンパイルするプロセッサ。

SCSS

ネスト

.center {
  text-align: center;
}

.center h1 {
  margin-bottom: 10px;
}

↑これを↓こうかける。

.center {
  text-align: center;
  h1 {
    margin-bottom: 10px;
  }
}

変数

h2 {
  .
  .
  .
  color: #999;
}
.
.
.
footer {
  .
  .
  .
  color: #999;
}

↑これを↓こうかける。

$lightGray: #999;
.
.
.
h2 {
  .
  .
  .
  color: $lightGray;
}
.
.
.
footer {
  .
  .
  .
  color: $lightGray;
}

scssを使って書き換えたカスタムCSS

$ subl app/assets/stylesheets/custom.css.scss

@import "bootstrap";

/* mixins, variables, etc. */

$grayMediumLight: #eaeaea;

/* universal */

html {
  overflow-y: scroll;
}

body {
  padding-top: 60px;
}

section {
  overflow: auto;
}

textarea {
  resize: vertical;
}

.center {
  text-align: center;
  h1 {
    margin-bottom: 10px;
  }
}

/* typography */

h1, h2, h3, h4, h5, h6 {
  line-height: 1;
}

h1 {
  font-size: 3em;
  letter-spacing: -2px;
  margin-bottom: 30px;
  text-align: center;
}

h2 {
  font-size: 1.2em;
  letter-spacing: -1px;
  margin-bottom: 30px;
  text-align: center;
  font-weight: normal;
  color: $grayLight;
}

p {
  font-size: 1.1em;
  line-height: 1.7em;
}


/* header */

#logo {
  float: left;
  margin-right: 10px;
  font-size: 1.7em;
  color: white;
  text-transform: uppercase;
  letter-spacing: -1px;
  padding-top: 9px;
  font-weight: bold;
  line-height: 1;
  &:hover {
    color: white;
    text-decoration: none;
  }
}

/* footer */

footer {
  margin-top: 45px;
  padding-top: 5px;
  border-top: 1px solid $grayMediumLight;
  color: $grayLight;
  a {
    color: $gray;
    &:hover {
      color: $grayDarker;
    }
  }
  small {
    float: left;
  }
  ul {
    float: right;
    list-style: none;
    li {
      float: left;
      margin-left: 10px;
    }
  }
}

Railsのルート

テストを名前付きルートを使ったものに修正する。

$ spec/requests/static_pages_spec.rb

require 'spec_helper'

describe "Static pages" do

  describe "Home page" do

    it "should have the h1 'Sample App'" do
      visit root_path
      expect(page).to have_content('Sample App')
    end

    it "should have the base title" do
      visit root_path
      expect(page).to have_title("Ruby on Rails Tutorial Sample App")
    end

    it "should not have a custom page title" do
      visit root_path
      expect(page).not_to have_title('| Home')
    end
  end

  describe "Help page" do

    it "should have the h1 'Help'" do
      visit help_path
      expect(page).to have_content('Help')
    end

    it "should have the title 'Help'" do
      visit help_path
      expect(page).to have_title("Ruby on Rails Tutorial Sample App | Help")
    end
  end

  describe "About page" do

    it "should have the h1 'About Us'" do
      visit about_path
      expect(page).to have_content('About Us')
    end

    it "should have the title 'About Us'" do
      visit about_path
      expect(page).to have_title("Ruby on Rails Tutorial Sample App | About Us")
    end
  end

  describe "Contact page" do

    it "should have the content 'Help'" do
      visit contact_path
      expect(page).to have_content('Contact')
    end

    it "should have the title 'Contact'" do
      visit contact_path
      expect(page).to have_title("Ruby on Rails Tutorial Sample App | Contact")
    end
  end
end

テストする

$ bundle exec rspec spec/requests/static_pages_spec.rb
=> 名前付きルートが定義されてないから失敗する。

ルートの定義を修正する。

$ subl config/routes.rb

 SampleApp::Application.routes.draw do
-  get "static_pages/home"
-  get "static_pages/help"
-  get "static_pages/about"
-  get "static_pages/contact"
+  root  'static_pages#home'
+  match '/help',    to: 'static_pages#help',    via: 'get'
+  match '/about',   to: 'static_pages#about',   via: 'get'
+  match '/contact', to: 'static_pages#contact', via: 'get'
+  match '/about', to: 'static_pages#about',  via: 'get'

match '/about', to: 'static_pages#about', via: 'get'
↑このコードは、↓この名前付きルートを生成する

about_path -> '/about'
about_url  -> 'http://localhost:3000/about' 

レイアウトファイルのリンクを修正

ヘッダ

$ subl app/views/layouts/_header.html.erb 

<header class="navbar navbar-fixed-top navbar-inverse">
  <div class="navbar-inner">
    <div class="container">
      <%= link_to "sample app", root_path, id: "logo" %>
      <nav>
        <ul class="nav pull-right">
          <li><%= link_to "Home",    root_path %></li>
          <li><%= link_to "Help",    help_path %></li>
          <li><%= link_to "Sign in", '#' %></li>
        </ul>
      </nav>
    </div>
  </div>
</header>

フッタ

$ subl touch app/views/layouts/_footer.html.erb

<footer class="footer">
  <small>
    <a href="http://railstutorial.jp/">Rails Tutorial</a>
    by Michael Hartl
  </small>
  <nav>
    <ul>
      <li><%= link_to "About",   about_path %></li>
      <li><%= link_to "Contact", contact_path %></li>
      <li><a href="http://news.railstutorial.jp/">News</a></li>
    </ul>
  </nav>
</footer>

RSpecを洗練させる

RSpecユーティリティ用ファイルを作成

$ subl spec/support/utilities.rb

def full_title(page_title)
  base_title = "Ruby on Rails Tutorial Sample App"
  if page_title.empty?
    base_title
  else
    "#{base_title} | #{page_title}"
  end
end

RSpecをもっとシンプルに書く

$ subl spec/support/utilities.rb

require 'spec_helper'

describe "Static pages" do
  subject { page }

  describe "Home page" do

    before {visit root_path}
    it {should have_content('Sample App')}
    it {should have_title(full_title(''))}
    it {should_not have_title('| Home')}

  end

  describe "Help page" do

    before {visit help_path}
    it {should have_content('Help')}
    it {should have_title(full_title('Help'))}

  end

  describe "About page" do

    before {visit about_path}
    it {should have_content('About Us')}
    it {should have_title(full_title('About Us'))}

  end

  describe "Contact page" do

    before {visit contact_path}
    it {should have_content('Contact')}
    it {should have_title(full_title('Contact'))}

  end
end

Usersコントローラ作成

コントローラファイルを生成

$ rails generate controller Users new --no-test-framework

テスト作成

$ rails generate integration_test user_pages
$ subl spec/requests/user_pages_spec.rb

require 'spec_helper'

describe "User pages" do

  subject { page }

  describe "signup page" do
    before { visit signup_path }

    it { should have_content('Sign up') }
    it { should have_title(full_title('Sign up')) }
  end
end

テスト実行

$ bundle exec rspec spec/requests/user_pages_spec.rb
=> 失敗する

$ bundle exec rspec spec/ #と実行すると全てのテストを実行する。

テストをパスするように修正

ルートを修正

SampleApp::Application.routes.draw do
  get "users/new"

  root  'static_pages#home'
  match '/help',    to: 'static_pages#help',    via: 'get'
  match '/about',   to: 'static_pages#about',   via: 'get'
  match '/contact', to: 'static_pages#contact', via: 'get'
  match '/about', to: 'static_pages#about',  via: 'get'
+  match '/signup',  to: 'users#new',  via: 'get'

ビューを修正

+ <% provide(:title, 'Sign up') %>
+ <h1>Sign up</h1>
<p>Find me in app/views/users/new.html.erb</p>

テスト実行

$ bundle exec rspec spec/requests/user_pages_spec.rb
=> 成功する

HomeページのSignupボタンにリンクを設定

<div class="center hero-unit">
  <h1>Welcome to the Sample App</h1>

  <h2>
    This is the home page for the
    <a href="http://railstutorial.jp/">Ruby on Rails Tutorial</a>
    sample application.
  </h2>

  <%= link_to "Sign up now!", signup_path, class: "btn btn-large btn-primary" %>
</div>

<%= link_to image_tag("rails.png", alt: "Rails"), 'http://rubyonrails.org/' %>

gitにコミット

$ git add .
$ git commit -m "Finish layout and routes"
$ git checkout master
$ git merge filling-in-layout
13
12
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
13
12