20210613のRubyに関する記事は20件です。

Marqeta使ってみた(その1)

先日IPOしたばかりのMarqetaプラットフォームを使ってみました。MarqetaはSandboxが提供されているので気軽に遊んでみることができそうです。 Sandboxの使い方はこちらから: https://www.marqeta.com/docs/developer-guides/core-api-quick-start まずはアカウント作成 メールアドレス含む必要な情報を記入して進みます。 メール受信しアドレスが確認されます。その後、SNSでも確認されます。 ダッシュボードへアクセス しばらく経つとサンドボックス作成のメールが来るので、ダッシュボードへアクセスします。 SDK 現在PythonとRubyのSDKが用意されてるようです。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Rails初学者によるRailsチュートリアル学習記録⑭ 第12章

目次 1. はじめに 2. 第12章の概要 3. 学習内容 4. 終わりに 1. はじめに この記事は、Rails初学者の工業大学三年生がRailsチュートリアルの学習記録をつけるための記事です。 筆者自体がRailsやWebについて知識が少ないので、内容の解釈などに間違いがある可能性があります。(その時はコメントで指摘してくださると助かります!) Railsチュートリアル内ではRailsの内容以外にも、gitでのバージョン管理やHerokuを使ったデプロイも学習しますが、gitに関しては既に私が学習済みのため学習記録には記述しません。 演習の記録も省略します。 2. 第12章の概要 この章では、ユーザーがパスワードを忘れてしまった時の、パスワードの再設定機能を実装していきます。 パスワードの再設定機能に使用する処理は、11章のアカウントの有効化で使用した処理と似ている個所が多いです。 この機能を使用する流れとしては、ログインフォームの「forgot password」というリンクをクリックしたら、 メールアドレスを入力するフォームに遷移し、メールアドレスを送信するとパスワードの再設定用のメールが届きます。 そのメール内にあるリンクをクリックすると新しいパスワードを入力するフォームに遷移し、 新しいパスワードを送信することでパスワードを更新できます。 パスワードの再設定機能実装の準備 PasswordResetsリソースの追加 Userモデルの変更 パスワードを再設定するためのアクション createアクションでメールを送信する editアクションでパスワードを再設定する updateアクションでパスワードを更新する 3. 学習内容 1. パスワードを再設定機能の実装準備 1-1. PasswordResetsリソースの追加 アカウントの有効化の時と同じように、パスワードを再設定するという処理を、 リソースとして扱えるようにするために、PasswordResetsリソースの作成からはじめます。 アカウントの有効化の機能では、メール内のリンクをクリックしたタイミングで、 データベース内の有効化ステータスを変更したかったので、editアクションのみを使用しましたが、 今回はフォームを生成する必要があるのでnewアクションも使用します。 以下のコマンドを利用してPasswordResetsコントローラを生成します。 rails generate controller PasswordResets new edit 生成されたアクションへのルーティングを追加します。 newアクションとeditアクションで生成されたビューから値を受け取り、 メールの送信やパスワードの再設定を行うcreateアクションとupdateアクションのルーティングも用意する必要があります。 そのために、以下のコードをroutes/rbの最後の行に追加します。 'resources :password_resets, only: [:new, :create, :edit, :update]' これでPasswordResetsリソースのルーティングの追加ができました。 ついでにこのタイミングで、forgot passwordのリンクをログインフォームに追加して、 パスワード再設定画面へ遷移できるようにします。 パスワード再設定画面へのリンクを追加したログインフォーム <% provide(:title, "Log in") %> <h1>Log in</h1> <div class="row"> <div class="col-md-6 col-md-offset-3"> <%= form_with(url: login_path, scope: :session, local: true) do |f| %> <%= f.label :email %> <%= f.email_field :email, class: 'form-control' %> <%= f.label :password %> <%= link_to "(forgot password)", new_password_reset_path %> <%= f.password_field :password, class: 'form-control' %> <%= f.label :remember_me, class: "checkbox inline" do %> <%= f.check_box :remember_me %> <span>Remember me on this computer</span> <% end %> <%= f.submit "Log in", class: "btn btn-primary" %> <% end %> <p>New user? <%= link_to "Sign up now!", signup_path %></p> </div> </div> この時点で、ログインフォームは以下の画像のようになります。(画像はRailsチュートリアル内から引用) 1-2. Userモデルの変更 アカウントの有効化の機能の実装時に、 ・activation_digest ・activated ・activated_at の3つの属性をUserモデルに追加した時のように、ここでは以下の2つの属性を追加します。 ・reset_digest ・reset_sent_at 前回追加した有効化した日時を格納するactivated_atは有効化機能で使用しませんでしたが、 今回追加する、パスワード再設定用のメールを送った日時を格納するreset_sent_atは、 再設定用のメールに有効期限を持たせるために使用します。 以下のコマンドで属性の追加を行います。 rails generate migration add_reset_to_users reset_digest:string reset_sent_at:datetime このコマンドを実行することでUserモデルは以下の表のようになります。 属性名 型名 id integer name string email string created_at datetime updated_at datetime password_digest string remember_digest string admin boolean activation_digest string activated boolean activated_at datetime reset_digest string reset_sent_at datetime PasswordResetsコントローラを生成したときにforgot passwordリンクを追加した時のように、 ここではパスワード再設定用のフォームを作成しておきます。 このフォームはメールアドレスの入力フィールドのみのフォームで、 ここにメールアドレスを入力して送信すると、パスワード再設定用のメールが届きます。 パスワード再設定用のフォーム <% provide(:title, "Forgot password") %> <h1>Forgot password</h1> <div class="row"> <div class="col-md-6 col-md-offset-3"> <%= form_with(url: password_resets_path, scope: :password_reset, local: true) do |f| %> <%= f.label :email %> <%= f.email_field :email, class: 'form-control' %> <%= f.submit "Submit", class: "btn btn-primary" %> <% end %> </div> </div> このフォームは以下の画像のようになります。(画像はRailsチュートリアル内から引用) ここまでで、パスワード再設定機能の実装をする準備ができました。 2.パスワードを再設定するためのアクション 2-1. createアクションでメールを送信する createアクションでは、先ほど実装したフォームに入力されたメールアドレスからユーザーを探し、 生成したパスワード再設定トークンをハッシュ化した再設定ダイジェストと、その時のタイムスタンプで データベースの属性を更新します。 それと同時にトークンとメールアドレスが入ったリンクが含まれたメールを送信します。 以下のコードがcreateアクションでのコードです。 app/controllers/password_resets_controller.rb def create @user = User.find_by(email: params[:password_reset][:email].downcase) if @user @user.create_reset_digest #再設定トークンを生成する @user.send_password_reset_email #再設定用メールを送信する flash[:info] = "Email sent with password reset instructions" redirect_to root_url else flash.now[:danger] = "Email address not found" render 'new' end end コメントを入れた2行でそれぞれトークンの生成とメールの送信を行っています。 これらのメソッドはUserモデルに追加します。 app/models/user.rb class User < ApplicationRecord attr_accessor :remember_token, :activation_token, :reset_token before_save :downcase_email before_create :create_activation_digest # パスワード再設定の属性を設定する def create_reset_digest self.reset_token = User.new_token #トークンの生成 update_attribute(:reset_digest, User.digest(reset_token)) #トークンをハッシュ化してreset_digestに格納 update_attribute(:reset_sent_at, Time.zone.now) #reset_sent_atにタイムスタンプを格納 end # パスワード再設定のメールを送信する def send_password_reset_email UserMailer.password_reset(self).deliver_now #メールを送信する end これでパスワードの再設定用のメールを送信する機能が実装できました。 ここからはメイラーの設定を行っていきます。 ただ、設定内容はアカウントの有効化の時と同じで、違う部分としてはメールの中に入れる リンクとメールの文章くらいです。 app/mailers/user_mailer.rb class UserMailer < ApplicationMailer def account_activation(user) #有効化用のメールのメソッド @user = user mail to: user.email, subject: "Account activation" end def password_reset(user) #パスワード再設定用のメールのメソッド @user = user mail to: user.email, subject: "Password reset" #送信先をuserのメールアドレスに、件名をPassword resetに設定 end end app/views/user_mailer/password_reset.html.erb <h1>Password reset</h1> <p>To reset your password click the link below:</p> <%= link_to "Reset password", edit_password_reset_url(@user.reset_token, email: @user.email) %> <p>This link will expire in two hours.</p> <p> If you did not request your password to be reset, please ignore this email and your password will stay as it is. </p> これにより、 https://example.com/password_resets/<再設定トークン>/edit?<メールアドレス> というリンクが含まれたメールが送信できます。 2-2. editアクションでパスワードを再設定する これでメールを送信する準備が整いました。 ここからはリンクをクリックされた後のeditアクションの動作を定義していきます。 まず、メール内のリンクをクリックしたときに遷移するフォームが必要です。 このフォームではパスワードの入力フィールドを2つ置き、1つは確認用として使用します。 この後、そこに入力されたパスワードでデータベースの属性を更新したいのですが、 ここで1つ、このフォーム特有の処理を加える必要があります。 それはリンクから受け取ったメールアドレスを、隠しフィールドとしてページ内に保存しておく処理です。 なぜこの処理が必要なのかというと、updateアクションでメールアドレスを基にユーザーを検索し、 そのユーザーのパスワードを更新したいのですが、 editアクションでリンクからメールアドレスを取得しても、何もしないとフォーム送信時にその情報が消えてしまうからです。 よって、隠しフィールドとしてメールアドレスを保存することで、、フォームの送信時に新しいパスワードと一緒に メールアドレスが送信されるようにします。 パスワード再設定のフォーム <% provide(:title, 'Reset password') %> <h1>Reset password</h1> <div class="row"> <div class="col-md-6 col-md-offset-3"> <%= form_with(model: @user, url: password_reset_path(params[:id]), local: true) do |f| %> <%= render 'shared/error_messages' %> <%= hidden_field_tag :email, @user.email %> <%= f.label :password %> <%= f.password_field :password, class: 'form-control' %> <%= f.label :password_confirmation, "Confirmation" %> <%= f.password_field :password_confirmation, class: 'form-control' %> <%= f.submit "Update password", class: "btn btn-primary" %> <% end %> </div> </div> <%= hidden_field_tag :email, @user.email %>この部分でユーザーのメールアドレスを 隠しフィールドで保存しています。 ここからeditアクションにバリデーションを加えます。 パスワードを再設定しようとしているユーザーが有効化されているか、 リンク内の有効化トークンは最初にデータベースに保存した記憶ダイジェストと一致するかを検証します。 app/controllers/password_resets_controller.rb class PasswordResetsController < ApplicationController before_action :get_user, only: [:edit, :update] before_action :valid_user, only: [:edit, :update] def edit end private def get_user @user = User.find_by(email: params[:email]) end # 正しいユーザーかどうか確認する def valid_user unless (@user && @user.activated? && @user.authenticated?(:reset, params[:id])) redirect_to root_url end end end 2-3. updateアクションでパスワードを更新する ここまでで、パスワード再設定のフォームへの遷移、メールの送信、新しいパスワードの送信までが実装できました。 ここからは、送信された新しいパスワードを基にデータベースの値を更新します。 ただ、新しいパスワードが送られたらどのような場合でも更新できてしまっては危険です。 具体的には次の3つの条件を設けます。 1. パスワード再設定の有効期限が切れていないか 2. 無効なパスワードは受け付けず、エラー文を表示する 3. 新しいパスワードが空文字列ではないか(ユーザー情報の編集で空入力を許可していた) これらの条件を満たした時にパスワードの更新が行われるようにします。 2はrenderメソッドでフォームを再表示する。3はempty?メソッドとrenderメソッドで空文字だった時に フォームが送信されないようにすることでそれぞれ実装できます。 1の有効期限の判断は、password_reset_expired?とcheck_expirationというメソッドを定義することで 実装していきます。 1つめのpassword_reset_expired?メソッドが有効期限内の時にfalse、有効期限を過ぎたときにtrueを返すメソッドで、 Userモデルに定義します。 2つめのcheck_expirationは上記のpassword_reset_expired?メソッドを呼び出し、 有効期限が切れていた時にエラー文を表示させて、 パスワード再設定用のメールアドレスを入力するフォームにリダイレクトします。 app/models/user.rb def check_expiration if @user.password_reset_expired? flash[:danger] = "Password reset has expired." redirect_to new_password_reset_url end end app/controllers/password_resets_controller.rb def check_expiration if @user.password_reset_expired? flash[:danger] = "Password reset has expired." redirect_to new_password_reset_url end end そして、上記のメソッドを使用して3つの条件を設けたupdateアクションが以下のコードです。 updateアクション class PasswordResetsController < ApplicationController before_action :get_user, only: [:edit, :update] before_action :valid_user, only: [:edit, :update] before_action :check_expiration, only: [:edit, :update] # 有効期限が切れてないかを最初に判断する def update if params[:user][:password].empty? # 空文字かどうかを判断する @user.errors.add(:password, :blank) render 'edit' elsif @user.update(user_params) # パスワードを更新する log_in @user flash[:success] = "Password has been reset." redirect_to @user else render 'edit' # パスワードが無効の場合フォームを再表示する end end end 以上で、この章で実装したかったパスワードの再設定機能が実装できました。 4. 終わりに この章は11章で扱った内容と似た部分が多かったので、 内容を進めるのも記事を書くのもあまり時間をかけずに進められました。 今まで実装したものはHerokuでデプロイしてるので、自分が開発したアプリで実際にユーザー登録できて感動です。 まだユーザー登録の機能しかないですが、残り2章でマイクロポストの投稿機能とユーザーのフォロー機能を 実装していきます。 どちらも内容がかなり濃いので時間がかかりそうですが頑張ります。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【第3章】Railsチュートリアルで急にファイルの保存ができなくなった時にやったこと

