yucatio@システムエンジニア

趣味で作ったものいろいろ

RubyMineでminitestを実行する

今、『プロを目指す人のためのRuby入門』(伊藤淳一[著])を読んでるんですが、使用するテストフレームワークminitestなのですよね。

RubyMineでminitestを追加しようとしたら、”New”の一覧にもないし、とりあえず手動でファイル作って

require 'minitest/autorun'

と書いてみたら”そんなファイルないよ”とのエラーが出ました。

f:id:yucatio:20180612114010p:plain

f:id:yucatio:20180612114019p:plain

公式ドキュメント見たら、minitestの実行要件が載っていたのでその通りにします。

Minitest - Help | RubyMine

と言っても、詳細な手順はさすがに載っていなくて、久々にrubyをさわったらBundlerの使い方を忘れていたので、詳細な手順を残しておきます。

Bundle Init

Tools > Bundler > Init でBundlerを初期化します。

f:id:yucatio:20180612120255p:plain

GemFileの書き換え

GemFileが作成されたので、下記を追加します。

group :test do
    gem "minitest"
    gem 'minitest-reporters', '>= 0.5.0'
end

minitest-reportersは、minitest のバージョンが 5.0.0ならばインストールは必須ではないのですが、入れておくとテスト結果をツリー状に表示してくれるので、追加するのがおすすめです。(Important noteに書いてある)

公式ドキュメントには、'cucumber-rails'も書かれていますが、今回は必要ないので外しています。

Bundle Install

Tools > Bundler > Install を選択して、gemをインストールします。

f:id:yucatio:20180612121439p:plain

これでminitestを使用する準備が整いました。

テストファイル作成

“New”メニューにminitestのテンプレートが追加されるかと思いましたが、されませんでした。 テストファイルは、New > Ruby Class Template らへんから作ります。

minitestのテストファイルは、(拡張子を除いた部分が)_testで終わるか、test_で始まり、拡張子が.rbである必要があります。

また、テストクラス名はTestで終わる必要があります。

テストメソッドはtest_で始める必要があります。

ヘッダーはこんな感じ

require 'minitest/autorun'
require 'minitest/reporters'
MiniTest::Reporters.use!

テストクラスはMinitest::Testを継承します。

f:id:yucatio:20180612121741p:plain

テスト実行

テストの実行はソースコードの実行と同じようにファイル右クリック > Runでできます。testフォルダ右クリック > Run All Tests ..で全てのテストを実行可能です

f:id:yucatio:20180612135028p:plain

テスト実行結果です。テストを再実行したい場合は、左上の緑の三角ボタンを押します。

f:id:yucatio:20180612134439p:plain

環境

番外編

minitest-reportsをbundle installした直後に、以下のエラーが出ましたが、Rubymineを再起動したらエラーは出なくなりました。

