2018年6月25日

プログラミング

Railsでseed-fuを使って初期データを作ろう!

目次

  1. はじめに
  2. gem seed-fuの導入
  3. 基本の使い方
  4. 関連付け(アソシエーション)
  5. seed_once
  6. シンタックスシュガー(もうひとつの書き方)
  7. CSVからのデータ作成
  8. ユーザー作成時に注意すること
  9. まとめ

はじめに

Railsにはデフォルトで初期データを入れる機能がありますが、実行する度に同じデータが作成されてしまいます。seed-fu を利用するとデータの追加、管理が簡単にできるようになります!

seed_fu のGithubリポジトリ

今回使用する環境

  • Ruby: 2.4.1
  • Ruby on Rails: 5.1.4
  • seed-fu: 2.3.9

gem seed-fuの導入

seed-fu のインストール

まず seed-fu をインストールしましょう。

Gemfile

gem 'seed-fu'

$ bundle install を実行

ディレクトリを作成

次に seed ファイルを置くディレクトリを作成します。

db/fixtures
db/fixtures/development
db/fixtures/production

db/fixtures は必ず必要なディレクトリです。
db/fixtures に作成した seed ファイルを置くこともできますが、db/fixtures/developmentdb/fixtures/production に seed ファイルを作成すると環境ごとに異なるデータを作成することができとても便利です。

POINT!!

db/fixture 以下の seed ファイルはアルファベット順に読み込まれます。読み込む順番を指定する必要がある時は以下のようにファイル名の始めに数字を入れましょう。
01_category.rb
02_sub_category.rb
03_skill.rb

基本の使い方

seed ファイルの作成

db/fixturesに以下のように seed ファイルを作成します。
ここでは例として Category モデルを使っています。

01_category.rb

Category.seed do |s|
s.id = 1
s.name = 'HTML'
end

Category.seed do |s|
s.id = 2
s.name = 'CSS'
end

Category.seed do |s|
s.id = 3
s.name = 'Ruby'
end

seed_fu コマンドの実行

$ rails db:seed_fu を実行

実行結果

== Seed from ./db/fixtures/development/01_category.rb
- Category {:id=>1, :name=>"HTML"}
- Category {:id=>2, :name=>"CSS"}
- Category {:id=>3, :name=>"Ruby"}

これでデータが作成されます!

データの更新

一度作ったデータを更新したい時は、
変更したい部分を修正
01_category.rb

...

Category.seed do |s|
s.id = 3
s.name = 'Ruby on Rails'
end

もう一度$ rails db:seed_fu を実行

実行結果

== Seed from ./db/fixtures/development/01_category.rb
- Category {:id=>1, :name=>"HTML"}
- Category {:id=>2, :name=>"CSS"}
- Category {:id=>3, :name=>"Ruby on Rails"}

このようにデータの更新をする事ができます。

関連付け(アソシエーション)

関連付けのあるデータの作成

has_many などで関連付けがされている場合、どのようにデータを作ればいいでしょう?
HTMLカテゴリーの中に「Webフォントの設定」、「画像の設定」という Skill を作ってみます。

02_skill.rb

Skill.seed do |s|
s.id = 1
s.category = Category.find_by(name: 'HTML')
s.name = 'Webフォントの設定'
end

Skill.seed do |s|
s.id = 2
s.category = Category.find_by(name: 'HTML')
s.name = '画像の設定'
end

$ rails db:seed_fu を実行

実行結果

