Rails6.1ハンズオン(4)~6.0の機能を触る


はじめに

Rails6.1ハンズオン(3)の続きです。

6.1ハンズオンと言いながら、実は6.0をまともに触っていない筆者。。。
ですので今回は6.0で追加された機能を触ってみます。
コードはGithubにあげています。章ごとにコミットしてますので、参考にしていただければ幸いです。

やること

個人的に気になった(面白そうor仕事で使いそう)機能をピックアップして、現在のRails_6.1_hands_onプロジェクトに追加してみます。

  • Action Text
  • Action Mailbox
  • ActiveRecord::Relation#pick

参考:Ruby on Rails 6の主要な新機能・機能追加・変更点 - Qiita

5-1. Action Text

5-1-1. Action Text, Active Storageの導入

参考:Action Text の概要 - Railsガイド

まずはActiveStorageが必要なので、

rails active_storage:install

をしたが、

rails aborted!
Don't know how to build task 'active_storage:install' (See the list of available tasks with `rails --tasks`)

と出た。ActiveStorageのREADMEをみると、

rails/rails

Run bin/rails active_storage:install to copy over active_storage migrations.
NOTE: If the task cannot be found, verify that require "active_storage/engine" is present in config/application.rb.

らしいので、config/application.rbをみると、

require "rails"
# Pick the frameworks you want:
require "active_model/railtie"
require "active_job/railtie"
require "active_record/railtie"
# require "active_storage/engine"
require "action_controller/railtie"
# require "action_mailer/railtie"
# require "action_mailbox/engine"
# require "action_text/engine"
require "action_view/railtie"
require "action_cable/engine"
require "sprockets/railtie"

となっていた。rails new で色々無効にしていたのでコメントアウトされていたらしい。

action_text/engineも無効化されているのでこちらも有効にしておく。

そしてやっと、

rails active_storage:install
rails action_text:install

migrationファイルができているので、忘れずにrails db:migrateする。

config/storage.ymlを作る(最初からあるイメージだが、今回は無かった)

local:
  service: Disk
  root: <%= Rails.root.join("storage") %>

test:
  service: Disk
  root: <%= Rails.root.join("tmp/storage") %>

config/environments/development.rb(test.rbも任意で、このハンズオンでテスト書くのかな...)に追加:

config.active_storage.service = :local

5-1-2. ActionTextをモデルに適用する

Commentのcontentがtextになっていたのを、Action Textに置き換える。

rails g migration RemoveContentInComment
class RemoveContentInComment < ActiveRecord::Migration[6.1]
  def change
    remove_column :comments, :content, :text
  end
end

rails db:migrateして、

app/models/comment.rb

class Comment < ApplicationRecord
  belongs_to :community
  has_rich_text :content
end

has_rich_textでcontentカラムを作ったかのように振る舞ってくれるようになる。

app/views/comments/new.html.haml(一部)

= form.label :content, class: 'form-label'
= form.rich_text_area :content, class: 'form-control mb-4'

app/views/communities/show.html.haml

= comment.content

simple_formatを外した。

すると以下のようになる。

思ってたのと違う。cssが読み込まれていない。action_text:installしたときに新しく生成されたcssは、app/assets/stylesheets/actiontext.scss。内容がこちら

//
// Provides a drop-in pointer for the default Trix stylesheet that will format the toolbar and
// the trix-editor content (whether displayed or under editing). Feel free to incorporate this
// inclusion directly in any other asset bundle and remove this file.
//
//= require trix/dist/trix

// We need to override trix.css’s image gallery styles to accommodate the
// <action-text-attachment> element we wrap around attachments. Otherwise,
// images in galleries will be squished by the max-width: 33%; rule.
.trix-content {
  .attachment-gallery {
    > action-text-attachment,
    > .attachment {
      flex: 1 0 33%;
      padding: 0 0.5em;
      max-width: 33%;
    }
// (以下省略)

trix/dist/trixをrequireしていて、更に添付ファイルの表示に関するスタイルを上書きしているらしい。

app/views/layouts/application.html.hamlでは、

= stylesheet_link_tag 'application'を消して、= stylesheet_pack_tag 'application'に変えているので、上記ファイルは読み込まれない。

= stylesheet_link_tag 'application'を復活させれば動く(動作確認済み)。

だが、せっかくなので、webpackerに寄せる。

app/javascript/stylesheets/application.scss

@import "~@fortawesome/fontawesome-free/scss/fontawesome";

$primary: #9400d9;
@import "bootstrap";
@import "trix/dist/trix";
@import "actiontext.scss";

app/javascript/stylesheets/actiontext.scssではsprocket用のコードを外して記述。

// We need to override trix.css’s image gallery styles to accommodate the
// <action-text-attachment> element we wrap around attachments. Otherwise,
// images in galleries will be squished by the max-width: 33%; rule.
.trix-content {
  .attachment-gallery {
    > action-text-attachment,
    > .attachment {
      flex: 1 0 33%;
      padding: 0 0.5em;
      max-width: 33%;
    }

    &.attachment-gallery--2,
    &.attachment-gallery--4 {
      > action-text-attachment,
      > .attachment {
        flex-basis: 50%;
        max-width: 50%;
      }
    }
  }

  action-text-attachment {
    .attachment {
      padding: 0 !important;
      max-width: 100% !important;
    }
  }
}

すると、

できた。

こんな感じで入力できる。

それで投稿すると

画像が表示されない。

chromeのconsoleを見ると、

GET http://localhost:3000/rails/active_storage/representations/redirect/eyJfcmFpbHMiOnsibWVzc2FnZSI6IkJBaHBCZz09IiwiZXhwIjpudWxsLCJwdXIiOiJibG9iX2lkIn19--dce7eada98f7015981b311d8495658640b895ad9/eyJfcmFpbHMiOnsibWVzc2FnZSI6IkJBaDdCem9MWm05eWJXRjBTU0lJY0c1bkJqb0dSVlE2RkhKbGMybDZaVjkwYjE5c2FXMXBkRnNIYVFJQUJHa0NBQU09IiwiZXhwIjpudWxsLCJwdXIiOiJ2YXJpYXRpb24ifX0=--9a6414b9afa153c394bf23eb32d0e368370e8b60/Screenshot_20210304-220735.png 500 (Internal Server Error)

読み込めてない。500なので内部的なエラー。

したがってrailsのコンソールを見ると、

LoadError (Generating image variants require the image_processing gem. Please add `gem 'image_processing', '~> 1.2'` to your Gemfile.)

ちゃんと書いてあった。Gemfileにgem 'image_processing', '~> 1.2'を追加。bundle install。

表示されました。

5-2. Action Mailbox

私は勘違いしていました。
Railsには、Action MailerとAction Mailboxの2つがあるということを。
送信用と受信用で分かれているということを。

いつかメール受信機能を使うときのために名前だけ覚えておきます。
問い合わせフォームとか作れるみたいですね。
送信用のAction Mailerを試したかったので、ここは割愛します。

5-3. ActiveRecord::Relation#pick

DB上のテーブルの絞り込み条件や並べ替えを指定した際に、最初のレコードの特定のカラムの値を取得する

らしいです。

掲示板のコミュニティの最新コメント投稿を表示してみます。

app/views/communities/index.html.haml(一部)

author_name, created_at = community.comments.order(created_at: :desc).pick(:author_name, :created_at)


便利...なのか...?.first.pluck(:hoge)で良くない...?

以上です。
ついに次回、6.1の機能に触る編です!!