`rescue in specs': Your bundle is locked to ansi (1.5.0), but that version could not be found in any of the sources listed in your Gemfile. If you haven't changed sources, that means the author of ansi (1.5.0) has removed it. You'll need to update your bundle to a different version of ansi (1.5.0) that hasn't been removed in order to install. (Bundler::GemNotFound)

f:id:yucatio:20180612125428p:plain

yucatio.hatenablog.com

リソースにfirstとかlastとかtodayでアクセスしたい場合のリンクパスの生成方法 (Ruby on Rails)

railsでリンクパスを作成するときに、

events/123/tickets/1

のようにIDを指定するのではなく、

events/123/tickets/last

lastように、

リソースパスに文字列を指定する方法。

うまくいく方法

シンボルを渡せばよいだけでした。

event_ticket_path(@event, :last)
#=> /events/123/tickets/last
# routes.rb

Rails.application.routes.draw do
  resources :events  do
    resources :tickets
  end
end

うまくいかない方法

モデルのIDに文字列を渡したところ、0に変換されてしまいました。

ticket = @event.tickets.build(id: 'last')
event_ticket_path(@event, ticket)
#=> /events/123/tickets/0
環境

RubyでArrayをHashに変換する

前回の記事で、ArrayをHashに変換するのにArray#mapとArray#to_hを使用して、ArrayをHashに変換しました。

yucatio.hatenablog.com

オブジェクトの配列を、オブジェクトのIDをハッシュのキー、オブジェクト自身をハッシュのバリューとして登録したい場合があります。

例として、配列のデータをハッシュに変換します。idをキーとして、データ自体を値としたHashを作成するには下記で実現できます。

arr = [
  {id: 1, name: "Alice", age: 20}, 
  {id: 2, name: "Bob", age: 30}
]

arr.map {|data| [data[:id], data]}.to_h
# => 
# {
#   1=>{:id=>1, :name=>"Alice", :age=>20}, 
#   2=>{:id=>2, :name=>"Bob", :age=>30}
# }

順を追って見ていきます。まずmapオブジェクトで、配列の各要素を、[data[id], data]に変換します。

arr.map {|data| [data[:id], data]}
# => 
# [
#   [1, {:id=>1, :name=>"Alice", :age=>20}], 
#   [2, {:id=>2, :name=>"Bob", :age=>30}]
# ]

これを、to_hを使用してハッシュに変換します。

[[1, {:id=>1, :name=>"Alice", :age=>20}], [2, {:id=>2, :name=>"Bob", :age=>30}]].to_h
# => 
# {
#   1=>{:id=>1, :name=>"Alice", :age=>20}, 
#   2=>{:id=>2, :name=>"Bob", :age=>30}
# }

to_hの方法を知る前は以下のように書いていましたが、to_hの方がすっきり書けるように思います。

obj_hash = {}
arr.each { |data|
  obj_hash[data[:id]] = data
}
環境

Railsでajax通信時にattribute名とfull_messageの組み合わせでレスポンスを返す

ajaxでの非同期通信時に、attributeごとのメッセージを表示するのに手間取ったので記録しておきます。

ajax通信でない時は、errors.full_messages_for(:attribute_name)で各attributeのエラーメッセージは取得できます。

やりたいこと

ajax通信時に、入力エラーがある場合に、入力項目ごとに表示したい。

こうなればよい。

f:id:yucatio:20170414023228p:plain:w400

errorsを使用する場合(うまくいかなかった例)

コード

class TicketsController < ApplicationController
  def create
    ticket = Ticket.create(ticket_params)

    if ticket.save
      render json: {message: 'success'}, status: :created
    else
      error_messages = ticket.errors
      render json: {message: error_messages}, status: :unprocessable_entity
    end
  end
end

レスポンス

{"message":
  {"password":["を入力してください"],
    "email":["を入力してください","は有効でない形式です"]}
}

画面表示

f:id:yucatio:20170414023247p:plain:w400

メッセージボディしか表示されません。これじゃない。

errors.full_messages を使用する場合(うまくいかなかった例)

コード

class TicketsController < ApplicationController
  def create
    ticket = Ticket.create(ticket_params)

    if ticket.save
      render json: {message: 'success'}, status: :created
    else
      error_messages = ticket.errors.full_messages
      render json: {message: error_messages}, status: :unprocessable_entity
    end
  end
end

レスポンスはこのようになります。

{"message":["パスワードを入力してください","メールアドレスを入力してください","メールアドレスは有効でない形式です"]}

画面に表示するとしたらこうなります。

f:id:yucatio:20170414023306p:plain:w400

1ヶ所に全てのエラーを表示する場合はこれでもよいですが、項目ごとに表示するといった目的は達成できません。

ticket.errors.keys と errors.full_messages_for 組み合わせる(うまくいった例)

コード

class TicketsController < ApplicationController
  def create
    ticket = Ticket.create(ticket_params)

    if ticket.save
      render json: {message: 'success'}, status: :created
    else
      error_messages = ticket.errors.keys.map { |key| [key, ticket.errors.full_messages_for(key)]}.to_h
      render json: {message: error_messages}, status: :unprocessable_entity
    end
  end
end

レスポンス

{"message":
  {"password":["パスワードを入力してください"],
   "email":["メールアドレスを入力してください","メールアドレスは有効でない形式です"]}
}

画面表示

f:id:yucatio:20170414023228p:plain:w400

できました!

環境

RubyMineでRuby on railsの開発をする その8: おすすめ設定3つ

ナビゲーションバーの表示

現在開いているファイルの階層をウィンドウ上部に表示させます。

View > Nabigation Bar を選択

f:id:yucatio:20170207185038p:plain:w200

画面上部に awesome_events > app >views > events > new.html.slim と、現在開いているファイルの階層が表示されるようになりました。

f:id:yucatio:20170204195918p:plain

階層をクリックすると、同階層の他のファイルが表示され、ここからファイルを開くことができます。同一コントローラの他のファイルを参考のため開くときに便利です。

f:id:yucatio:20170204195931p:plain

空白文字の表示

半角空白や全角空白はデフォルトでは単なる空白ですが、空白文字の表示を設定すると、それぞれ別の記号で表示してくれるようになります。

RubyMine メニュー > Preferences.. を選択

f:id:yucatio:20170204195806p:plain:w200

Editor > General > Appearence をい開いて、Show whitespaces のチェックを入れます。

f:id:yucatio:20170204195823p:plain

半角スペースは.(ドット)、全角スペースは□(四角)、タブは→|で表示されるようになりました。

f:id:yucatio:20170204195735p:plain

チームで開発している場合は、チームメンバーにもこの設定を入れてもらいましょう。 新人が全角空白や、タブを仕込んでくるのをちょっとは防げるはず。

ツールバーの表示

各種操作を行うためのツールバーを表示します。

View > Toolbar を選択します。

f:id:yucatio:20170204195840p:plain:w200

ツールバーが表示されました。各種タスクを実行するのに便利です。

f:id:yucatio:20170204195853p:plain

環境

RubyMineでRuby on railsの開発をする その7: ER図の出力

RubyMineでのERDの出力方法です。引き続き、"パーフェクト Ruby on Rails" に掲載されているサンプルアプリ (awesome_events)を使用していきます。 DBの設定が事前に必要です。

yucatio.hatenablog.com

DBを右クック > Diagrams > Show Visualization... を選択します。

f:id:yucatio:20170204155020p:plain

Rails Model Dependency Diagram を選択します。

f:id:yucatio:20170204155204p:plain

ER図が出力されました。

f:id:yucatio:20170204155443p:plain

環境

RubyMineでRuby on railsの開発をする その6: DB (Sqlite) の設定

RubyMineでのSqliteの設定方法です。引き続き、"パーフェクト Ruby on Rails" に掲載されているサンプルアプリ (awesome_events)を使用していきます。

yucatio.hatenablog.com

Sqliteの設定

View > Tool Windows > Database を開く。

f:id:yucatio:20170204151513p:plain

Databaseウィンドウが開きます。

f:id:yucatio:20170204151645p:plain

プラス記号 > Import from sources を選択します。

f:id:yucatio:20170204151742p:plain

developmentを選択します。

f:id:yucatio:20170204151923p:plain

初回はJDBCドライバのエラーが出るので、'Download missing driver files' をクリックして、ドライバファイルをダウンロードします。

f:id:yucatio:20170204152046p:plain

Error: Driver class 'org.sqlite.JDBC' not found の対処をします。

f:id:yucatio:20170204152148p:plain

リンク先に飛ぶと、Sqliteの設定タブに飛ぶので、ここでApplyを押します。

f:id:yucatio:20170204152436p:plain

元の、コネクション作成の画面に戻ります。

f:id:yucatio:20170204151923p:plain

Test Connection でコネクションのテストをします。

成功しました。OKを押して、DBの設定を完了します。

f:id:yucatio:20170204153313p:plain

DBに接続され、テーブル一覧、カラム一覧が表示されました。 これで開発効率が上がりそうです。

f:id:yucatio:20170204153446p:plain

SQLの実行

SQLを実行します。テーブル名やカラム名SQLキーワードは補完してくれます。便利。

f:id:yucatio:20170204153734p:plain

緑の三角矢印を押して、実行します。 表形式で見れます。見やすい。

f:id:yucatio:20170204153926p:plain

ちなみに、SQLを入力するウィンドウは、データベースパネル > プラス記号 > Console File で追加することができます。

f:id:yucatio:20170204154056p:plain

環境