railsのajaxのやり方

ajaxのやり方は色々あると思うのですが、その中の一つの書き方です。

サンプルとして、commentの中の現在時刻を更新する方法をajaxで書きます。

こんなpartialがあったとします

view側

comments/index.html

- year = Time.now.year
- month = Time.now.month
- day = Time.now.day
= render partial: "time", locals: { year: year, month: month, day: day }

coments/_time.html.slim

.test*{ "data-time" => [year, month, day] }
  .year = "#{year}"
  .month = "#{month}"
  .day = "#{day}"

data属性を使っているのは、DOM操作にすると個人的に壊れやすくなるからです。

エラー時の処理を書きたい場合は、$.ajaxを使用してください。

js側

comments.coffee

$ ->
  $('.test').on 'click', ->
    $this = $(this)
    time = $this.data('time')
    params = {year: time[0], month: time[1], day: time[2]}
    $.get 'time', params, (r) ->
      $('.test').html(r)

routes側

getの取得先がない状態のままになっているので、routeを追加します。

config/routes.rb

  get 'time' => 'comments#time'

受け取ったデータを加工する処理をコントローラーに書きます。

これができたらあとはいじり放題なので、ここまで来るのが難所な気がします。

controller側

comments_controller.rb

  def time
    @year = params[:year].to_i + 1
    @month = params[:month].to_i + 1
    @day = params[:day].to_i + 1
    render layout: false
  end

render layout: falseにしているのは、表示するviewを現在のままにしておきたいからです。

呼び出されるview側

comments/time.html.slim

- year = @year
- month = @month
- day = @day
.test*{ "data-time" => [year, month, day] }
  .year*{"data-year" => year} = "#{year}年"
  .month*{"data-month" => month} = "#{month}月"
  .day*{"data-day" => day} = "#{day}日"

これで一応動きます。

個人的に一番難しいのは、routesとdef timeを作成する場所です。

binding.pryでお望みの場所にたどり着いた瞬間に、ゴールが見えるって感じがしています。

一つの書き方として、覚えておきたかったので、書きました。

以上です。