Railsチュートリアル第3章(第6版)で、急にファイルが保存できなくなった。 やったこと① ファイル保存時に表示されるメッセージを読んだ ファイルを保存しようとすると、メッセージが表示されて保存が出来ない。 メッセージを読むもよく分からず、調べてみると以下のような記事があった。 『ENOSPCってなんやねん!!』 @kaitaku どうやらENOSPCはディスクに十分な容量がないことを意味するらしい。 上記の記事の参考元はこちら↓ https://github.com/facebook/create-react-app/issues/4301 やったこと② チュートリアルを遡り容量の上げ方を確認した そういえば、どこかで容量について触れられていたような・・・。と思い探してみると普通に書いてあった。 これをやっておけば良かったのか。。。 ということでRailsチュートリアルのヘルプページを確認する。 やったこと③ Railsチュートリアルのヘルプページに従って、hello_appとtoy_appを削除した 後はヘルプページに従うのみ。 今後のチュートリアルでは第3章で作成したsample_appだけを使うようなので、まずは以前の章で作成したhello_appとtoy_appを思い切って削除する。ソースコードはGitHubにpushしているので安心。 再度ファイルを保存してみると、無事メッセージが表示されずに保存することができた。 手順にはEBSのボリュームを増やす方法も書いてあるので、やっておいた方が良いと思われる。 まとめ やったこと①②③の流れで解決できた。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

