ROR學習筆記(38)——繼續查詢&查詢后的排序(ajax)

源文檔在下面的URL:
https://github.com/kamionayuki/shop


用非AJAX的方式實現了查詢和排序后,還是想用AJAX的方式實現。但在此之前,需要把cookies這個隱患排除掉。無意中有了一個驚人的發現,就是在views中xxx_path是可以隨意加參數的。比如:
view中

<%= link_to "all products", products_path(para1: "txy", para2: " ai ", para3: "txl") %>

controller中

def index
    @para = params[:para1] +params[:para2] + params[:para2]
    @product = Product.all
end

用這個方法完全可以繞過cookies,以免把相關信息暴露出去。真的是太好了。
去掉了cookies后,就想用ajax來進行查詢和排序,原理跟原來一樣,只是用了ajax的方法了,具體操作如下:

  1. views中
    修改index.html.erb
<h1><%= link_to "Product", root_path %></h1>
  <%= will_paginate @products, renderer: BootstrapPagination::Rails %>  
  <%= form_tag search_products_path, method: "get", remote: true do %>
  <%= label_tag :s_price, "Price" %>
  <%= text_field_tag :s_price %>
  <%= submit_tag "Search" %>
  <% end %>
<table class="table table-striped">
  <%= render partial: 'thead', locals: {query: @query, order: @order} %>
  <%= render 'tbody' %>
</table>

新增加"views/products/_thead.html.erb",并且用params[:query]來傳送當前頁面的查詢條件

<thead>
    <tr>
      <th><%= link_to "ID", sort_products_path(sort_by: order[:p_id], query: query), remote: true %></th>
      <th><%= link_to "Name", sort_products_path(sort_by: order[:p_name], query: query), remote: true %></th>
      <th><%= link_to "Price", sort_products_path(sort_by: order[:p_price], query: query), remote: true %></th>
      <th><%= link_to "Description", sort_products_path(sort_by: @order[:p_description], query: @query), remote: true  %></th>
      <th><%=t '.actions', :default => t("helpers.actions") %></th>
    </tr>
</thead>

新增加"views/products/_tbody.html.erb"

<tbody>
<% @products.each do |product| %>
  <tr>
    <td><%= link_to product.id, product_path(product) %></td>
    <td><%= product.name %></td>
    <td><%= product.price %></td>
    <td><%= product.description %></td>
    <td>
      <%= link_to t('.edit', :default => t("helpers.links.edit")),
                  edit_product_path(product), :class => 'btn btn-default btn-xs' %>
      <%= link_to t('.destroy', :default => t("helpers.links.destroy")),
                  product_path(product),
                  :method => :delete,
                  :data => { :confirm => t('.confirm', :default => t("helpers.links.confirm", :default => 'Are you sure?')) },
                  :class => 'btn btn-xs btn-danger' %>
    </td>
  </tr>
<% end %>
</tbody>

新增加"views/products/_products.js.erb"

$("thead").next().remove();
$("thead").after("<%= j render('tbody') %>");
$("tbody").prev().remove();
$("tbody").before("<%= j render(partial: 'thead', locals: {query: @query, order: @order}) %>");
  1. controller中沒有多少變化,只是把cookies[:query]變成了params[:query],同時增加了@query用來把查詢條件傳給頁面中的params[:query]。并且對@order進行了一下優化。
def index
    @products = Product.all.paginate(page: params[:page], per_page: 12)
    query = "1 = 1"
    @query = encode(query)
    respond_to do |format|
      format.html         
    end  
  end

  def sort
    @query = params[:query]
    query = decode(params[:query])
    order_query = params[:sort_by].join(" ")
    @products = Product.where(query).order(order_query).paginate(page: params[:page], per_page: 12)
    order_change(@order, params[:sort_by])
    render '_products'    
  end

  def search    
    if params[:s_price] == ""
      redirect_to :back
    else
      query = "price like \'%s\'" % params[:s_price]
      @products = Product.where(query).paginate(page: params[:page], per_page: 12)
      @query = encode(query)
      render '_products'      
    end   
  end
  
  private
    def order_init
      @order = {}
      @order[:p_price] = ["price", "desc"]
      @order[:p_id] = ["id", "desc"]
      @order[:p_name] = ["name", "desc"]
      @order[:p_description] = ["description", "desc"]
      return @order
    end

    def order_change(order, sort_by)      
      key = "p_" + sort_by.first
      value = sort_by.last
      value = value == "desc" ? "asc" : "desc"
      order[key.to_sym] = [sort_by.first, value]
    end
  1. routs中
