学生向けプログラミング入門 | 無料

学生向けにプログラミングを無料で解説。Java、C++、Ruby、PHP、データベース、Ruby on Rails, Python, Django

Rails導入編 | カート機能の実装 | 23 | Gメール

↓↓クリックして頂けると励みになります。



22 | チェックアウト】 << 【ホーム】 >> 【24 | ログイン





Railsアプリケーションで電子メールの設定を行うには、Gメールを利用するのが一番簡単です。
Gメールを利用するには、設定でセキュリティの「2段階認証プロセス」をオンにし、アプリパスワードを取得する必要があります。
アプリパスワードの取得方法は下記のページを参考にしてください。
mrradiology.hatenablog.jp


「SampleCart/config/environments」フォルダの「development.rb」ファイルに設定を追加します。
77行目に以下の記述を追加しています。

  #Gメールの設定
  config.action_mailer.delivery_method = :smtp
  config.action_mailer.smtp_settings = {
    address: "smtp.gmail.com",
    port: 587,
    enable_starttls_auto: true,
    authentication: "plain",
    user_name: 'win.rails.learn@gmail.com',
    password: '生成したアプリパスワード'
  }



記述追加 【SampleCart/config/environments/development.rb】77行目

require "active_support/core_ext/integer/time"

Rails.application.configure do
  # Settings specified here will take precedence over those in config/application.rb.

  # In the development environment your application's code is reloaded any time
  # it changes. This slows down response time but is perfect for development
  # since you don't have to restart the web server when you make code changes.
  config.enable_reloading = true

  # Do not eager load code on boot.
  config.eager_load = false

  # Show full error reports.
  config.consider_all_requests_local = true

  # Enable server timing
  config.server_timing = true

  # Enable/disable caching. By default caching is disabled.
  # Run rails dev:cache to toggle caching.
  if Rails.root.join("tmp/caching-dev.txt").exist?
    config.action_controller.perform_caching = true
    config.action_controller.enable_fragment_cache_logging = true

    config.cache_store = :memory_store
    config.public_file_server.headers = {
      "Cache-Control" => "public, max-age=#{2.days.to_i}"
    }
  else
    config.action_controller.perform_caching = false

    config.cache_store = :null_store
  end

  # Store uploaded files on the local file system (see config/storage.yml for options).
  config.active_storage.service = :local

  # Don't care if the mailer can't send.
  config.action_mailer.raise_delivery_errors = false

  config.action_mailer.perform_caching = false

  # Print deprecation notices to the Rails logger.
  config.active_support.deprecation = :log

  # Raise exceptions for disallowed deprecations.
  config.active_support.disallowed_deprecation = :raise

  # Tell Active Support which deprecation messages to disallow.
  config.active_support.disallowed_deprecation_warnings = []

  # Raise an error on page load if there are pending migrations.
  config.active_record.migration_error = :page_load

  # Highlight code that triggered database queries in logs.
  config.active_record.verbose_query_logs = true

  # Highlight code that enqueued background job in logs.
  config.active_job.verbose_enqueue_logs = true

  # Suppress logger output for asset requests.
  config.assets.quiet = true

  # Raises error for missing translations.
  # config.i18n.raise_on_missing_translations = true

  # Annotate rendered view with file names.
  # config.action_view.annotate_rendered_view_with_filenames = true

  # Uncomment if you wish to allow Action Cable access from any origin.
  config.action_cable.disable_request_forgery_protection = true

  # Raise error when a before_action's only/except options reference missing actions
  config.action_controller.raise_on_missing_callback_actions = true

  #Gメールの設定
  config.action_mailer.delivery_method = :smtp
  config.action_mailer.smtp_settings = {
    address: "smtp.gmail.com",
    port: 587,
    enable_starttls_auto: true,
    authentication: "plain",
    user_name: 'win.rails.learn@gmail.com',
    password: '生成したアプリパスワード'
  }

end



注文を受けたことを知らせるメール送信を実装します。


ターミナルで以下のコマンドを入力します。
コマンド
rails generate mailer Order received shipped

~/Desktop/Rails7_1/SampleCart $ rails generate mailer Order received shipped

      create  app/mailers/order_mailer.rb
      invoke  erb
      create    app/views/order_mailer
      create    app/views/order_mailer/received.text.erb
      create    app/views/order_mailer/received.html.erb
      create    app/views/order_mailer/shipped.text.erb
      create    app/views/order_mailer/shipped.html.erb
      invoke  test_unit
      create    test/mailers/order_mailer_test.rb
      create    test/mailers/previews/order_mailer_preview.rb



