Ruby on Rails: получение ошибки 404 не найдено при переходе на следующую страницу после поиска с использованием pg_search и will_paginate

Я столкнулся со странной ошибкой, когда переход на следующую страницу после поиска приведет к ошибке 404 не найдено. Но нумерация страниц работает хорошо, если я не ищу.

маршруты.rb

resources :activities do
  post :search, on: :collection
end

match "/403", to: "errors#error_403", via: :all
match "/404", to: "errors#error_404", via: :all
match "/422", to: "errors#error_422", via: :all
match "/500", to: "errors#error_500", via: :all

get :ie_warning, to: 'errors#ie_warning'
get :javascript_warning, to: 'errors#javascript_warning'
get :pwreset, to: "pages#pwreset"
get :activities, to: "activities#index"
get :home, to: "pages#home"
root to: "pages#home"

контроллер.rb

@@page_size = 3
# GET /activities
def index
  @activities = Activity.paginate(:page => params[:page], :per_page => @@page_size)
end

# POST /products/search
def search
  if params[:search][:title].present?
    @activities = Activity.search_activities(params[:search][:title]).paginate(:page => params[:page], :per_page => @@page_size)
    render :index
  else
    @activities = Activity.paginate(:page => params[:page], :per_page => @@page_size)
  end

end

html.haml

- @activities.each do |activity|
.row
  .col-md-8
    = link_to activity.title, activity
  .col-md-2
    %p= activity.publisher
  .col-md-2
    %p= activity.created_at.to_date

.force-to-bottom
  .text-center
    = will_paginate @activities


= simple_form_for :search, url: search_activities_path, method: :post do |f|

  .form-inline
    = f.input :title, label: false, placeholder: 'search...'

    = button_tag(type: 'submit', class: "btn btn-primary") do
      %span.glyphicon.glyphicon-search{"aria-hidden" => "true"}

    %span.glyphicon.glyphicon-remove{"aria-hidden" => "true"}
    = link_to 'clear filter', activities_path

сообщение об ошибке

Started GET "/activities/search?page=2" for ::1 at 2018-04-16 04:39:57 +0100
Processing by ActivitiesController#show as HTML
Parameters: {"page"=>"2", "id"=>"search"}
Activity Load (17.9ms)  SELECT  "activities".* FROM "activities" WHERE "activities"."id" = $1 LIMIT $2  [["id", 0], ["LIMIT", 1]]
Rendering errors/error_404.html.haml within layouts/application
Haml::TempleEngine: Option :ugly is invalid
Rendered errors/error_404.html.haml within layouts/application (6.2ms)
Haml::TempleEngine: Option :ugly is invalid
Haml::TempleEngine: Option :ugly is invalid
Rendered layouts/_environment_notice.html.haml (2.0ms)
Completed 404 Not Found in 245ms (Views: 162.2ms | ActiveRecord: 74.7ms)

кто-нибудь может помочь, пожалуйста, я до сих пор не знаю, что происходит с этой ошибкой после нескольких часов исследований


person Zilong Tian    schedule 16.04.2018    source источник


Ответы (2)


При поиске параметры передаются методом POST (method: :post). Когда вы нажимаете на следующую страницу, вы запрашиваете страницу через GET, однако браузер не отправляет параметры поиска через GET, и нет маршрута get :search, поэтому вместо этого используется действие show, ведущее к странице 404.

Хотя может быть возможно заставить will_paginate использовать POST, это не рекомендуется.

См. https://github.com/mislav/will_paginate/wiki/Simple-search :

При создании формы поиска убедитесь, что ее метод GET

<% form_tag request.path, :method => 'get' do %>
  <% content_tag :label do %>
    Search term:
    <%= text_field_tag :search, params[:search] %>
  <% end %>
<% end %>

Если действие вашей формы — POST (или любой другой метод HTTP), то условие поиска не будет применяться к последующим ссылкам на страницы. Другими словами, когда вы переходите по ссылке «Следующая страница» или любой другой странице, параметры поиска будут потеряны.

В любом случае поисковые формы, которые публикуются с помощью GET, являются лучшей практикой. Одним из непосредственных преимуществ является то, что пользователи могут добавлять результаты поиска в закладки. Кэширование — еще одно преимущество: браузеры, прокси-серверы и т. д. с удовольствием кэшируют содержимое, полученное в результате запроса GET.

person stefan0xC    schedule 16.04.2018
comment
спасибо за ответ, вы очень хорошо объяснили! поэтому мне просто нужно изменить метод формы с post на get, а также в route.rb? и вы упомянули, что нет маршрута get: поиск, как мне добавить маршрут? извините, это мой первый опыт использования ruby ​​on rails. мои вопросы могут быть глупыми - person Zilong Tian; 16.04.2018

пост :search, on: :collection А ваш запрос-то получиться?

person Imre Raudsepp    schedule 16.04.2018
comment
извини, я тебя не понимаю. запрос получен, потому что will_paginate ? - person Zilong Tian; 16.04.2018
comment
У вас есть объявленные ресурсы :activities do post :search, on: : collection end /activities/search?page=2 ссылка только для запроса на публикацию ..не для запроса на получение - person Imre Raudsepp; 16.04.2018
comment
ресурсы :активности только: [:индекс] сделать коллекцию получить :поиск, в: 'деятельности#поиск' конец конец - person Imre Raudsepp; 16.04.2018
comment
спасибо, я просто изменил сообщение, чтобы получить как route.rb, так и html. и он начинает работать сейчас. Но раньше URL-адрес был /activities/search?page=2, а теперь /activities/search?utf8=✓&search[title]=d&button=. Можно ли это исправить? - person Zilong Tian; 16.04.2018