paramsメソッドについて

挨拶 こんにちは、プレイライフの熊﨑です! 来月友人の結婚式があるということで、自分の婚期について若干の不安を抱えています。 結婚はいつになるのやら、、、、 そんなことは置いといて、今日もアウトプットを行っていこうと思います! 本日はparamsメソッドについてです。 対象読者 paramsメソッドの使用経験はあるが、なんとなく使っている方 paramsメソッドについて paramsとはリクエストで送られてきた値を受け取るためのメソッドです。 送られるデータの種類 送られてくる情報には、「投稿フォームなどPOSTで送信されたデータ」と「検索フォームなどGETで送信されURLにクエリとして入るデータ」があります。 これらのデータを取得するのが、paramsメソッドの役目です。 使い方 以下のように書くことでカラム名の値を取得することができます。 params[:カラム名] どのように使うのか? URLから送られてきた情報をコントローラーで使用したいとき 具体例 ユーザーから以下のようなリクエストが飛んできている場合 https://hogehoge.com/users/12 controller.rb def show @user = User.find(params[:id]) end # params[:id]で12を返す 投稿された情報をコントローラーで使用したいとき 具体例 controller.rb def create user = User.new(permit_params) user.save end def permit_params params.permit(:name) end permitメソッドを使用しているのはストロングパラメータにするためです。 カラムを取得しないでparamsメソッドを実行すると、フォームに入力した情報以外も取得できてしまいます。 そのため、User.new(params)のようにすると、悪意を持ったユーザーがフォームに入力されている以外の不正な値を投稿した際に、DBの値が更新されてしまう可能性が出てきます。(Rails4からは、permitメソッドで許可されていないパラメータはDBに保存できないようになっています。) このような場合に備えて、ストロングパラメータにすることで、フォームに入力した情報以外を更新できないようにする必要があります。 まとめ paramsメソッドは投稿フォームやURLから送られてきたデータを取得するメソッド paramsで受け取った値を用いてDBを更新する場合には、strongパラメータにする必要がある。 参考記事 https://railsguides.jp/action_controller_overview.html https://pikawaka.com/rails/params
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Ruby基礎まとめ① (変数、条件分岐、繰り返し、ハッシュ、メソッド)

はじめに Progateで学習したRubyの内容を自分なりにまとめておく。 Hello World 基本的にputsを用いて処理結果を表示していく puts "Hello Ruby" 文字列と数値 数字を取り扱う場合は以下のような違いがある puts 3 + 5 # 8 puts "3 + 5" # 3 + 5 # 文字列の連結 puts "私は" + "Diggy-MO'です." # 私はDiggy-MO'です. 変数 変数の宣言 変数の宣言、変更などのルールは大体他言語と同じ text = "Piscineはつら楽しい" # 変数の宣言 puts "42tokyoの" + text length = 8 width = 9 puts length * width puts "--------------" length += 5 # 変数の変更 puts length * width 変数を文字列に含める場合 "文字列 #{変数名} 文字列" ""(ダブルクォーテーション)で囲む必要あり ''(シングルクォーテーション)だと、#{変数名}という文字列として扱われてしまう 数値と文字列の単純な連結 puts age + "歳です" はできない length = 9 width = 8 area = length * width puts "面積は#{area}です" 単語の命名規則 snake_case: 単語の間をアンダーバーでつなぐ命名規則 配列 # 変数名 = [値1, 値2, 値3, ...] languages = ["日本語", "英語", "スペイン語"] puts languages[1] puts "#{languages[0]}を話せます" 条件分岐 if, else # 書式 if 条件1 条件1が成立する(true)時の処理 elsif 条件2 条件2が成立する時の処理 else どの条件も成立しない時の処理 end A以上(>= A) Aではない(!= A) AかつB(A && B) などの条件の書き方も他言語と同様 number = 48 if number % 3 == 0 && number % 5 == 0 puts "FizzBuzz" elsif number % 5 == 0 puts "Buzz" elsif number % 3 == 0 puts "Fizz" else puts number end 繰り返し処理 each # 書式 配列.each do |変数名| 処理 end 変数のスコープ 繰り返し処理(each)の中で使った変数は、eachの中でしか使えない。 languages = ["日本語", "英語", "スペイン語"] border = "---------------------" # 変数のスコープ languages.each do |language| # languageはeachの中でしか使えない puts border puts "#{language}を話せます" end # puts language <- エラー ハッシュ それぞれの値にキーを設定して管理する。 # 書式 {"キー1" => 値1, "キー2" => 値2, ...} 通常のハッシュ キーの値の変更や追加などもできる exam = {"subject" => "Math", "score" => 80} puts exam["subject"] # キーの値を出力 exam["subject"] = "Science" # キーの値を変更 puts exam["subject"] exam["grade"] = "good" # 新しいキーと値の追加 puts exam["grade"] シンボル 文字を""や''の代わりに先頭に:をつけた書き方 # {:キー1 => 値1, :キー2 => 値2, ...} # {キー1: 値1, キー2: 値2, ...} (省略形) # 変数名[:キー] で呼び出し(省略形でも呼び出し方は同じ) exam = {:subject => "Math", :score => 80} exam = {subject: "Math", score: 80} # この2つ同じ puts "#{exam[:subject]}: #{exam[:score]}点" nil nil は何かが存在しないことを表すために用いられるオブジェクト nilに関しては、コメントで紹介して頂いた以下の記事から引用させて頂いた。 exam = {subject: "Math"} if exam[:score] puts "#{exam[:subject]}の結果は#{exam[:score]}点です" else # 存在しないキーを指定すると、nil(false)となる puts "#{exam[:subject]}の結果は分かりません" end 要素がハッシュである配列 # 変数名 = [ # {キー1: 値1, キー2: 値2}, # {キー1: 値1, キー2: 値2}, # ] characters = [ {name: "にんじゃわんこ", age: 14}, {name: "ひつじ仙人"}, {name: "ベイビーわんこ", age: 5}, {name: "とりずきん"} ] characters.each do |character| puts "--------------------" puts "名前は#{character[:name]}です" if character[:age] puts "年齢は#{character[:age]}歳です" else puts "年齢は秘密です" end end メソッド # 書式 ド名(引数) 処理 return 戻り値 end メソッド名(引数) # メソッドの呼び出し 通常のメソッド def price_with_shipping(price) if price >= 5000 return price end return price + 500 end puts "商品の合計金額は3000円です" puts "お支払い金額は、送料込みで#{price_with_shipping(3000)}円です" puts "-----------" puts "商品の合計金額は10000円です" puts "お支払い金額は、送料込みで#{price_with_shipping(10000)}円です" キーワード引数 # def メソッド名(引数1:, 引数2:, 引数3:, ...) # 処理 # return 戻り値 # end # メソッド名(引数1: 値1, 引数2: 値2, 引数3: 値3, ...) def buy(item:, price:, count:) puts "#{item}を#{count}台のお買い上げです" puts "合計金額は#{price * count}円です" end buy(item:"テレビ", price:15000, count:2) おわりに 次回はクラスとインスタンスについてまとめようと思う。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Rails】DBから範囲式や期間で絞り込みする方法