== Seed from ./db/fixtures/development/02_skill.rb
- SubCategory {:id=>1, :category=>#, :name=>"Webフォントの設定"}
- SubCategory {:id=>2, :category=>#, :name=>"画像の設定"}

このように関連付けのあるデータを作成する事ができます。

seed_once

seedメソッドだと??

rails db:seed_fuを実行すると、毎回データの作成または更新が行われます。

例えば、
seed ファイルを作成

Category.seed do |s|
s.id = 1
s.name = 'HTML'
end

$ rails db:seed_fu を実行

railsアプケーションやコンソール上でカテゴリーの名前を「HTML」から「html」に変更して
もう一度$ rails db:seed_fu を実行

実行結果

== Seed from ./db/fixtures/development/01_category.rb
- Category {:id=>1, :name=>"HTML"}

カテゴリーの名前は「HTML」に書き換えられます。

seed_onceを使う

一度データを作成した後は更新したくない場合、 seed_onceを使います。

先ほどと同じように、
seed ファイルを作成(今回はseed_onceを使います。)

Category.seed_once do |s|
s.id = 1
s.name = 'HTML'
end

$ rails db:seed_fu を実行

railsアプケーションやコンソール上でカテゴリーの名前を「HTML」から「html」に変更して
もう一度$ rails db:seed_fu を実行

Category.seed_once do |s|
s.id = 1
s.name = 'HTML'
end

実行結果

== Seed from ./db/fixtures/development/01_category.rb

一度作成したデータなので何も起きず、カテゴリーの名前は「html」のままになります。
(デフォルトでは作成したデータかどうかのチェックに ID を利用します。)

シンタックスシュガー

シンタックスシュガーを使ってみる

seedファイルを作成する時は、これまでのような記述の他に以下のように記述することもできます。

Category.seed(:id,
{ id: 1, name: 'HTML' },
{ id: 2, name: 'CSS' },
{ id: 3, name: 'Ruby' },
)

$ rails db:seed_fu

実行結果

== Seed from ./db/fixtures/development/01_category.rb
- Category {:id=>1, :name=>"HTML"}
- Category {:id=>2, :name=>"CSS"}
- Category {:id=>3, :name=>"Ruby"}

同じようにデータが作成されます。

CSVからのデータ作成

CSVファイルからデータを作成してみる

まずはCSVファイルを作る(ここではid, name の順。要素をカンマで区切ればOKです!)

db/fixtures/development/category.csv

1,HTML
2,CSS
3,Ruby

seedファイルにCSVから読み込む処理を書く
db/fixtures/development/01_category.rb

require 'csv'

csv = CSV.read('db/fixtures/development/category.csv')
csv.each do |category|
Category.seed do |s|
s.id = category[0]
s.name = category[1]
end
end

先ほど csvファイルには id, name の順に記述しました。
なので、category[0]id, category[1]name になります。

$ rails db:seed_fu

実行結果

== Seed from ./db/fixtures/development/01_category.rb
- Category {:id=>1, :name=>"HTML"}
- Category {:id=>2, :name=>"CSS"}
- Category {:id=>3, :name=>"Ruby"}

これでCSVファイルからデータを作成することができました!
大量のデータを作る時などに便利ですね。

ユーザー作成時に注意すること

device や sorcery を使っていると…

Railsアプリケーションの user には大抵 devise や sorcery を使った認証機能が実装されているのではないかと思います。

そのようなユーザーをこのように作ると…
00_user.rb

User.seed do |s|
s.id = 1
s.name = 'yuh'
s.email = 'sample@test.com'
s.password = 'password'
s.password_confirmation = 'password'
end

$ rails db:seed_fu

実行結果

== Seed from ./db/fixtures/development/00_user.rb
User {:id=>1, :name=>"yuh" :email=>"sample@test.com", :password=>"password", :password_confirmation=>"password"}

エラーも発生しないし、うまくいった 気がする!

しかし、
作成された user を確認してみると…

<User id: 1, name: "yuh", email: "sample@test.com", crypted_password: nil, salt: nil, created_at: "2018-06-22 01:36:04", updated_at: "2018-06-22 01:36:04">

!???
crypted_password: nil, salt: nil
パスワードが設定されていない!

POINT!!

通常のユーザー作成の手順ではパスワードを暗号化して crypted_password などが作成されます。
しかし、seed-fu ではこの処理は行われずそのままのデータを作成しようとします。
そのためパスワードが正しく設定されません。

ユーザーを作るときは?

このような時はデフォルトの seed を使いましょう。
00_user.rb

User.create!(id: 1, name: 'yuh', email: 'sample@test.com',
password: 'password', password_confirmation: 'password')

$ rails db:seed_fu

実行結果

== Seed from ./db/fixtures/development/00_user.rb

何も表示されませんが、作成された user を確認してみると…

<User id: 1, name: "yuh", email: "sample@test.com", crypted_password: "$2a$10$e7g2uKH8eoWYo.zmnTYcJOOF4gbs0g8egWfDwH6aPQy...", salt: "RvQfSMBKboxwzBEZ8Sv5"

きちんとパスワードが設定されています!

まとめ

初期データセットのためのgem、 seed-fu の使い方を見てきました。
seed-fu を利用するとデータの追加、管理が簡単にできるようになります!

ユーザー作成の時には注意が必要ですが(私はユーザー作成でハマりました…)使い方は難しくないと思います。
初期データを作成する時はぜひ使ってみてください!

2

0

AUTHOR

はらた

はらた エンジニア

サーバーサイドエンジニア Ruby on Railsを使った開発を行なっています

アプリでもっと便利に!気になる記事をチェック!

記事のお気に入り登録やランキングが表示される昨日に対応!毎日の情報収集や調べ物にもっと身近なメディアになりました。

palanでは一緒に働く仲間を募集しています

正社員や業務委託、アルバイトやインターンなど雇用形態にこだわらず、
ベテランの方から業界未経験の方まで様々なかたのお力をお借りしたいと考えております。

話を聞いてみたい

運営メンバー

eishis

Eishi Saito 総務

SIerやスタートアップ、フリーランスを経て2016年11月にeishis, Inc.を設立。 マーケター・ディレクター・エンジニアなど何でも屋。 COBOLからReactまで色んなことやります。

sasakki デザイナー

アメリカの大学を卒業後、日本、シンガポールでデザイナーとして活動。

しまだ

しまだ デザイナー

WebAR/VRのデザインと3DCG制作がメインです。 肩書きは「アニメ案件に関わりたいデザイナー」。

Miu マーケター

ドイツでWEBマーケティングしています。

しんのき エンジニア

主に React Native を使ったアプリ開発と AWS や Firebase を使ったサーバーレスアーキテクチャを担当しています。元々はインフラとかPHPをやっていました。

yamakawa

やまかわたかし デザイナー

フロントエンドデザイナー。デザインからHTML / CSS、JSの実装を担当しています。最近はReact NativeやReact360をよく触っています。

furuya エンジニア

サーバーサイド、フロントエンド、Unityと色々手を出してる雑食系エンジニア。ReactNativeが最近のマイブーム。

Sayaka Osanai デザイナー

Sketchだいすきプロダクトデザイナー。シンプルだけどちょっとかわいいデザインが得意。 好きな食べものは生ハムとお寿司とカレーです。

はらた

はらた エンジニア

サーバーサイドエンジニア Ruby on Railsを使った開発を行なっています

うえまつゆい エンジニア

サーバーサイドエンジニアからフロントエンドエンジニアになりました。主にReact Nativeでのアプリ開発をしています。

kobori

こぼり ともろう エンジニア

サーバーサイドエンジニア。SIerを経て2019年7月に入社。日々学習しながらRuby on Railsを使った開発を行っています。

sasai

ささい エンジニア

フロントエンドエンジニア WebGLとReactが強みと言えるように頑張ってます。

damien

Damien

WebAR/VRを中心に企画やディレクションやエンジニアもちょっとやっています。森に住んでいます。

デザイナーゲスト

ゲスト デザイナー

CONTACT PAGE TOP