- 投稿日:2020-08-17T23:45:38+09:00
herokuデプロイ中precompiling assets failedとエラーが出た時
ローカル環境では問題なく動いていたのにherokuでデプロイ中にprecompiling assets failedとエラーが出たので解決方法をまとめます。
logを調べているうちに環境内に問題がありそうだったので
ターミナルでエラー解析をします。RAILS_ENV=development bin/rails assets:precompileこちらを実行することで開発環境ないでエラーがないかを確認することができます。
中身を見てみると、、、
warning Integrity check: Flags don't match error Integrity check failed error Found 1 errors. ======================================== Your Yarn packages are out of date! Please run `yarn install --check-files` to update. ======================================== To disable this check, please change `check_yarn_integrity` to `false` in your webpacker config file (config/webpacker.yml).ローカルでyarnを最新の状態にしているからなのかファイルのバージョンに古いのがあったためupdateする必要があったのかなと思います。
また、
To disable this check, please change `check_yarn_integrity` to `false` in your webpacker config file (config/webpacker.yml).このままではチェックと指示があるので下記のように変更します。
/config/webpacker.ymlcheck_yarn_integrity: falseこの状態でもエラーが出たので下記コマンドで本番環境で問題がないか確認してみます。
RAILS_ENV=production bin/rails assets:precompile UnitConversionError Incompatible units: 'px' and ‘%’imcompatibleは相容れないという意味なんおでpxと%を同時に使っている可能性があります。
.main{ height: (100% - 780px); margin: 0 auto; }heightの計算にcalcを書いてない!!
.main{ height: calc(100% - 780px); margin: 0 auto; }もう一度デプロイするとうまくいきました。
- 投稿日:2020-08-17T22:12:12+09:00
Railsでワクワク個人開発 第3回:データの関連付け/ seedデータ投入
関連付けとモデル
日々の記憶がおぼろげだが、ここに記しておこう。関連づけられたデータを作成してみることにした。DB設計の段階から、ユーザーと彼らがもつ植物は関連付けようと考えていた。一人のUserは複数のPlantを所持する。共有することはしない。
Userモデルはさきの記事でmigrateした。今回はPlantモデルをつくる。
rails g model plant
をターミナルに打ち込むとplantができる。便利だ。db/migrate
フォルダから対応するファイルを開く。こんな感じで書く。class CreatePlants < ActiveRecord::Migration[6.0] def change create_table :plants do |t| t.integer :user_id, null: false t.string :plant_name, null: false t.string :img t.timestamps end end endこのときにDB設計が生きてくる。場当たり的にこれらを設定するのはうまくいかない。
終了したらmigrateをしよう。モデルクラスの修正
関連付けのお約束。モデルクラスの修正をした。
app/model/plant.rb
class Plant < ApplicationRecord belongs_to :user end
app/model/user.rb
class User < ApplicationRecord # Include default devise modules. Others available are: # :confirmable, :lockable, :timeoutable, :trackable and :omniauthable devise :database_authenticatable, :registerable, :recoverable, :rememberable, :validatable has_many :plants endplantはuserに属している、userは多くのplantを持っている。ということを書いた。
seedデータ投入
ここで、タネを入れる。seedとかいうサンプルデータをあらかじめ入れておく。
db/seed.rb
User.create(email: 'test@example.com', password: 'password') User.create(email: 'test2@example.com', password: 'password') Plant.create(user_id:1, plant_name: "flower", img: "flower_img") Plant.create(user_id:1, plant_name: "sun_flower", img: "sun_flower_img") Plant.create(user_id:2, plant_name: "dia", img: "dia_img") Plant.create(user_id:3, plant_name: "rose", img: "rose_img")ターミナルで
rails db:seed
と打つ。これでOK。 終了したらrailsのコンソールからデータを確認しよう。rails c
でできる。
User.all
と打ち込んだらいいぐあいに表示されるだろうか。よし。次回予告
いよいよネストされたリソースを使ってCRUD処理を書く。このあたり、途中経過がよくわからなくなっているので、結果だけ書いていく。
- 投稿日:2020-08-17T21:53:36+09:00
Slack APIを使ってみよう!【Slack + Rails】
はじめに
この記事では、Slackへメッセージを送るRailsアプリを作成してみます。
動作としてはこんな感じです。
- http://localhost:3000/hello にアクセスする
- Slackに「こんにちは」とメッセージが送られる
Slack APIとは何か?
Slack用のアプリケーション開発のためにSlackから公開されているAPIです。
事前準備
- Slackのワークスペースを作成する
下記ページを参考に、Slackのワークスペースを作成しておきましょう。※注意
アプリケーション開発用のワークスペースをすでに作成済みであれば、
新たに作成する必要はありません。
実際の業務などで使用しているワークスペースを流用しないようにしてください。Slackアプリを作ってみよう
まずは、Slack側でアプリを作ってみます。
アプリの新規作成
- 下記ページにアクセス
- 「Create New App」ボタンを押してモーダルを開きます。
App Name
は 「テストBot」(名前はなんでも良い)、
Develoment Slack Workspace
には作成した開発用のワークスペースを指定します。
- 右下の「Create App」ボタンを押すと、アプリが作成されます。
![]()
アプリのPermission(権限)の設定
- 権限設定画面を開く
アプリ新規作成後、下記のようなアプリの基本情報画面に遷移します。
Install your app to your workspace
というメニューを開くと、
「最低1つ以上のfeature
か、permission scope
を設定する必要がある」と書いてあります。
この
permission scope
というリンクを押すと、権限設定画面に移動します。![]()
- 必要なスコープの設定 権限設定画面で、必要な権限を設定します。
今回は、 メッセージの送信をできるようにしたい ので、
chat:write
というスコープを設定します。
これで、Botとして参加しているチャンネル内でメッセージの送信を行えるようになります。
スコープにはいろいろな種類があり、
それぞれのアプリに最低限必要なもののみを設定することで、
セキュリティを保つことができます。これで権限設定は完了です。
Botを設定する
- Botの名前を設定
左サイドメニューからApp Home
を選択して、アプリケーションのホーム画面を開きます。
赤枠で囲んだ部分の「Edit」ボタンを押して、アプリの名前を設定します。今回は下記のように設定しましたが、好きな名前で設定して問題ないです。
![]()
これでワークスペースにアプリをインストールできるようになりました。
ワークスペースにアプリをインストールする
- インストール画面を開く
左サイドメニューからInstall App
を選択して、
ワークスペースへのアプリインストール画面を開きます。![]()
- インストールの確認画面
「Install App To Workspace」ボタンを押すと、下記のような画面が開きます。
(画像では、ワークスペース名などを隠しています。)
「実行出来る内容」の部分が期待通りであることを確認して、「許可する」ボタンを押しましょう。![]()
- トークンが発行される 「許可する」ボタン押下後、下記の画面に遷移します。
この時に表示されるトークンが、
Slack APIを利用したメッセージの送信時に必要なので、メモしておいてください。
(このトークンを公開してはいけません。
トークンを知った人であれば誰でも、先ほど作成したBotとしてワークスペースへメッセージを送ることができるようになってしまいます。)![]()
ワークスペースのチャンネルにアプリを招待する
任意のチャンネルに、作成したアプリを招待します。
アプリを招待したいチャンネルを開いて、
/invite @アプリのワークスペースでの表示名
を送信します。
(今回は#テスト用チャンネル
という名前のチャンネルです。
任意のチャンネルで問題ないです。)これで、
#テスト用チャンネル
内で作成したアプリがメッセージを送信できるようになりました。
以上で、Slack側の準備は完了です。
RailsアプリからSlackへメッセージを送ってみよう
Railsアプリの準備
下記リポジトリに、今回使うRailsアプリを用意しているのでcloneしてください。
README.md
の手順にしたがって、環境構築を行ってください。今回使うgemの説明
下記2つのgemを
Gemfile
に追加しています。1. dotenv-rails
開発環境で、
アプリケーションのルートディレクトリに配置した.env
ファイル内から
ENV に変数を読み込むためのgemです。今回は、ワークスペースにアクセスするためのトークンの管理に使用します。
2. slack-ruby-client
RubyでSlackのAPIを利用するためのgemです。
今回は、Slackへメッセージを送信するために使います。
トークンを設定する
Railsアプリケーションに、作成したSlackアプリのトークンを設定します。
(ここで説明するのはレガシーな方法なですが、
今回はいったん手っ取り早くできるこちらの方法を利用します。)
.env
ファイルを作成するアプリケーションのルートディレクトリに、
.env
というファイルを作成しましょう。
ファイルの中身は下記です。.envBOT_USER_ACCESS_TOKEN=Botのアクセストークン
Botのアクセストークン
の部分は、
こちらで作成したトークンに置き換えてください。トークンの設定
次に、下記のファイルを作成してください。
これで、gemslack-ruby-client
を利用したAPIの実行時、
認証用のトークンがパラメータとして送信されるようになります。config/initializers/slack_ruby_client.rbSlack.configure do |config| config.token = ENV['BOT_USER_ACCESS_TOKEN'] end
hello
アクションを作成してみようでは、
slack-ruby-client
を利用してSlackAPIを実行するように、
コントローラーのアクションを作ってみます。ルーティングの追加
config/routes.rb
にルーティングを追加します。
「/hello
というパスにはapplicationコントローラー
のhello
アクション が対応する」
というルーティングです。config/routes.rbRails.application.routes.draw do # For details on the DSL available within this file, see https://guides.rubyonrails.org/routing.html + get "hello", to: 'application#hello' endアクションを作成する
hello
アクションを作成します。app/controllers/application_controller.rbclass ApplicationController < ActionController::API def hello client = Slack::Web::Client.new client.chat_postMessage( channel: '#テスト用チャンネル', text: 'こんにちは' ) end end上記のソースについて簡単に説明します。
client = Slack::Web::Client.new
slack-ruby-client
では、基本的にこのオブジェクトをレシーバとして、
様々なSlackAPIに対応したメソッドを呼び出します。
client.chat_postMessage
これは、 chat.postMessage methodというAPIに対応するslack-ruby-client
のメソッドです。
見ただけでわかると思うのですが、
メソッドの引数で「メッセージを送信するチャンネル」と「テキスト」を指定しています。メッセージを送る
では、実際にメッセージを送信してみましょう。
bin/rails
でサーバーを起動し、
ブラウザで http://localhost:3000/hello にアクセスします。
Slackを確認すると、下記のようにメッセージが送信されていると思います。今回作りたかったアプリケーションはこれで完成です。
今回は一つのAPIしか利用していませんが、
いろいろなAPIを複合的に利用することで目的のアプリを作成できるようになると思います。
- 用意されているAPIの一覧
Block Kit Builderを使ってメッセージのフォーマットを整えてみよう
実際にアプリを作成した場合、もう少しいい感じにテキストを表示したいと思います。
(箇条書き、文字サイズ、文字色の指定など)そんな場合は、下記のBlock Kit Builderを使ってみましょう。
これを使うと、簡単にボタンやテキストを配置のプロトタイプを作成することができます。
画面の右側に作成したリッチテキストから生成されたコードが表示されるので、
これをコピーすればすぐにアプリケーションに組み込むことができます。
作成したコード
{ "blocks": [ { "type": "section", "text": { "type": "mrkdwn", "text": "今日も暑いね:watermelon: 無理せずがんばろう:smile:" } }, { "type": "header", "text": { "type": "plain_text", "text": "何をチェックする?", "emoji": true } }, { "type": "actions", "elements": [ { "type": "button", "text": { "type": "plain_text", "emoji": true, "text": "天気" }, "style": "primary", "url": "https://www.jma.go.jp/jp/yoho/" }, { "type": "button", "text": { "type": "plain_text", "emoji": true, "text": "カレンダー" }, "style": "danger", "url": "https://calendar.google.com/" }, { "type": "button", "text": { "type": "plain_text", "emoji": true, "text": "ニュース" }, "url": "https://news.google.co.jp/" } ] } ] }
hello
アクションを更新してみよう試しに、先ほど作成した
hello
アクションを更新して、
作成したブロックをメッセージとして送信できるようにしてみましょう。
chat_postMessage
の引数に、blocks
を追加しています。
(ソースコードが長いので折りたたんでいます。)
hello
アクションを更新app/controllers/application_controller.rbdef hello client = Slack::Web::Client.new client.chat_postMessage( channel: '#テスト用チャンネル', text: 'こんにちは', blocks: [ { "type": "section", "text": { "type": "mrkdwn", "text": "今日も暑いね:watermelon: 無理せずがんばろう:smile:" } }, { "type": "header", "text": { "type": "plain_text", "text": "何をチェックする?", "emoji": true } }, { "type": "actions", "elements": [ { "type": "button", "text": { "type": "plain_text", "emoji": true, "text": "天気" }, "style": "primary", "url": "https://www.jma.go.jp/jp/yoho/" # 気象庁HP }, { "type": "button", "text": { "type": "plain_text", "emoji": true, "text": "カレンダー" }, "style": "danger", "url": "https://calendar.google.com/" # Googleカレンダー }, { "type": "button", "text": { "type": "plain_text", "emoji": true, "text": "ニュース" }, "url": "https://news.google.co.jp/" # Googleニュース } ] } ] ) endRailsアプリを起動し、 再度 http://localhost:3000/hello にアクセスします。
すると、Slackには下記のような通知がくると思います。Block Kit Builderの紹介は以上です。
Block Kit のチュートリアルについては、こちらも参照してください。あとがき
実際にRailsアプリをHerokuなどにデプロイすることで、
Slack上でコマンドを実行するとそれに応じてメッセージを返すBotを作成することもできます。記事ボリュームの都合上入れられなかったので、それについてはまた次回書きます。
Slack APIについてはいくつか日本語翻訳されているページもあるので、
こちら をベースにいろいろ学習できると思います。参考URL
- 投稿日:2020-08-17T21:50:38+09:00
Railsでactive_hashを使って都道府県などのセレクトボックスを作る
はじめに
・某プログラミングスクールのチーム開発で学んだ知識の備忘録として書きます。
・商品がどの都道府県から発送されるのか、という情報のために使用しました。
・間違いなどあれば指摘いただけますと幸いです。active_hashって何?
・
ハッシュデータとして定義したデータを、擬似的にActiveRecordのように扱う
ことができるのがactive_hash
というgem。
・都道府県など、項目数がほぼ変わらない静的データ
はテーブルにせず、active_hashを使うと便利。
・ActiveRecord <=> ActiveHashのリレーションを張ることができる
。使い方
順を追って書いていきます。
Gemfile# ファイルの一番下に記述追加。haml記法で記述するのでhaml-railsも入れます gem 'active_hash' gem 'haml-rails'ターミナル$ bundle installこれでactive_hashがインストールされました。
ミニアプリを作ってみます。ターミナル$ rails g model item name:string prefecture_id:integer
models/items.rb
db/migrate/20200817033056_create_items.rb
が作成されました。20200817033056_create_items.rbclass CreateItems < ActiveRecord::Migration[6.0] def change create_table :items do |t| t.string :name t.integer :prefecture_id t.timestamps end end endターミナル$ rails db:migrateこれでitemsテーブルができました。
ここ大事です
prefectureモデルを作るのですが、手動で作ります。
rails g model
はしません。modelsディレクトリに
prefecture.rb
ファイルを直接作成します。
作成したら中身を以下のように記述します。prefecture.rbclass Prefecture < ActiveHash::Base self.data = [ {id: 1, name: '北海道'}, {id: 2, name: '青森県'}, {id: 3, name: '岩手県'}, {id: 4, name: '宮城県'}, {id: 5, name: '秋田県'}, {id: 6, name: '山形県'}, {id: 7, name: '福島県'}, {id: 8, name: '茨城県'}, {id: 9, name: '栃木県'}, {id: 10, name: '群馬県'}, {id: 11, name: '埼玉県'}, {id: 12, name: '千葉県'}, {id: 13, name: '東京都'}, {id: 14, name: '神奈川県'}, {id: 15, name: '新潟県'}, {id: 16, name: '富山県'}, {id: 17, name: '石川県'}, {id: 18, name: '福井県'}, {id: 19, name: '山梨県'}, {id: 20, name: '長野県'}, {id: 21, name: '岐阜県'}, {id: 22, name: '静岡県'}, {id: 23, name: '愛知県'}, {id: 24, name: '三重県'}, {id: 25, name: '滋賀県'}, {id: 26, name: '京都府'}, {id: 27, name: '大阪府'}, {id: 28, name: '兵庫県'}, {id: 29, name: '奈良県'}, {id: 30, name: '和歌山県'}, {id: 31, name: '鳥取県'}, {id: 32, name: '島根県'}, {id: 33, name: '岡山県'}, {id: 34, name: '広島県'}, {id: 35, name: '山口県'}, {id: 36, name: '徳島県'}, {id: 37, name: '香川県'}, {id: 38, name: '愛媛県'}, {id: 39, name: '高知県'}, {id: 40, name: '福岡県'}, {id: 41, name: '佐賀県'}, {id: 42, name: '長崎県'}, {id: 43, name: '熊本県'}, {id: 44, name: '大分県'}, {id: 45, name: '宮崎県'}, {id: 46, name: '鹿児島県'}, {id: 47, name: '沖縄県'} ] enditemモデルにも記述を追加します。
item.rbclass Item < ApplicationRecord # この2行を追加 extend ActiveHash::Associations::ActiveRecordExtensions belongs_to_active_hash :prefecture end準備は以上です。
ちゃんと表示できて、データ送信もできたら完成とします。
コントローラーとビューを作ってルーティングも設定します。ターミナル$ rails g controller items newitems_controller.rbclass ItemsController < ApplicationController def new @item = Item.new end def create @item = Item.new(item_params) if @item.save redirect_to new_item_path else render 'new' end end private def item_params params.require(:item).permit(:name, :prefecture_id) end enditems/new.html.haml.form = form_with model: @item, local: true do |f| = f.text_field :name # 入力フィールドです = f.collection_select :prefecture_id, Prefecture.all, :id, :name, {include_blank: "---"}, {class: ""} = f.submit "送信"都道府県はf.collection_selectを使ってセレクトボックス形式で取得します。
= f.collection_select 保存されるカラム名, オブジェクトの配列, カラムに保存される項目, 選択肢に表示されるカラム名, {オプション}, {htmlオプション}
routes.rbRails.application.routes.draw do resources :items root 'items#new' end入力フィールドとセレクトボックスを埋めて送信したら入力画面に戻るようにしています。
成功したら入力フィールドが空になります。
sequelproなどのGUIツールでテーブルの中身を見るとデータが保存されているはずです。都道府県だけじゃなくこんなのにも使えます
・商品の状態
models/item_condition.rbclass ItemCondition < ActiveHash::Base self.data = [ {id: 1, condition: '新品、未使用'}, {id: 2, condition: '未使用に近い'}, {id: 3, condition: '目立った傷や汚れなし'}, {id: 4, condition: 'やや傷や汚れあり'}, {id: 5, condition: '傷や汚れあり'}, {id: 6, condition: '全体的に状態が悪い'} ] include ActiveHash::Associations has_many :items endこの場合、f.collection_selectはこんな感じです。
items/new.html.haml= f.collection_select :item_condition_id, ItemCondition.all, :id, :condition, {include_blank: "選択してください"}, {class: "select"}第5引数にはデフォルトで表示させたい文字列を、
第6引数にはクラス名やid名を指定します。まとめ
ミニアプリを作ったので少し長くなりましたが、active_hashを実装するだけなら以下の手順です。
1.gemをインストール
2.カラム作成(itemsテーブルにprefecture_idカラムをinteger型で作成
)
3.モデルファイル作成してテーブルにあたる記述を追加(prefecture.rb
)
4.Itemモデル側にアソシエーションを記述。通常とは違うので注意以上です。
今回active_hashのメソッドとして全部のデータを取得するためにallメソッド
を使いましたが、他にも色々あります。
参考サイトを載せるので必要であればそちらから見てください。参考
【Rails】active_hashを使って疑似モデルを作ろう
https://pikawaka.com/rails/active_hash
active_hashまとめ
https://qiita.com/Toman1223/items/8633142312bfa886d50b
- 投稿日:2020-08-17T21:44:04+09:00
【パス指定】ネストしたリソースのパス指定
概要
ネストしたリソースのパス指定方法について、一瞬戸惑ってしまったので備忘録として記録します。
環境
・ruby '2.5.7'
・rails '5.2.3'
・rspec-rails '4.0.0.beta2'指定方法
結論:
rails routes
してルーティングを一覧表示して確認する!(例) Rspecのリクエストテストでパス指定をする
次のような、ルーティングを宣言していたとします。
routes.rbresources :datespots do resources :comments, only: [:create, :destroy] endターミナルで
rails routes
すると、ルーティングが一覧表示される。Prefix Verb URI Pattern Controller#Action (省略) datespot_comments POST /datespots/:datespot_id/comments(.:format) comments#create datespot_comment DELETE /datespots/:datespot_id/comments/:id(.:format) comments#destroy (省略)これを元に、パス指定すればOK!
comments_spec.rb(省略) it "有効な内容のコメントが登録できること" do expect { post "/datespots/#{datespot.id}/comments", params: { datespot_id: datespot.id, comment: { content: "オシャレですね!" } } }.to change(datespot.comments, :count).by(1) end (省略)参考
- 投稿日:2020-08-17T20:51:47+09:00
【CSS】flex box画像の改行がしたい
画像付きボックスの改行ができなくて沼ったのでメモ。冷静に調べたらもっと早く解決できたと思いますが自分の検索力の無さを恨みますw
やりたいこと
この画像の様な画像つきのボックスを
画像①
こんな感じで幅をも持たせて各行に3個ずつ配置したい。
画像②
- まず前提としてボックスの親要素に
display: flex;
をかけています。「ボックスのwidthを親要素の32%に広げたらいけるんじゃね?」と思いましたがダメでした。
ソースコード
posts.scss///コンテナの親要素 .posts { margin: 50px 120px 50px; height: auto; display: flex; justify-content: space-between; ///コンテナ &__container { height: 300px; width: 32%; background-color: white; border-radius: 10px;このコードの様に書くと画像①の様になってしまいます。widthを指定しても無視されてボックスが画面一杯に一列に収まろうとします。
結果
親要素の
posts
にflex-wrap: wrap;
を追加してあげたら画像②の様に折り返して表示されました ^^flexboxを使うときはwrapをかけないと折り返され無いんですね。
同じ様な感じで困っている人に見てもらえたらいいなと思います。^^ 僕だけかもしれませんがw
- 投稿日:2020-08-17T20:40:52+09:00
プログラムを書くときの注意点:その2
【概要】
1.結論
2.オープン・クローズドの原則とは何か
3.オープン・クローズドの原則どう使うのか
4.なぜオープン・クローズドの原則が必要か
5.ここから学んだこと
1.結論
オープン・クローズドの原則にも従う!
2.オープン・クローズドの原則とは何か
●オープン・クローズドの原則とは、
拡張に対して開いていて、
修正に対して閉じていなければならない
つまり、拡張する分にはOKだけど、
拡張した時の修正範囲は最小限に止めようね。
そうしないと破壊的変更(とてつもない修正)を
しないといけなくなるということです!3.オープン・クローズドの原則はどう使うのか
言葉だけではイメージがしにくいと思うので
例を挙げてみます!オープン・クローズドの原則class A class Interface B class *** implementsB:interface B class Interface B puts ******オープン・クローズドの原則ではないclass A class B puts ******ただあまりにも抽象化しすぎると、
本当に必要でないクラスができてしまいます。
(上記ではわかりやすくするために簡素化しているので
”オープン・クローズドの原則ではない”方がわかりやすいですし、
class A
puts ****でいいまであります。)上記は簡単に書いているのでまだ追えていますが、
階層が深くなるとどこにいるのか
わからない(可読性がなくなる)
部分がでてきます。なので、変更箇所が今後ありそうな箇所を
予測した際に有効で、難しい原則です。これは”プログラムを書くときの注意点:その4(次々回投稿)”
のインターフェース分離の原則でも関わってきます。
4.なぜオープン・クローズドの原則が必要か
結論としては、プログラミングを書く際の要は以下の
3つに集約されると思っています。Ⅰ)保守性:修正(エラー発見のしやすさ)・管理のしやすさ
Ⅱ)拡張性:追加機能実装のしやすさ
Ⅲ)可読性:記述のわかりやすさ
が必要だと考えております。上記3つのことは自分が他の4つの原則を説明する際に同じことを言うので、
5つの原則のうちどれかを読んでいただくと
結論はすべてこの3つに収まります。つまり、上の3つを叶えるには
オープン/クローズドの原則に”も(他の4つの原則もあるので)”従う!!
5.ここから学んだこと
i)implements,interfaceメソッドを知ることができました!
ii)implements,interfaceメソッドを駆使することで
可読性かつ保守性のあるプログラムをかけますが、あまり不本意に適用
したらいいわけでないと思いました。プロジェクトでお客さまに提案する際や、
今後拡張しそうな箇所を予測した上で使う原則であり、非常に奥深い原則だなと感じました。
- 投稿日:2020-08-17T20:04:26+09:00
Railsでデータベースの中身を確認する
プログラミングの勉強日記
2020年8月17日 Progate Lv.226
今まではSQLiteStudioで確認していた。
SQLiteStudioの方が見やすいが、見るのに手間がかかるので、コンソールで確認することができたのでまとめる。方法
SQLiteはデータベースサーバを使用しないで、データベースごとに1つのファイルを使うことで管理する。
1. SQLiteコマンドのツールのインストール
SQLiteの公式サイトにアクセスする。Downloadをクリック。
Windows10の環境を利用するので、recompiled Binaries for Windowsのsqlite-tools-win32-x86-3330000.zipをクリックして、ダウンロードする。
ダウンロードが完了したら、zipファイルを展開する。
今回はRailsアプリの中のdbフォルダの下に展開した3つのファイルを置いた。2. コンソールの立ち上げ
dbフォルダの中に移動して、
.\sqlite3 .\development.sqlite3
とコマンドを入力するとコンソールが立ち上がる。
sqlite>
が出てくれば成功。.\sqlite3 .\development.sqlite3 SQLite version 3.33.0 2020-08-14 13:23:32 Enter ".help" for usage hints.主なコマンド
テーブルの一覧の表示
.tables
で作成したテーブルの一覧を表示する。sqlite> .tables ar_internal_metadata posts schema_migrations goods reviews usersカラム名などのテーブルの構造を表示する
.schema テーブル名
で指定したテーブルの構造を表示する。sqlite> .schema users CREATE TABLE IF NOT EXISTS "users" ("id" integer PRIMARY KEY AUTOINCREMENT NOT NULL, "name" varchar, "email" varchar, "created_at" datetime NOT NULL, "updated_at" datetime NOT NULL, "image_name" varchar, "password_digest" varchar);テーブルの中身を確認する
select * from テーブル名;
でテーブルの中身を確認できる。*
ですべてのテーブルの中身を表示できる。セミコロンを忘れないように。sqlite> select * from users; 1|aiueo|aiueo|2020-08-09 09:28:46.103511|2020-08-09 09:29:37.184446|1.jpg|$2a$12$eJlR9MsvgcnbXaEY2DpD3.hoQG3fy2vwdtE44buDy6DltamJQ/2Jmコンソールの終了
.quit
でコンソールを終了できる。.quit参考文献
- 投稿日:2020-08-17T19:17:02+09:00
Rails enum 都道府県をプルダウン方式で選択
はじめに
個人開発アプリでGoogle APIと連携して地図情報を取得できる様にしたのですが、
住所を全て手入力するのは面倒なので都道府県をプルダウン方式で選択できるようにしようと思います。
new.html.erb<%= form_for @ride, method: :post do |f| %> <%= f.select :prefecture, ['北海道', '青森県', '秋田県', '岩手県' 以下略], { include_blank: '選択してください' } %> <% end %>コードの可読性を無視して実装するならこんな感じで入力していくだけなのですが、
このようにview側に47都道府県全てを入力すると非常に見苦しいと思ったのでスマートにできる方法を探してみました。
enum
enumというものがあるようでこれによってviewではなくmodelに記述することができ、
view側のコードをかなりスッキリさせることができます!
class CreateRides < ActiveRecord::Migration[5.2] def change create_table :Rides do |t| t.integer :ride_area, null: false, default: 0 end endまずはintegerでカラムを作成します。
ride.rbclass Ride < ApplicationRecord enum ride_area:{ "---":0, 北海道:1,青森県:2,岩手県:3,宮城県:4,秋田県:5,山形県:6,福島県:7, 茨城県:8,栃木県:9,群馬県:10,埼玉県:11,千葉県:12,東京都:13,神奈川県:14, 新潟県:15,富山県:16,石川県:17,福井県:18,山梨県:19,長野県:20, 岐阜県:21,静岡県:22,愛知県:23,三重県:24, 滋賀県:25,京都府:26,大阪府:27,兵庫県:28,奈良県:29,和歌山県:30, 鳥取県:31,島根県:32,岡山県:33,広島県:34,山口県:35, 徳島県:36,香川県:37,愛媛県:38,高知県:39, 福岡県:40,佐賀県:41,長崎県:42,熊本県:43,大分県:44,宮崎県:45,鹿児島県:46, 沖縄県:47 } endモデル側にはこんな感じで都道府県を書いておきます。
ハッシュのキーがセレクトボックスに表示されます。
new.html.erb<%= form_for @ride, method: :post do |f| %> <%= f.select :prefecture, Ride.ride_areas.keys, {} %> <% end %>冒頭で書いたコードをこのように書き換えてあげましょう。
Ride.ride_areas.keys, {}
と書く事でモデルに書いている都道府県全てを順番に処理してくれるのでブラウザ上ではプルダウン方式で都道府県が選択できるようになっています!以上です。
- 投稿日:2020-08-17T18:35:53+09:00
An error occurred while installing libv8 (3.16.14.19), and Bundler cannot continue
bundle install しようとした時に libv8 でエラー
自分の環境では下記の手順で bundle install が通ったので、メモ。
- エラー
An error occurred while installing libv8 (3.16.14.19), and Bundler cannot continue.Make sure that `gem install libv8 -v ‘3.16.14.19’ —source
- rbenvにbundleをインストール
「libv8とtherubyracerが入らない時の対処法」をやっても入らないとき - Qiita
bundleがrbenv内のgemを使っていないとbundle installが通らないので、rbenvにbundleをインストール
- 下記のコマンドを実行
macOS Mojaveで古いlibv8とtherubyracerが入らない時の対処法 - Qiita
brew install v8-315 bundle config --local build.libv8 --with-system-v8 bundle config --local build.therubyracer --with-v8-dir=$(brew --prefix v8-315)さらにエラーがでた
An error occurred while installing mysql2 (0.4.10), and Bundler cannot continue. Make sure that `gem install mysql2 -v '0.4.10' --source 'https://rubygems.org/'` succeeds before bundling.LIBRARY_PATH の変更
export LIBRARY_PATH=$LIBRARY_PATH:/usr/local/opt/openssl/lib/一応これで bundle install が通った。
- 投稿日:2020-08-17T17:42:46+09:00
プログラムを書くときの注意点:その1
【概要】
1.結論
2.SOLID原則とは何か
3.単一責任の原則はどう使うのか
4.なぜ単一性の原則が必要か
5.ここから学んだこと
1.結論
単一責任の原則にも従おう!
2.SOLID原則とは何か
●SOLID原則とは、
i)単一責任の原則:1つのclassに1つの役割を
ii)オープン/クローズドの原則:追加機能はOK,ただ修正はせずに
iii)リスコフの置換原則:親クラスは子クラスと同じ動きに
iv)インターフェース分離の原則:利用用途に応じた最小限の動きに
v)逆依存性の原則:破壊的変更をさせるなの英語名の頭文字を取ったものです!
(ここでは分かり易く書きたいため、英語名は省略しています)
3.単一責任の原則はどう使うのか
あくまで原則なので、基本的な考え方の部分になります。
なので例を交えての紹介になります。例えばご紹介した、(”3つの値の正誤を確かめる条件式~演算子,論理積~
”)https://qiita.com/taka_no_okapi/items/dd92ab3f74cd28d3b364
のプログラムの”マシーン”に”人がお金を投入する”というプログラムをさせたいとします。user1.rbclass User1 def initialize(many_money) @money = many_money end def money @money end def choose_drink gets.to_i end end上記のプログラムをマシーンが書いてあるファイルに一気に書いてもいいですが、それですとマシーンが同じ数字を書く機能を持ちつつ人がお金を投入するシステムまで導入し1つのclassに2つの役割が入ってしまいます。
であれば”class Machine” “class user1”で
マシーン(クラス)は1つの役割、ユーザー(クラス)は1つの役割
にした方が保守性・拡張性・可読性が飛躍的に高まります。
4.なぜ単一責任の原則が必要か
結論としては、プログラミングを書く際の要は以下の
3つに集約されると思っています。Ⅰ)保守性:修正(エラー発見のしやすさ)・管理のしやすさ
Ⅱ)拡張性:追加機能実装のしやすさ
Ⅲ)可読性:記述のわかりやすさ
が必要だと考えております。上記3つのことは自分が他の4つの原則を説明する際に
同じことを言うので、5つの原則のうちどれかを読んでいただくと
結論はすべてこの3つに収まります。つまり、上の3つを叶えるには
単一責任の原則に”も(他の4つの原則もあるので)”従おう!!
5.ここから学んだこと
i)単一性の原則は非常に理解しやすく、すぐに適応できるので
意識するだけでプログラムの考えを受け入れやすかったです!ii)物体ごと(上記の例ですと、user1とMachine)だけではなく
機能ごと(Machineであれば同じ数字を揃える意外に、景品を選んでくれる機能など)でも分けたほうがプログラムしやすいです!
- 投稿日:2020-08-17T17:39:51+09:00
Railsのコントローラーについて
概要
Railsアプリケーションのコントローラーについて解説してみたいと思います。
今回のゴール
『MVCモデルについて知る』・『コントローラーの役割について』・『実践的な使い方』をついて確認することです。
1. MVCモデルとは
アプリケーションを作成する時に、コードを上手に管理するための考え方のひとつです。
あくまで考え方のひとつなので、絶対的に正しいというものではありません。
Railsアプリケーションは、このMVCフレームワークを取り入れています。MVCの3要素
『Model』・『View』・『Controller』になります。
・Model
・・・ システムの中でビジネスロジックを担当する・
View
・・・ 表示や入出力といった処理をする・
Controller
・・・ ユーザーの入力に基づき,ModelとViewを制御するRailsにおけるMVCの処理の流れ
クライアントからのリクエストを『Controller』が受け取る
『Controller』は『Model』にデータ処理をお願いする
『Model』はデータベースからデータを処理し、『Controller』にデータを返す
『Controller』は『View』に受け取ったデータの処理をお願いする
『View』はクライアントが見るのに適した形(HTML文書)を作成し『Controller』に返す
『Controller』はクライアントにHTML文章をレスポンスとして返す
1〜6を繰り返すことにより、Webアプリケーションとして成り立っています。
2. コントローラーの役割について
結論
・ルーティングから送られた情報をもとに、指定されたコントローラーのアクションメソッドを実行すること
・Model・Viewと連携して、クライアントにレスポンスを返すことアクションメソッド
ルーティングから指定されたアクションの具体的な処理内容を記述したメソッドです。
アクションメソッドのイメージclass SamplesController < ApplicationController def index # 具体的な処理内容 ...... ...... end end今回の例ですと...
ルーティングでsamplesコントローラーのindexアクションが指定された時、実行するアクションメソッドをdef index...end
という形で記述します。Modelとの連携について
目的
モデルを介して、データベースの新規作成や変更や取得をすることです。
方法
モデルが継承しているActiveRecord クラスのメソッドを使い、モデルに指示を出します。
下記はメソッドの一部の例になります。
メソッド 内容 all データベースの全てのデータを取得する find データベース内の、ある1つのデータを取得する new データの新規作成を生成する save データベースにデータを保存する メソッドのイメージ(モデルクラス名).[メソッド] Sample.allViewとの連携について
目的
モデルから受け取ったデータをビューに渡し、クライアントに返すレスポンスデータを作成することです。
方法
モデルからのデータをインスタンス変数を代入します。
@samples = Sample.allこれにより、ビューファイルでデータを使えるようになります。
3. 実践的な使い方
コントローラーの設定場所
app/controllers
ディレクトリ内に
コントローラー名_controller.rb
ファイルを設定します。コントローラーの命名規制
基本的に『複数形』にします。
理由は、Railsが使用するファイルなどを名前によって自動的に推測するからです。
仮に単数形にもできますが、開発者自身で明示的にコード記述しなければいけなかったり、予期せぬエラーのもとになってしまいます。
名称 例 備考 コントローラー名 samples コントローラークラス名 SamplesController キャメルケース コントローラーファイル名 samples_controller.rb スネークケース コントローラーファイルの構造
コントローラーファイルの中身は、このようになっています。
app/controllers/samples_controller.rbclass SamplesController < ApplicationController def index # 具体的な処理内容 ...... ...... end end作成したコントローラーファイルは『ApplicationControllerクラス』を継承します。
ApplicationControllerクラスとは
app/controllers/application_controller.rbclass ApplicationController < ActionController::Base end
app/controllers/application_controller.rb
ファイルに定義されたクラスです。
ActionController::Baseクラスを継承しただけの、(ほとんど)空のクラスになります。原則、各コントローラーは、ApplicationControllerクラス継承しているので
アプリケーション共通の機能(ログイン・ログアウトなど)が必要な場合に使用します。
ActionController::Baseクラスとは
コントローラーの基本的な機能を提供するクラスです。
リクエスト/レスポンス処理に関わる基盤部分を担っています。HTTPリクエストのパラメータの処理
コントローラーでは、クライアントからのHTTPリクエストのパラメータを『paramsメソッド』を経由して取得しています。
paramsメソッド
Railsが暗黙的にリクエストパラメータを処理して、ハッシュ形式でデータをparamsに格納してくれるメソッドです。
GETリクエスト・POSTリクエストによるアクセスでも、データの受け取り方に違いはありません。GETリクエストによるアクセス
HTTPリクエストのリクエストラインの『リクエストURI』にパラメータを含め、Webサーバにアクセスします。
『URL形式』と『クエリ形式』でパラメータを渡すことができます。
URL形式
下記のルーティング設定があった時に
Prefix Verb URI Pattern Controller#Action user GET /users/:id(.:format) users#show
http://sample.com/users/7
というURLでアクセスすると
リクエストの:id
のパラメータは7
という意味になり
Rails内ではparamsに格納されparams[:id]
の値は"7"
となります。app/controllers/users_controller.rbclass UsersController < ApplicationController def show params[:id] # "7" end end
クエリ形式
URLの最後に「?」に続けて「パラメータ名=値」を記述します。
複数のパラメータがある場合は「&」でつなげて記述します。
上記の例の同じルーティングを利用し
http://sample.com/users/7?keyword=query&num=10
というURLでアクセスすると
params[:keyword]
の値は"query"
、params[:num]
は"10"
となります。app/controllers/users_controller.rbclass UsersController < ApplicationController def show params[:keyword] # "query" params[:num] # "10" end end
POSTリクエストによるアクセス
クライアントがフォームからの入力で「送信」ボタンを押した場合などに発生するリクエストです。
HTTPリクエストの『ボディ』にパラメータを含め、Webサーバにアクセスします。またGETリクエストに比べて、多くのパラメータを送信することができます。
paramsを保存する時の注意点
『params』をデータベースに保存する時は、『Strong Parameters』という仕組みを使います。
Strong Parametersとは
Rails3系まで使われていた『Mass Assignment』の脆弱性を解消するための仕組みです。
『Mass Assignment』では、モデルに保存に関するparamsの情報を記述していましたが
『Strong Parameters』では、コントローラーに保存するparamsの情報を記述します。Strong_Parametersのイメージclass UsersController < ApplicationController def create @user = User.new(user_params) # user_paramsメソッドを使って、データの新規作成 @user.save # モデルを介して、データベースに保存する end # Strong Parametersはクラス外部から呼び出さないので、privateメソッドに記述する private def user_params params.require(:user).permit(:name, :age) end end今回の例ですと
user_params
メソッドで、保存するパラメータを:user
の:name
と:age
に指定しています。requireメソッド
データベースに保存するテーブル名を指定します。
permitメソッド
データベースのテーブルに保存するカラム名を指定します。
コントローラーの解説は以上になります。
ありがとうございました。
- 投稿日:2020-08-17T17:35:43+09:00
docker-composeでDeviseを導入
Device
ログイン機能やユーザー登録機能をとても簡単に実装することができるgem。参考にした記事
https://qiita.com/Orangina1050/items/a16e655519a60f35b394下準備
コントローラーの作成 ついでにアクションとビューを作成するterminal$ docker-compose run web bin/rails g controller comments index導入編
Gemfileに、deviseを追加する。terminal$ docker-compose run web bundle install #deviseをインストールする $ docker-compose build #構築する。終わったら、 deviseの設定ファイルを作成する
terminal$ docker-compose run web bin/rails g devise:installログイン機能用のモデル作成を行い(1)、を行いマイグレーション(2)
その後、ログイン機能に必要なビューファイルをまとめて作成(3)terminal$ docker-compose run web bin/rails g devise user #・・・(1) $ docker-compose run web rake db:migrate #・・・(2) $ docker-compose run web bin/rails g devise:views #・・・(3)views/comments/index.html.erbを編集し、下記を加える
index.html.erb<div class="field"> <%= f.label :name %> <br /> <%= f.text_field :name %> </div>ちなみに、私はここで、
NoMethodError in Devise::Sessions#new
エラーが発生した。一度、コンテナを止めて(1)、削除し(2)、再度コンテナを構築したら(3)、解決した。
(理由をわかっていないので宿題ですね)terminal$ docker ps -a $ docker stop (コンテナ名) #・・・(1) $ docker rm (コンテナ名) #・・・(2) $ docker-compose build #・・・(3)新規登録時に名前を入力できるようにする
usersテーブルにnameカラムをstring型で追加するマイグレーションファイルを作成terminal$ docker-compose run web bin/rails g migration AddNameToUsers name:string $ rake db:migrateここでもまた、エラーが発生する場合は、再起動すると直る場合あり!
DBに名前を格納できるように変更する
deviseは初期の状態では、strong parameterが新規登録時のメールアドレスとパスワードのみ受け取るように設定されている。
しかし、deviseのstrong parameterはgem内のため、いじることができない。
なので、deviseが提供しているconfigure_permitted_parametersメソッドを利用するconfigure_permitterd_parametersとは・・・
deviseのstrong parameterを追加することができるメソッド
application_controllerに記述するcontrollers/application_controller.erbbefore_action :configure_permitted_parameters, if: :devise_controller? def configure_permitted_parameters devise_parameter_sanitizer.permit(:sign_up, keys: [:name]) # 新規登録時(sign_up時)にnameというキーのパラメーターを追加で許可する end
- 投稿日:2020-08-17T16:38:21+09:00
resourcesメソッド以外のアクションを行いたい場合
【概要】
1.結論
2.collection,memberメソッドとは何か
3.どのように使うか
4.なぜcollection,memberメソッドが必要か
5.ここから学んだこと
1.結論
member,collectionメソッドを使おう!
2.collection,memberメソッドとは何か
簡単に言いますと、
member:resourcesメソッド以外のアクション(特定のデータあり)
collection:resourcesメソッド以外のアクション(特定のデータなし)resourcesメソッドについては以下のURLを参照してください!
URL:特定のデータとは”:id”のことを指し、
“member”はAというUserに紐づいているものしか
見れない(=特定の人が特定の情報しかみれない)アクションをしたい場合に使用できます!例えばお気に入り登録を見たい場合です。
“collection”は、全てのデータを対象とします。例えば検索機能を追加したい場合です。
3.どのように使うか
member,collectionも使い方は同じで、
routes.rbcollection do get ‘*****(入れたい任意のアクション名)’で使用できます!
もちろんmember,collectionを使用せずその他のアクションを設定す流方法があります。
memberメソッドですと
routes.rbget ‘users/:id/(任意のアクション名)’, to ‘users#(任意のアクション名)’colletionメソッドですと
routes.rbget ‘users/(任意のアクション名)’, to ‘users#(任意のアクション名)’になります。
ただ注意点としてはprefixが自動生成されないので
冗長な表現になりかねないです。簡単にかけるものは簡潔にプログラムしないと、保守性・拡張性・可読性が損なわれます!
4.なぜcollection,memberメソッドが必要か
結論としては、resourcesメソッド以外のアクションを行いたいからです。
つまり、member,collectionメソッドを使おう!ということです。
5.ここから学んだこと
I)7つのアクション以外に設定できるアクションがあることをしり、ユーザーがが求めるユーティリティーへの対応幅が広がりました!
ii)わざわざURLを指定してアクションを設定しないといけない手間が省け
プログラムを見やすく書きやすくできる手段を知りました!
- 投稿日:2020-08-17T13:21:59+09:00
CRUD,resourcesメソッドとの関係性
【概要】
1.結論
2.CRUD,resourcesメソッドとは何か
3.なぜCRUD,resourcesメソッドが必要か
4.ここから学んだこと
5.余談
1.結論

️webアプリケーションに必要な4つの概念(7つのアクション)の主要機能

️
Create=new+create
Read=index+show
Update=edit+update
Delete=destroy
2.CRUD,resourcesメソッドとは何か
●CRUDとは、
Create:登録機能
Reading:参照機能
Update:変更機能
Delete:削除機能
の処理の頭文字を取ったものです!●resourcesメソッドとは”CRUD"を実現するためのメソッドで、
new:新規作成
create:保存
index:一覧表示
show:詳細表示
edit:編集
update:更新
destroy:削除
のRuby on Railsの慣習的な7つのアクションが1セットになったメソッドになります!
3.なぜCRUD,resourcesメソッドが必要か
結論から申し上げますと、
webアプリケーションを作るために必須の概念とアクションなんです!CRUDは4つの概念(規則)であり、
resourcesメソッドはCRUDを行うための7つの行動(アクション)なんです。
Amazonでも、楽天でも、Twitterでもこのアクションは必ず入っています!むしろ入っていないと、一般的に我々が使用している
Webアプリケーション機能を果たせません!CRUDのそれぞれの概念に対応しているアクションが
あります。
4.ここから学んだこと
i)CRUDの4つの概念をさらに細かく7つのアクションに落とし込むことで
一つの概念をより細かいアクションで理解することができました!
ii)Webアプリケーションを作るには基本的な考え方があり、
その仕組み作りの部分でCRUDを基本に肉付けしていくという
フレームワークを知ることができました!
5.余談
では、Railsにその本来備わっている7つのメソッド以外に
どうやってroute.rbにアクションをつけるかということは
次回の”collection,memberメソッド”をお楽しみに!
- 投稿日:2020-08-17T12:19:08+09:00
Rails jsファイルの読み込みはなぜviewの一番下に記述するのか?
今までなんとなくでjsファイルの読み込みをviewの一番下に記述してたが、なぜそうするのかが学べたので備忘録投稿
scriptタグを記述する場所
scriptタグを記述する場所は以下の2つ
-</body>
の直前
-<head></head>
の中どっちに記述した方がいいの?
通常は
</body>
の直前に記述するのがいい。
理由としてはブラウザがHTML要素を読み込むとき、上から順々に読み込んでいく。そのときにjsのコードを読み込むのはHTMLに比べて時間がかかる。
つまり上に記述される<head></head>
の中にすると、jsの読み込み時間がかかってしまい肝心なHTML要素が読み込まれずに、ブラウザに何も表示されなくなる時間が発生してしまう。つまり
</body>
の直前に記述すると、、、?
<body></body>
の最後に記述することによって、HTML要素の解析を済ましてからjsファイルの読み込みをさせた方が、ユーザビリティが高い例外
<body></body>
が表示されると同時にjsを実行させたり、jsでcssを操作する場合などは<head></head>
の中に記述する必要がある。
- 投稿日:2020-08-17T11:57:46+09:00
CSV出力の0落ち対応
- 投稿日:2020-08-17T11:02:18+09:00
部分テンプレートの実装
部分テンプレートとは
同じHTML構造の部分を共通化することによって、無駄なくビューファイルを作成することができます。この共通化された部分を、 部分テンプレートといいます。
部分テンプレートを使用した場合、そのHTML構造を他のビューでも使いまわすことができるという利点も存在します。
また、部分テンプレートのファイル名は必ずアンダーバー「_」から始まります。
部分テンプレートを使用したい場所を切り取る
例えば、以下のeach文の中身を切り取る(command+x)。
app/views/posts/index.html.erb<% @posts.each do |post| %> <div class="content"> <div class="content__left"> <div class="content__left--image"></div> </div> <div class="content__right"> <div class="content__right__top"> <%= link_to post.title, post_path(post.id), class: "content__right__top--title" %> </div> <div class="content__right__bottom"> <div class="content__right__bottom--userName"> <%= link_to post.user.nickname, user_path(post.user), class: "content__right__bottom--userName--btn" %> </div> <div class="content__right__bottom--date"> <%= post.created_at %> </div> </div> </div> </div> <% end %>部分テンプレート用のファイルを作成
app/views/postsディレクトリに、部分テンプレート用のファイル_post.html.erbを作成します。
app/views/posts/_post.html.erb<div class="content"> <div class="content__left"> <div class="content__left--image"></div> </div> <div class="content__right"> <div class="content__right__top"> <%= link_to post.title, post_path(post.id), class: "content__right__top--title" %> </div> <div class="content__right__bottom"> <div class="content__right__bottom--userName"> <%= link_to post.user.nickname, user_path(post.user), class: "content__right__bottom--userName--btn" %> </div> <div class="content__right__bottom--date"> <%= post.created_at %> </div> </div> </div> </div>部分テンプレートを呼び出す
続いて、こちらの部分テンプレートを呼び出します。そのためには、renderメソッドを利用します。
厳密にいうと、renderメソッドにpartialオプションとlocalsオプションを加えて利用する。
partialオプションとは
renderメソッドで使用できるオプションです。 partialというオプションを付けることで、明示的に部分テンプレート名を指定し、部分テンプレートを表示することができます。
下の例では、_sample.html.erbという部分テンプレートを呼び出しています。【例】
<% render partial: "sample", locals: { post: "hello!" } %>localsオプションとは
renderメソッドで使用できるオプションです。 localsというオプションを付けることで、部分テンプレート内でその変数を使えるようになります。
【例】
<% render partial: "sample", locals: { post: "hello!" } %>これで部分テンプレート内においてhello!という文字列の代入されたpostという変数が使えるようになります。
実装
app/views/posts/index.html.erb<% @posts.each do |post| %> <%= render partial: "post", locals: { post: post } %> <% end %>ここでのrenderメソッドのlocalsオプションに注目してみます。{ post: post }の右側のpostはeachメソッドのブロックパラメータのpostで、Postのインスタンスを示しています。一方、左側のpostは部分テンプレート内での変数の名前を表しています。
以上!
- 投稿日:2020-08-17T05:36:46+09:00
Railsでワクワク個人開発 第2回:画面遷移図とログイン実装
画面遷移図を書こう
人の記憶は儚いもので、各所に散らされたコードを見てもなんら思い出せることがない。githubのコミット履歴には確実に残っているが、そのときの私の思いはどこにあるのだろう。個人開発の記録を少しずつ記していく。
画面遷移図を書いた。drawioという便利なソフトがあった。vscodeの拡張機能としても利用できたので大変ありがたい。
この記事にとても詳しく書かれている。
https://qiita.com/riku-shiru/items/5ab7c5aecdfea323ec4e
drawioの操作感はわりと優れている。さっさと好きな絵がかける。githubにも図形がそのまま反映されるといいな。なにか方法があるはずだ。とりあえず風呂敷は広げるべきだ。まだ実装できないところもとりあえず書いておく。そうすれば後々いい思い出になるはず。
ログイン機能の実装
さっそくログイン機能を作ろう。これはdeviseというgemをつかう。
Gemfile
にgem 'devise'
を追加してコマンドラインでbundle install
を行う。
あとの詳しい設定はこちらの記事にある。
https://qiita.com/salvage0707/items/d3ddc889458ac186e62eいろいろ書いてあるが、「4, viewファイルの生成」まで行えば問題ない。 (私はモデル作成のコマンドを
rails g devise user
とした。)htmlの表示を変更しよう。
app/views/layouts/application.html.erb
を変更する。<!-- 略 --> <body> <% if user_signed_in? %> <%= link_to "ログアウト", destroy_user_session_path, method: :delete %> <% else %> <%= link_to "ログイン", new_user_session_path %> <%= link_to "新規登録", new_user_registration_path %> <% end %> <%= yield %> </body> <!-- 略 -->よく調べていないが、このapplication.html.erbというのは全てのビューファイルの根幹になるものらしい。手打ちでHTMLをやっていたころにフレームページをつくったがそれに似ている。上記の
<%= yield %>
に各ファイルの内容が表示されるようだ。
<% if user_signed_in? %>
という文を書くことで、ログインしているかどうかで表示を変更できるようにしている。link_to記法はよく使われるものなので勉強したい。
<%= link_to 'link', パス名 %>linkが表示される文字、パス名に行き先を設定する。パス名はコマンドラインで
rails routes
とやると現在設定されているパスの一覧が表示されるので、それを参考にして欲しい。↓ rails guideに詳しい記述があった。
https://railsguides.jp/getting_started.html#%E3%83%AA%E3%83%B3%E3%82%AF%E3%81%AE%E8%BF%BD%E5%8A%A0
おわり
ちょっとずつ記憶が掘り起こされてきた感がある。これでログイン/ログアウトができるようになったので、ちょっとユーザーのサンプルデータをつくってみよう。seed.rbとかいうファイルに設定すればいい。それが終わったら今度はモデルの関連付けをする。これが曲者だった。
- 投稿日:2020-08-17T00:44:45+09:00
Rails Tutorialを咀嚼する【第3章 ほぼ静的なページの作成】
3.1 セットアップ
【演習】
1.BitbucketがMarkdown記法のREADME (リスト 3.3) をHTMLとして正しく描画しているか、確認してみてください。
2.本番環境 (Heroku) のルートURLにアクセスして、デプロイが成功したかどうか確かめてみてください。⇒そのままやってみてください。
3.2 静的ページ
■コントローラ
コントローラとは (基本的に動的な) Webページの集合を束ねるコンテナのこと。
→ちょっと意味が分からない。■rails generate controller StaticPages home help
コントローラーにstatic_pages_controller.rbが生成される。
routes.rbに
・static_pages/home
・static_pages/help
が生成される。この時点でアドレスバーに「static_pages/home」と入力すれば移動する。
異動する先はビューの「home.html.erb」。
※helpも同様。■HTTPメソッド
GET、POST、PATCH、DELETEの4つがある。
GET:ページを呼び出す
POST:ユーザーが何かを入力して送信するときに使う。
PATCH:おそらく更新に使う。
DELETE:削除に使う【演習】
1.Fooというコントローラを生成し、その中にbarとbazアクションを追加してみてください。
→コントローラーを生成するのでrails generateを使います。
rails generate controller Foo bar baz2.コラム 3.1で紹介したテクニックを駆使して、Fooコントローラとそれに関連するアクションを削除してみてください。
コラムを参照
→rails destroy controller Foo bar baz3.3 テストから始める
■テストケース、テストスイート
1つのテストのことをテストケースと呼ぶ。
テストケースが集まったものをテストスイートと呼ぶ。■テスト駆動設計
テストコードを書いてから開発を進める手法■static_pages_controller_test.rb
rails gと同時に生成されている。test/controllers/static_pages_controller_test.rbtest "should get home" do get static_pages_home_url assert_response :success endこのファイルは既にActionDispatch::IntegrationTestを継承しているので、
そういうものなのだと理解する。
「should get home」というテストを新しく生成。
「get static_pages_home_url」でアクセス。
「assert_response :success」で成功か否か判断。■touch app/views/static_pages/about.html.erb
touch app/views/static_pagesのディレクトリに
about.html.erbのファイルを生成する。右クリックからの「ファイルを作成」でもいける。
■about.html.erb
とかはいらない。
3.4 少しだけ動的なページ
→リファクタリングを行っているページなので、最悪後回しでも大丈夫。
■mv app/views/layouts/application.html.erb layout_file
application.html.erb を layout_fileに移動する。■assert_select "title", "Home | Ruby on Rails Tutorial Sample App"
移動した先のページのタイトルタグの中身が「"Home | Ruby on Rails Tutorial Sample App"」かどうか確認する。【演習】
1.StaticPagesコントローラのテスト (リスト 3.24) には、いくつか繰り返しがあったことにお気づきでしょうか? 特に「Ruby on Rails Tutorial Sample App」という基本タイトルは、各テストで毎回同じ内容を書いてしまっています。そこで、setupという特別なメソッド (各テストが実行される直前で実行されるメソッド) を使って、この問題を解決したいと思います。まずは、リスト 3.30のテストが green になることを確認してみてください (リスト 3.30では、2.2.2で少し触れたインスタンス変数や文字列の式展開というテクニックを使っています。それぞれ4.4.5と4.2.2で詳しく解説するので、今はわからなくても問題ありません)。
→「Ruby on Rails Tutorial Sample App」という文字ががたくさん出てきて面倒だよね?という話です。@base_titleにRuby on Rails Tutorial Sample Appという文字列を代入し、
それぞれで展開をしている。■Provideメソッド
タグの中身以外が同じになるようにしている。
provideメソッドでパラメータを引き渡し、yieldメソッドで受け取る。
タイトルを統一させることで、■app/views/layouts/application.html.erb
デザインの根幹をなしているもの。【演習】
1.サンプルアプリケーションにContact (問い合わせ先) ページを作成してください17 (ヒント: まずはリスト 3.15を参考にして、/static_pages/contactというURLのページに「Contact | Ruby on Rails Tutorial Sample App」というタイトルが存在するかどうかを確認するテストを最初に作成しましょう。次に、3.3.3でAboutページを作ったときのと同じように、Contactページにもリスト 3.40のコンテンツを表示してみましょう。)。1.static_pages/にcontact.html.erbというファイルを作る。
routes.rb<% provide(:title, "Contact") %> <h1>Contact</h1> <p> Contact the Ruby on Rails Tutorial about the sample app at the <a href="https://railstutorial.jp/contact">contact page</a>. </p>2.テストを作る。名前をcontactに変えるだけ
static_pages_controller_test.rbtest "should get contact" do get static_pages_contact_url assert_response :success assert_select "title", "contact | #{@base_title}" end3.routesを設定する
routes.rbget 'static_pages/contact'4.コントローラーにパスを通す。
static_pages_controller.rbdef contact end【演習】
1.リスト 3.41にrootルーティングを追加したことで、root_urlというRailsヘルパーが使えるようになりました (以前、static_pages_home_urlが使えるようになったときと同じです)。リスト 3.42のFILL_INと記された部分を置き換えて、rootルーティングのテストを書いてみてください。rootはどこのディレクトリにも属していないのでstatc_pagesは不要
static_pages_controller_test.rbtest "should get root" do get root_url assert_response :success end3.5 最後に
3.6 高度なセットアップ