はじめに Railsを使用して開発している中でDBから必要な情報を取得する際に、どのように取得するのがベストかを自分用にまとめました。 経緯 以下のような、条件の絞り込みをしたい場合 ・Aカラムの3ヶ月以内のすべてのレコードを取得したい ・Bカラムの20以下のレコードをすべて取得したい ・Cカラムの10未満のレコードをすべて取得したい ・Dカラムの10以上のレコードをすべて取得したい ・Eカラムの10~20の間のレコードをすべて取得したい ・Fカラムの10以上~20未満のレコードをすべて取得したい 方法 ・updated_atが3ヶ月以内のすべてのレコードを取得したい example.rb User.where("updated_at >= ?", 3.months.ago) ・ageの20以下のレコードをすべて取得したい example.rb User.where(age: ..20) ・ageの10未満のレコードをすべて取得したい example.rb User.where(age: ...10) ・ageの10以上のレコードをすべて取得したい example.rb User.where(age: 10..) ・ageの10~20の間のレコードをすべて取得したい example.rb User.where(age: 10..20) ・ageの10以上~20未満のレコードをすべて取得したい example.rb User.where(age: 10...20) 補足 上記は範囲オブジェクトを使った書き方になります。 Ruby2.6以降から範囲オブジェクトの絞り込みができます。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

rubyを使ってSSH越しにDBへアクセスしたい