生成されたファイルを編集します。
「SampleCart/app/mailers」フォルダにある「order_mailer.rb」ファイルを以下のように編集します。
3行目にdefault from: 'Sample Cart 'の記述を追加しています。
また、10行目の「received(order)」メソッドの内容も変更しています。


記述追加 【SampleCart/app/mailers/order_mailer.rb】3,11行目

class OrderMailer < ApplicationMailer

  default from: 'Sample Cart <win.rails.learn@gmail.com>'

  # Subject can be set in your I18n file at config/locales/en.yml
  # with the following lookup:
  #
  #   en.order_mailer.received.subject
  #
  def received(order)
    @order = order
    mail to: order.email, subject: 'Sample Cart 注文確認'
  end

  # Subject can be set in your I18n file at config/locales/en.yml
  # with the following lookup:
  #
  #   en.order_mailer.shipped.subject
  #
  def shipped
    @greeting = "Hi"

    mail to: "to@example.org"
  end
end



電子メールのテンプレートを作成します。
「SampleCart/app/views/order_mailer/received.html.erb」ファイルを以下のように編集します。


記述編集 【SampleCart/app/views/order_mailer/received.html.erb】

<%= @order.name %>様
<br>
Sample Cartでのご注文、誠にありがとうございます。
<br>
あなたがご注文されたのは以下の商品です。
<br>
<%= render @order.line_items -%>
<br>
商品発送の際には別途電子メールでご連絡いたします。



「<%= render @order.line_items -%>」の記述で読み込まれるのは「SampleCart/app/views/line_items/_line_item.html.erb」ファイルです。
ここでは「truncate()」などの正規のヘルパーメソッドを使用できます。
以下のように記述すると項目の数量とタイトルを1行の形式に整えます。


記述編集 【SampleCart/app/views/line_items/_line_item.html.erb】

<%= sprintf("%2d x %s",
            line_item.quantity,
            truncate(line_item.good.title, length: 50)) %>



メールの生成をするための記述をコントローラー「orders_controller.rb」ファイルに行います。
「create()」メソッド35行目にOrderMailer.received(@order).deliver_laterの記述を追加します。


記述追加 【SampleCart/app/controllers/orders_controller.rb】

class OrdersController < ApplicationController

  include CurrentCart
  before_action :set_cart, only: [:new, :create]
  before_action :ensure_cart_isnt_empty, only: :new
  before_action :set_order, only: [:show, :edit, :update, :destroy]

  # GET /orders or /orders.json
  def index
    @orders = Order.all
  end

  # GET /orders/1 or /orders/1.json
  def show
  end

  # GET /orders/new
  def new
    @order = Order.new
  end

  # GET /orders/1/edit
  def edit
  end

  # POST /orders or /orders.json
  def create
    @order = Order.new(order_params)
    @order.add_line_items_from_cart(@cart)

    respond_to do |format|
      if @order.save
        Cart.destroy(session[:cart_id])
        session[:cart_id] = nil
        OrderMailer.received(@order).deliver_later
        format.html { redirect_to markets_index_url, notice: '商品が注文されました。' }
        format.json { render :show, status: :created, location: @order }
      else
        format.html { render :new }
        format.json { render json: @order.errors, status: :unprocessable_entity }
      end
    end
  end

  # PATCH/PUT /orders/1 or /orders/1.json
  def update
    respond_to do |format|
      if @order.update(order_params)
        format.html { redirect_to order_url(@order), notice: "注文が変更されました。" }
        format.json { render :show, status: :ok, location: @order }
      else
        format.html { render :edit, status: :unprocessable_entity }
        format.json { render json: @order.errors, status: :unprocessable_entity }
      end
    end
  end

  # DELETE /orders/1 or /orders/1.json
  def destroy
    @order.destroy!

    respond_to do |format|
      format.html { redirect_to orders_url, notice: "注文を削除しました。" }
      format.json { head :no_content }
    end
  end

  private
    # Use callbacks to share common setup or constraints between actions.
    def set_order
      @order = Order.find(params[:id])
    end

    # Only allow a list of trusted parameters through.
    def order_params
      params.require(:order).permit(:name, :address, :email, :pay_type)
    end

    def ensure_cart_isnt_empty
      if @cart.line_items.empty?
        redirect_to markets_index_url, notice: '商品がカートに入っていません。'
      end
    end    
end



これで注文されたときに入力されたメールアドレス宛に自動でメールを送ることができます。
動作を確認してください。
発送完了時のメールが必要であれば「SampleCart/app/mailers/order_mailer.rb」ファイルの「shipped()」メソッドを同じ様に実装すればよいです。

注文確認メール
注文確認メール



22 | チェックアウト】 << 【ホーム】 >> 【24 | ログイン




↓↓クリックして頂けると励みになります。

関連記事(外部サイト)