resources :products do
    collection do
      get 'search'
      get 'sort'
    end
  end

大功告成!!!
wait~~~用ajax來實現查詢和排序的好處是頁面的url地址不會把相關信息顯示出來。但上面的做法有兩個問題

  1. 因為用的是“get”方法,所以當鼠標移動在表頭的鏈接上時,仍然會顯示相關信息(這個應該好處理,只要把sort改成post,views用button_to就可以了,具體如下)
    view中
  <thead>
    <tr>
      <th><%= button_to "ID", sort_products_path(sort_by: order[:p_id], query: query), remote: true, class: "btn btn_link" %></th>
      <th><%= button_to "Name", sort_products_path(sort_by: order[:p_name], query: query), remote: true, class: "btn btn_link" %></th>
      <th><%= button_to "Price", sort_products_path(sort_by: order[:p_price], query: query), remote: true, class: "btn btn_link" %></th>
      <th><%= button_to "Description", sort_products_path(sort_by: @order[:p_description], query: @query), 
                                                                    remote: true, class: "btn btn_link"  %></th>
      <th><%=t '.actions', :default => t("helpers.actions") %></th>
    </tr>
  </thead>

routes中

resources :products do
    collection do
      get 'search'
      post 'sort'
    end
  end
  1. 用了ajax進行排序和查詢后。從此再也不能用will_paginate進行分頁了。為這解決這個,花了兩個多小時也沒有搞定,也沒有查到資料。不知道有沒有好的方法來進行處理。參考了一下其它的網站,如果是ajax進行查詢的排序的話,就沒有分頁功能。如果有分頁功能的話,就沒有用到ajax。因此以后如果有分頁的需求,就不用ajax好了。吼吼~~~~

繼續補充(重要)

可以對will_paginate進行ajax的分頁了!!真的是無心插柳啊,哈哈哈哈。如下:

  1. index.html.erb修改一下:
<%- model_class = Product -%>
  <h1><%= link_to "Product", root_path %></h1>
  
  <%= render 'paginate' %>
  
  <%= form_tag search_products_path, method: "get", remote: true do %>
  <%= label_tag :s_price, "Price" %>
  <%= text_field_tag :s_price %>
  <%= submit_tag "Search" %>
  <% end %>
<table class="table table-striped">
  <%= render partial: 'thead', locals: {query: @query, order: @order} %>
  <%= render 'tbody' %>
</table>
  1. 增加一個_paginate.html.erb的文件
<%= will_paginate @products, renderer: BootstrapPagination::Rails %>
  1. _products.js.erb修改一下:
$("thead").next().remove();
$("thead").after("<%= j render('tbody') %>");
$("tbody").prev().remove();
$("tbody").before("<%= j render(partial: 'thead', locals: {query: @query, order: @order}) %>"); 
var flag = $(".pagination").prev();
$(".pagination").remove();
flag.after("<%= j render('paginate') %>");
$(".pagination a").attr('data-remote', 'true')
  1. 最要注意的是,排序的ajax不要用post方法,用get方法就OK了!!
    這真的是太意外了,哈哈哈
最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 228,156評論 6 531
  • 序言:濱河連續發生了三起死亡事件,死亡現場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發現死者居然都...
    沈念sama閱讀 98,401評論 3 415
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 176,069評論 0 373
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 62,873評論 1 309
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 71,635評論 6 408
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發上,一...
    開封第一講書人閱讀 55,128評論 1 323
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 43,203評論 3 441
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 42,365評論 0 288
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發現了一具尸體,經...
    沈念sama閱讀 48,881評論 1 334
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 40,733評論 3 354
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發現自己被綠了。 大學時的朋友給我發了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 42,935評論 1 369
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 38,475評論 5 358
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發生泄漏。R本人自食惡果不足惜,卻給世界環境...
    茶點故事閱讀 44,172評論 3 347
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 34,582評論 0 26
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 35,821評論 1 282
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 51,595評論 3 390
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 47,908評論 2 372

推薦閱讀更多精彩內容