概要 rubyで動的に生成したクエリをDBに対してパラメータを少しずつ変えて繰り返し実行したいけど、対象のDBはsshしないとアクセスできないんだよな〜って場合の解決方法です。(もっと良い方法あったらコメントでこっそり教えてください。) まずはローカルで まず、以下のような例でローカルのDBに対してクエリを繰り返し実行するrubyのプログラムを書いてみます。 ストーリー 発行されるクエリはバッチの対象者抽出クエリ 条件の日付を1日づつ変更して各日付でどれだけ抽出されるのか調べたい test.rb require 'mysql2' require 'date' start_date = Date.new(2021, 6, 1) end_date = Date.new(2021, 6, 5) current_date = start_date db = Mysql2::Client.new(host: "127.0.0.1", username: "hoge", password: '', :encoding => 'utf8', database: 'test') query = <<~EOS SELECT count(id) FROM users where updated_at = ? EOS while current_date < end_date do request = db.prepare(query) result = request.execute(current_date) result.each { |c| puts "#{current_date}\n#{c["count(id)"]}アカウント" } end 上記のものを実行すると以下のような感じで結果が出てきます。 sh $ ruby test.rb 2021-06-01 0 アカウント 2021-06-02 1 アカウント 2021-06-03 0 アカウント 2021-06-04 0 アカウント ssh越しのDBに対して実行できるように変更していく ssh越しのDBに対して実行できるように変えたものが以下です。 test2.rb require 'mysql2' require 'date' require 'net/ssh/gateway' gateway = Net::SSH::Gateway.new( 'host', # SSHするホスト 'user', # SSHするユーザー port: 22, keys: ['~/.ssh/id_rsa'] ) start_date = Date.new(2021, 6, 1) end_date = Date.new(2021, 6, 5) current_date = start_date gateway.open('DBがあるサーバーのホスト', 3306) do | port | db = Mysql2::Client.new(host: "127.0.0.1", port: port, username: "hoge", password: '', :encoding => 'utf8', database: 'test') query = <<~EOS SELECT count(id) FROM users where updated_at = ? EOS while current_date < end_date do request = db.prepare(query) result = request.execute(current_date) result.each { |c| puts "#{current_date}\n#{c["count(id)"]}アカウント" } end end 最後に 例だと5日分ですが、1年分をやろうとすると、とても手作業でやる気にはならないのでこういった自動化が有用に思えます。 SSHしなくてもDBダンプしてきてやればいいじゃんと思う方がいらっしゃるかもしれませんが、さっとダンプできるならその方がいいと自分も思います。 でも、バッチなどの抽出条件が複雑で複数テーブルをダンプしてこないといけなく、レコード数も膨大となるとダンプしてくるのも時間がかかります。 そういった場合に自分はこういった方法でやっています。 最後まで読んでいただきありがとうございました。 参考 class::Net::SSH::Gateway RubyでSSHトンネル経由でサーバにアクセスする
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

初投稿テスト

uniq.rb p [1, 1, 2, 3, 3].uniq
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

[Rails] テストコードとは

はじめに 私はテストコードを書くのが苦手です。特にこれを読めば、「そんなあなたでも大丈夫!テストコードを楽にかける方法が。。。」みたいな記事でもありません。 書くのが苦手な私に、こんなに重要で必要なものだから、書かないといけないんだよ。と再認識させるため、そもそもテストコードとはということをまとめてみました。よろしくお願いします。 テストコード テストコードとはアプリケーション内に記述するコードで、実装した機能が正しく機能するか自動で確かめてくれるコードです。 例えば、「名前の記入欄が空欄だとエラーがでる」や「メールアドレスが空欄だとエラーが出る」など、考えられる挙動を全て書き出し、そのテストコードを記述していきます。 記述するのは大変ですが、一度記述してしまえば、コマンド一つでそれらの挙動を自動で確かめてくれるのです。 RSpec(アールスペック) RSpecはRailsアプリケーションのテストコードを書くために用いられるGemです。 Railsには標準でmini_testというテスト用のGemが導入されていますが、RSpecを使うのが主流だそうです。 なぜテストコードを書くのか 私はいつもブラウザで挙動がうまくいっているのかポチポチして確かめていますが、テストコードは書く必要はあります。 もしブラウザポチポチだけで確認を終えてしまうと、どのようなテストを行ったのか、記録が残りません。 また、ブラウザでポチポチしているのは人間なので、人為的ミスが起こったり、抜けがある可能性が高いです。 加えて、仕様に変更があったときは、もう一度全部確認し直さなければなりません。その変更で他の機能にも影響が及んでいる可能性もありますし。。。 しかしテストコードを書いているとそのようなことは起こらないため、アプリケーションのクオリティが担保がされるものと言えます。 テストコードはアプリケーションの挙動を漏れなく確認したり、変更があったときに迅速に対応できたりと、アプリケーションのクオリティが担保できる重要なものなんですね。 テストコードには書くべきパターンというのが二つあります。それが正常系と異常系です。 正常系 このテストは、ユーザーが開発者の意図する操作を行った時の挙動を確認するテストコードです。 例えば「正しく全ての項目が入力されていればログインできる」というのは、開発者が意図した操作で、正常系です。 異常系 こっちが私は記述量が多くて大変だと感じます。 異常系は正常系の逆で、開発者が意図しない操作をユーザーが行った時の挙動を確認するテストコードです。 例えば「パスワードが空欄だった場合、ログインできない」みたいなものです。 続いてテストの種類についてです。 単体テストコード これはモデルやコントローラーなどの機能ごとに問題がないか確かめるテストコードです。 バリデーションの挙動を確認したりします。先ほどの「パスワードを空欄だった場合、ログインできない」というのはバリデーションがしっかり機能しているか確認している単体テストコードと言えますね。 結合テストコード これはユーザーがブラウザで操作する一連の流れを再現して、問題ないか確かめます。 例えば、「投稿ボタンを押すと投稿完了ページに移動し、TOPページに戻ると先ほど投稿した内容が表示されている」といった一連の流れを一気に確かめます。これはコマンドを押してテストを実行すると、自動でブラウザが開き、アプリケーションが動き出すので、うおおおおおってなります。笑 RSpecの導入と設定 最後にRSpecの導入方法と設定を残しておきます。よく忘れるので。。。 まずはGemfileにGemを追加します。gem 'rspec-rails', '~> 4.0.0'を記述してください group :development, :test doの中に記述すること気をつけてください。(Gemの動作に制限を持たせるため。) Gemfile group :development, :test do # Call 'byebug' anywhere in the code to stop execution and get a debugger console gem 'byebug', platforms: [:mri, :mingw, :x64_mingw] gem 'rspec-rails', '~> 4.0.0' end 記述できたら、ターミナルで導入したいアプリケーションのディレクトリにいることを確認して ターミナル % bundle install 続いてターミナルで下記のコマンドを実行。 ターミナル % rails g rspec:install 下記のように表示されたら成功 ターミナル create .rspec create spec create spec/spec_helper.rb create spec/rails_helper.rb 続いて、生成された.rspecファイルを開いて下記のように記述します。(2行目を追加) .rspec --require spec_helper --format documentation これで設定完了です。 おまけで、もし、例えばUserモデルのテストコードが書きたければ、ターミナルで下記のコマンドを実行して作成します。 ターミナル % rails g rspec:model user 最後に オリジナルアプリのテストコードが全くかけておらずこれから取り掛かるのがちょっといやです。 ただテストコードは記述中にバグを見つけられたり、一発でクリアしたりすると気持ちいいので、個人的には取り掛かると結構ハマったりします。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Ruby】アクセサメソッドについて学習してみた

はじめに プログラミング初心者です。 知識があやふやだったアクセサメソッドについて学習しましたので、備忘録として投稿します。 間違い等ございましたら、ご指摘お願いします。 用語の定義 アクセサメソッド ゲッターメソッドやセッターメソッドなどインスタンス変数の読み取りや書き込みができるメソッドの総称 ゲッターメソッド インスタンス変数の読み取り専用のインスタンスメソッドのこと セッターメソッド インスタンス変数の書き込み専用のインスタンスメソッドのこと ※メソッド名の末尾に=(イコールをつけると)、代入式のようにメソッドを呼び出すことが出来る class Car def initialize puts "車の色を入力してください" @color = gets.chomp end # ゲッター(読み取り) def color @color end # セッター(書き込み) def color = (set) @color = set end end car = Car.new # ※initializeメソッドでredと入力したとする # ゲッターでインスタンスメソッドの値を確認 puts car.color # => red # セッターを使用し、インスタンスメソッドの値を書き換える car.color = "white" # 再びゲッターでインスタンスメソッドの値を確認 puts car.color # => white アクセサメソッドの必要性 クラスの外部からインスタンスの値を変更しようとすると、エラーが発生する →エラーが発生しないようにするためにはインスタンスメソッドを経由する必要がある →そこで使用するのがアクセサメソッド 簡単な記述方法 ゲッターとセッターには、簡単に記述する方法がある。 # ゲッター attr_reader :インスタンス変数名 # シンボル型 attr_reader "インスタンス変数名" # 文字列型 # セッター attr_writer :インスタンス変数名 # シンボル型 attr_writer "インスタンス変数名" # 文字列型 # ゲッター+セッター attr_accessor :インスタンス変数名 # シンボル型 attr_accessor "インスタンス変数名" # 文字列型 attr_readerは、ゲッターメソッドを定義してくれるメソッド attr_writerは、セッターメソッドを定義してくれるメソッド attr_accessorは、ゲッターメソッドとセッターメソッドの両方を定義してくれるメソッド まとめ あやふやだったアクセサメソッドについて、整理できたかなと思います。 まだまだ知識不足なところがありますので、理解を深め次第追記していきたいと思います!
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Ruby】アクセサメソッドを理解する

はじめに プログラミング初心者です。 知識があやふやだったアクセサメソッドについて学習しましたので、備忘録として投稿します。 間違い等ございましたら、ご指摘お願いします。 用語の定義 アクセサメソッド ゲッターメソッドやセッターメソッドなどインスタンス変数の読み取りや書き込みができるメソッドの総称 ゲッターメソッド インスタンス変数の読み取り専用のインスタンスメソッドのこと セッターメソッド インスタンス変数の書き込み専用のインスタンスメソッドのこと ※メソッド名の末尾に=(イコールをつけると)、代入式のようにメソッドを呼び出すことが出来る class Car def initialize puts "車の色を入力してください" @color = gets.chomp end # ゲッター(読み取り) def color @color end # セッター(書き込み) def color = (set) @color = set end end car = Car.new # ※initializeメソッドでredと入力したとする # ゲッターでインスタンスメソッドの値を確認 puts car.color # => red # セッターを使用し、インスタンスメソッドの値を書き換える car.color = "white" # 再びゲッターでインスタンスメソッドの値を確認 puts car.color # => white アクセサメソッドの必要性 クラスの外部からインスタンスの値を変更しようとすると、エラーが発生する →エラーが発生しないようにするためにはインスタンスメソッドを経由する必要がある →そこで使用するのがアクセサメソッド 簡単な記述方法 ゲッターとセッターには、簡単に記述する方法がある。 # ゲッター attr_reader :インスタンス変数名 # シンボル型 attr_reader "インスタンス変数名" # 文字列型 # セッター attr_writer :インスタンス変数名 # シンボル型 attr_writer "インスタンス変数名" # 文字列型 # ゲッター+セッター attr_accessor :インスタンス変数名 # シンボル型 attr_accessor "インスタンス変数名" # 文字列型 attr_readerは、ゲッターメソッドを定義してくれるメソッド attr_writerは、セッターメソッドを定義してくれるメソッド attr_accessorは、ゲッターメソッドとセッターメソッドの両方を定義してくれるメソッド まとめ あやふやだったアクセサメソッドについて、整理できたかなと思います。 実装経験が少ないため、attr_accessorの出番は少ないですが、これから有益な情報を入手しましたら発信して行きたいと考えております!
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Rails】世界一丁寧なDeviseの導入手順

0. はじめに はじめに Deviseを導入するとき毎回手順を忘れてしまいませんか? 僕自身毎回DeviseのREADMEを見たり、Qiitaの記事を見たりして進めていたのですが、これを機にまとめようと思ったので記しておきます。 一度この記事を一通り読んでから手を動かすことをおすすめします。 環境 Ruby: 2.6.6 Rails: 6.0.0 1. 導入 Gemfile gem 'devise' bundle installでhttps://rubygems.orgからGemをインストール 2. Deviseのインストール terminal $ rails g devise:install これを走らせることでdeviseのconfigファイルをインストールして導入していきます。 2.5 ルートビューの作成 ルートパスのビューを作成します。すでにルートパスのビューを作成している方は3. モデルのインストールに進んでください。 terminal $ rails g controllers Pages index routes.rbを以下のように書き換え config/routes.rb Rails.application.routes.draw do root to: 'pages#index' end 3. モデルのインストール terminal $ rails g devise {モデル名} これを走らせることでモデル、マイグレーションファイル、テストファイルのインストールができる。 4. マイグレーションファイルの編集 db/migrate/××××××××××××××_devise_create_◯◯.rb # frozen_string_literal: true class DeviseCreateUsers < ActiveRecord::Migration[6.0] def change create_table :users do |t| ## Database authenticatable t.string :name, null: false t.string :email, null: false, default: "" t.string :encrypted_password, null: false, default: "" ## 省略 end end end 上記で行ったモデルのインストールでマイグレーションファイルが作成されます。emailとpassword以外に必要なカラムがあれば追加。ここではnameカラムを追加しています。 すでに他のテーブルを作成していればrails db:migrate、していなければrails db:createをしてからrails db:migrateをターミナルで実行してください。 5. ストロングパラメータの設定 4. マイグレーションファイルの編集でマイグレーションファイルにカラムを追加した場合、以下の設定が必要になります app/controllers/application_controller.rb class ApplicationController < ActionController::Base before_action :configure_permitted_parameters, if: :devise_controller? protected def configure_permitted_parameters devise_parameter_sanitizer.permit(:sign_up, keys: [:name]) end end keys: [:◯◯]は4. マイグレーションファイルの編集で設定したカラム名です。今回の場合、nameカラムを追加で記述したので、keys: [:name]となります。 6. ビューのインストール terminal $ rails g devise views 先にモデルをインストールしてからでないと後々設定がめんどくさくなるので、先にモデルをインストールすることをおすすめします。勉強したての頃、ここで詰まったことがあります。 7. 最後に これでDeviseを導入する一連の流れは終了です。 8. まとめ 一連の作業をターミナルの出力結果とともに載せておきます。ご参考までに。 terminal $ rails g devise:install Running via Spring preloader in process 78732 create config/initializers/devise.rb create config/locales/devise.en.yml =============================================================================== Depending on your application's configuration some manual setup may be required: 1. Ensure you have defined default url options in your environments files. Here is an example of default_url_options appropriate for a development environment in config/environments/development.rb: config.action_mailer.default_url_options = { host: 'localhost', port: 3000 } In production, :host should be set to the actual host of your application. * Required for all applications. * 2. Ensure you have defined root_url to *something* in your config/routes.rb. For example: root to: "home#index" * Not required for API-only Applications * 3. Ensure you have flash messages in app/views/layouts/application.html.erb. For example: <p class="notice"><%= notice %></p> <p class="alert"><%= alert %></p> * Not required for API-only Applications * 4. You can copy Devise views (for customization) to your app by running: rails g devise:views * Not required * =============================================================================== $ rails g controller Pages index Running via Spring preloader in process 78991 create app/controllers/pages_controller.rb route get 'pages/index' invoke erb create app/views/pages create app/views/pages/index.html.erb invoke test_unit create test/controllers/pages_controller_test.rb invoke helper create app/helpers/pages_helper.rb invoke test_unit invoke assets invoke scss create app/assets/stylesheets/pages.scss $ rails g devise User Running via Spring preloader in process 78899 invoke active_record create db/migrate/20210610081935_devise_create_users.rb create app/models/user.rb invoke test_unit create test/models/user_test.rb create test/fixtures/users.yml insert app/models/user.rb route devise_for :users $ rails g devise:views Running via Spring preloader in process 80035 invoke Devise::Generators::SharedViewsGenerator create app/views/devise/shared create app/views/devise/shared/_error_messages.html.erb create app/views/devise/shared/_links.html.erb invoke form_for create app/views/devise/confirmations create app/views/devise/confirmations/new.html.erb create app/views/devise/passwords create app/views/devise/passwords/edit.html.erb create app/views/devise/passwords/new.html.erb create app/views/devise/registrations create app/views/devise/registrations/edit.html.erb create app/views/devise/registrations/new.html.erb create app/views/devise/sessions create app/views/devise/sessions/new.html.erb create app/views/devise/unlocks create app/views/devise/unlocks/new.html.erb invoke erb create app/views/devise/mailer create app/views/devise/mailer/confirmation_instructions.html.erb create app/views/devise/mailer/email_changed.html.erb create app/views/devise/mailer/password_change.html.erb create app/views/devise/mailer/reset_password_instructions.html.erb create app/views/devise/mailer/unlock_instructions.html.erb $ rails db:create Created database '〇〇_development' Created database '〇〇_test' $ rails db:migrate == 20210610083101 DeviseCreateUsers: migrating ================================ -- create_table(:users) -> 0.0374s -- add_index(:users, :email, {:unique=>true}) -> 0.0408s -- add_index(:users, :reset_password_token, {:unique=>true}) -> 0.0357s == 20210610083101 DeviseCreateUsers: migrated (0.1141s) ======================= 参考記事
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Rails】Bootstrapを活用し、アイコンを押すと指定のリンクに飛ばす方法

はじめに 今回はBootstrapで使用できるアイコンを押すと、 指定のパス先へ飛ぶ方法について書かせていただきます。 BootstrapのアイコンURL:https://icons.getbootstrap.jp/ 下記イメージです! このようなヘッダーの人型のアイコンを押すと、ユーザー詳細ページに飛ぶような場合 ※今回はBootstrapの基本的な使い方等は割愛させていただきます。 開発環境 Bootstamp バージョン5 Ruby on Rails バージョン2.6.5 記述方法 通常Railsでパスを指定する際には下記のlink_toメソッドを使用します。 link_toメソッド <%= link_to '表示させる文字列', (指定のパス)_path, method: :メソッド, class: "" %> 最初、自分は”表示させる文字列”の部分にアイコンのHTMLを差し込めば表示させれるかなと思い、記述してみましたがうまくいきませんでした。 (式展開でHTMLを記述しましたが、コードがそのまま表示されてしまいました?) 解決策としてlink_toメソッドの記述の仕方を下記に変更することで問題が解決しました! link_toメソッド <%= link_to( 指定のぱす _path) do %> 表示させる文字 <% end %> 完成形 完成形 <%= link_to(user_path) do %> # アイコンの記述 <svg xmlns="http://www.w3.org/2000/svg" width="30" height="30"fill="currentColor" class="bi bi-person-circle mx-3 text-dark" viewBox="0 0 16 16"> <path d="M11 6a3 3 0 1 1-6 0 3 3 0 0 1 6 0z"/> <path fill-rule="evenodd" d="M0 8a8 8 0 1 1 16 0A8 8 0 0 1 0 8zm8-7a7 7 0 0 0-5.468 11.37C3.242 11.226 4.805 10 8 10s4.757 1.225 5.468 2.37A7 7 0 0 0 8 1z"/> </svg> <% end %> この書き方で先程のフッダー画像の人型のアイコンを押すとユーザー詳細ページへ飛ぶように設定できました! CSSでテキストのデコレーションを消さないと、アイコンが青色のリンク色になってしまうので気をつけてください!
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

'/tmp/mysql.sock' (2)エラー解決方法

環境 Rails6.1.3 Ruby3.0.1 MySQL8.0.23 エラー内容 時々、 ActiveRecord::ConnectionNotEstablished (Can't connect to local MySQL server through socket '/tmp/mysql.sock' (2)): というソケットに接続できないエラーが出ることがあります。 原因 原因の一つとして考えられるのが、Mysqlサーバーが起動していないことです。 MySQLサーバーの状態を確認してみます。 % mysql.server status Permission denied ERROR! MySQL is not running, but PID file exists PIDファイルはあるが、サーバーが動いていないと表示されました。 PIDとはプロセスIDのことで、プロセスを管理するための識別子のことです。実際にファイルの中身をみてみると整数が割り当てられていると思います。 PIDファイルもない場合は、ファイルを作成することになります。 解決方法 サーバーを動かすために以下のコマンドを入力します。 % sudo mysql.server start Starting MySQL SUCCESS! これでもうまくいかない時は、 % sudo mysql.server restart も試してみてください。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

gemパッケージのインストール先を表示させる

gem env gemdir でインストール先のパスが表示される。 $ gem env gemdir /Users/yusaku/.rbenv/versions/2.6.6/lib/ruby/gems/2.6.0 $ ls `gem env gemdir` build_info doc gems cache extensions specifications
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Redditの日本語版サイト(ようなもの)作ってみた

はじめに redditという海外の掲示板サイトの日本語版のようなものを作ってみました。 概要 5chのような掲示板サイトです。登録をすると自分の立てたスレの通知や一覧が見れたりします。 工夫した点 登録なしでもありでも使えるようにすること。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Rails 消費税計算

プログラミングの学習を始めて3ヶ月、 Ruby on Railsでの、消費税計算についてまとめます。 前提として、 商品(Product)とカート(Cart)の作成が終えていて、 Productにはsales_priseのカラムがあります。 モデルに記載 Productモデルに記載します。 Product.rb def add_tax_sales_price (self.sales_price * 1.10).round end Productのカラムである sales_price の前に 必ず add_tax_ を記載してください。 私はそれで rails s した時に永遠にループしてしまい serverが起動せず大変な目にあいました。 viewに記載 消費税を計算して反映させたい部分に <%= @product.add_tax_sales_price.to_s(:dalimited) %> Productモデルに * 1.10 (2021年6月現在)の税率のため、 変更があった場合はmodelを変更するだけでviewページは反映されます。 (:dalimited)は数値を3桁区切りにしてくれます。 例: 12,345,678 1,234円
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

newとbuildの違い

newとbuildってどう使い分けるの? buildは、buildはアソシエーションを関連づけさせているときに使用し 外部参照キーを自動でセットしてくれる 親要素への結びつけが必要な場合はそこを自動でやってくれる モデルを関連付けしたときにbuildを使う buildはnewのエイリアス(ショートカットキー) buildは新しい書き方で buildは親要素から子要素のデータをセットしてくれる便利なことをするやつ newは子要素を自分で記述する必要がある <例> ※@post = @user.posts.buildは、@post = Post.new(user_id: @user.id)と同じ。 ※user.rbに「has_many :posts」があると、「Userインスタンス.posts.build」というメソッドが使える」ようになる。 これは「Userインスタンスに紐付いたPostインスタンスを生成する」メソッド。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

アソシエーション部分で働いている色々なモデル内まとめ

belong_to この関連付けをされているクラスには外部キーがあること前提 外部キーが別クラスにある場合はhas_oneを使用する必要がある :optional belong_toで使えるオプションの一つ 公式 :optionalオプションをtrueに設定すると、 関連付けされたオブジェクトの存在性のバリデーションが実行されないようになる。 ☆値が空で来たときはエラーを返さずに、その空情報をなかったかのように振る舞わせることができる ☆optional: trueはpresence:trueと逆のことをしている ☆外部キーのnilを許容してくれる ☆アソシエーション組んである状態のため親要素がないとエラー!って出てしまうモデルのチェックを回避してくれる 今回は親の情報が入った時点で子要素側に親_idの情報が渡すことができるようになる そのため親が存在していないと子は保存できない状態にあるということ いつ親の要素が入るのか 親と子の要素が一緒に登録されるからことここの記述が必要になるという特殊な状態 一旦子要素が親要素がない状態でも作られるようにしていて 親要素ができたタイミングで子要素を紐付けをさせるようにしている reject_if: :all_blank accepts_nested_attributes_forをすると空の文字列が入っているデータを弾いてくれる allow_destroy: true モデル経由から別モデルを削除する時に必要なオプション 親要素側から削除する必要がある ※今回はネストさせて使用するデータベース = controllerがない = destroyアクションがないという状態 コントローラがない特殊なモデルaccepts_nested_attributes_forの関係の時どう削除するか 自分に紐づいているコントローラを持たないモデルのデータを消したいときに使う dependent: :destroy 親要素がいなくなってしまったときに子要素が浮いた状態にならないように削除される belongs_toとhas_oneのどちらを選ぶか 2つのモデルの間に1対1の関係を作りたいのであれば、いずれか一方のモデルにbelongs_toを追加し、もう一方のモデルにhas_oneを追加する必要があります。 外部キー(foreign key)をどちらに置くかできまる
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

草野球の出欠確認Webアプリを作ろう! part.12

これから作っていく簡単なWebアプリの作成メモ(自分の備忘)です。 自分用なのであまり凝りすぎないように書いていきたい。 <<前回の記事 今回やったこと 前回記事でbootstrapを導入した際に、既存のCSSが適用されなくなってしまい、一時気力を失ってしまった。 しかし、これまで作ったものをbootstrapのスタイルに置換することで、見た目はこれまでと違うが以降の作業を継続できるようにした。 (未考慮の部分は時間ややる気があるときに整えることにする、後回しともいう) 以下、今回主にクラスなどの部分を編集したスケジュール機能とユーザー機能の画面を示す。 スケジュール機能 一覧画面 app/views/schedules/index.html.erb <h1>チームの予定一覧</h1> <div class="mx-3 d-block"> <%= link_to '新規作成', new_schedule_path, class: 'btn btn-primary' %> </div> <% if @schedules.blank? %> <div class="container mx-auto"><%= "表示できる予定がありません。" %></div> <% else %> <div class="container mx-auto table-responsive"> <table id="schedules_table" class="table table-striped table-hover table-sm"> <thead> <tr> <th scope="col">件名</th> <th scope="col">予定日</th> <th scope="col">予定の時間</th> </tr> </thead> <tbody> <% @schedules.each do |lst| %> <tr class="clickable-row" data-href="<%= schedule_path lst.id %>"> <td><%= lst.title %></td> <td><%= lst.date_of %></td> <td><%= lst.start_time.strftime('%H:%M') %> ~ <%= lst.end_time.strftime('%H:%M') %></td> </tr> <% end %> </tbody> </table> </div> <% end %> 新規画面 app/views/schedules/new.html.erb <h1>予定の新規作成</h1> <div class="container mx-auto"> <div class="mb-3 d-block"> <%= link_to '予定一覧へ', schedules_path, class: 'btn btn-primary' %> </div> <%= form_for @schedules, url: {action: "create"} do |f| %> <div class="form-group mb-3"> <label class="form-label">件名:</label> <%= f.text_field :title, class: 'form-control' %> </div> <div class="form-group mb-3"> <label class="form-label">予定の日付:</label> <%= raw sprintf( f.date_select(:date_of, use_month_numbers: true, order: [:year,:month,:day], selected: Time.zone.now, start_year: Time.zone.now.year + 5, end_year: Time.zone.now.year, date_separator: '%s' ),'年','月') + '日' %> </div> <div class="form-group mb-3"> <label class="form-label">開始時間:</label> <%= f.time_select :start_time, class: 'form-control' %> &nbsp;~&nbsp; <label class="form-label">終了時間:</label> <%= f.time_select :end_time , class: 'form-control'%> &nbsp;( <label class="form-label">集合時間:</label> <%= f.time_select :meeting_time, class: 'form-control' %> ) </div> <div class="d-block"> <%= f.submit "新規作成する", class: 'btn btn-success' %> </div> <% end %> </div> 編集画面 app/views/schedules/edit.html.erb <h1>予定の編集</h1> <div class="container mx-auto"> <div class="mb-3 d-block"> <%= link_to '予定一覧へ', schedules_path, class: 'btn btn-primary' %> </div> <%= form_for @schedules, url: {action: "update", id: @schedules.id} do |f| %> <div class="form-group mb-3"> <label class="form-label">件名:</label> <%= f.text_field :title, class: 'form-control' %> </div> <div class="form-group mb-3"> <label class="form-label">予定の日付:</label> <%= raw sprintf( f.date_select(:date_of, use_month_numbers: true, order: [:year,:month,:day], selected: Time.zone.now, start_year: Time.zone.now.year + 5, end_year: Time.zone.now.year, date_separator: '%s' ),'年','月') + '日' %> </div> <div class="form-group mb-3"> <label class="form-label">開始時間:</label> <%= f.time_select :start_time, class: 'form-control' %> &nbsp;~&nbsp; <label class="form-label">終了時間:</label> <%= f.time_select :end_time, class: 'form-control' %> &nbsp;( <label class="form-label">集合時間:</label> <%= f.time_select :meeting_time, class: 'form-control' %> ) </div> <div class="d-block"> <%= f.submit "保存する", class: 'btn btn-success' %> </div> <% end %> </div> 詳細画面 app/views/schedules/show.html.erb <h1>予定の詳細</h1> <div class="container mx-auto"> <div class="mb-3 d-block"> <%= link_to '予定一覧へ', schedules_path, class: 'btn btn-primary' %> </div> <div class="form-group mb-3"> <label class="form-label">件名:</label> <%= @schedules.title %> </div> <div class="form-group mb-3"> <label class="form-label">予定の日付:</label> <%= @schedules.date_of.strftime("%Y年%m月%d日") %> </div> <div class="form-group mb-3"> <label class="form-label">開始時間 ~ 終了時間: </label> <%= @schedules.start_time.strftime("%H:%M") %> &nbsp;~&nbsp; <%= @schedules.end_time.strftime("%H:%M") %> &nbsp;( <label class="form-label">集合時間:</label> <%= @schedules.meeting_time.strftime("%H:%M") %> ) </div> <div class="d-block"> <%= link_to '編集', edit_schedule_path(@schedules.id), class: 'btn btn-success' %> <%= link_to '削除', schedule_path(@schedules.id), method: :delete, class: 'btn btn-danger' %> </div> </div> ユーザー機能 一覧画面 app/views/users/index.html.erb <h1>メンバーの一覧</h1> <div class="mx-3 d-block"> <%= link_to '新規作成', new_user_path, class: 'btn btn-primary' %> </div> <% if @users.blank? %> <div><%= "表示できるメンバーがいません。" %></div> <% else %> <div class="container mx-auto table-responsive"> <table class="table table-striped table-hover table-sm"> <thead> <tr> <th scope="col">ユーザー名</th> <th scope="col">メールアドレス</th> </tr> </thead> <tbody> <% @users.each do |lst| %> <tr class="clickable-row" data-href="<%= user_path lst.id %>"> <td><%= lst.name %></td> <td><%= lst.email %></td> </tr> <% end %> </tbody> </table> </div> <% end %> 新規画面 app/views/users/new.html.erb <h1>ユーザーの新規作成</h1> <div class="container mx-auto"> <div class="mb-3 d-block"> <%= link_to 'ユーザー一覧へ', users_path, class: 'btn btn-primary' %> </div> <%= form_for @users, url: {action: "create"} do |f| %> <div class="form-group mb-3"> <label class="form-label">ユーザー名:</label> <%= f.text_field :name, class: 'form-control' %> </div> <div class="form-group mb-3"> <label class="form-label">メールアドレス:</label> <%= f.email_field :email, size: "40", class: 'form-control' %> </div> <div class="form-group mb-3"> <label class="form-label">パスワード:</label> <%= f.password_field :password, class: 'form-control' %> </div> <div class="form-group mb-3"> <label class="form-label">パスワード(確認欄):</label> <%= f.password_field :password_confirmation, class: 'form-control' %> </div> <div class="d-block"> <%= f.submit "新規作成する", class: 'btn btn-success' %> </div> <% end %> </div> 編集画面 app/views/users/edit.html.erb <h1>ユーザーの編集</h1> <div class="container mx-auto"> <div class="mb-3 d-block"> <%= link_to 'ユーザー一覧へ', users_path, class: 'btn btn-primary' %> </div> <%= form_for @users, url: {action: "update", id: @users.id} do |f| %> <div class="form-group mb-3"> <label class="form-label">ユーザー名:</label> <%= f.text_field :name, class: 'form-control' %> </div> <div class="form-group mb-3"> <label class="form-label">メールアドレス:</label> <%= f.email_field :email, class: 'form-control' %> </div> <div class="form-group mb-3"> <label class="form-label">パスワード:</label> <%= f.password_field :password, class: 'form-control' %> </div> <div class="form-group mb-3"> <label class="form-label">パスワード(確認欄):</label> <%= f.password_field :password_confirmation, class: 'form-control' %> </div> <div class="d-block"> <%= f.submit "保存する", class: 'btn btn-success' %> </div> <% end %> </div> 詳細画面 app/views/users/show.html.erb <h1>ユーザーの詳細</h1> <div class="container mx-auto"> <div class="mb-3 d-block"> <%= link_to 'ユーザー一覧へ', users_path, class: 'btn btn-primary' %> </div> <div class="form-group mb-3"> <label class="form-label">ユーザー名:</label> <%= @users.name %> </div> <div class="form-group mb-3"> <label class="form-label">メールアドレス:</label> <%= @users.email %> </div> <div class="form-group mb-3"> <label class="form-label">パスワード:</label> <%= "(セキュリティに配慮し、パスワードは非表示です)" %> </div> <div class="d-block"> <%= link_to '編集', edit_user_path(@users.id), class: 'btn btn-success' %> <%= link_to '削除', user_path(@users.id), method: :delete, class: 'btn btn-danger' %> </div> </div> ちまちましか進められなくて進みが遅いので、できればどこかで時間を作って作業したいと思う。 内容はゼロだけど今回はここまで。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む