Rails: 如何防止路由与静态页面和动态页面冲突?
Rails: How to prevent routing clashes with static and dynamic pages?
我有以下路线:
Rails.application.routes.draw do
get '/:id', to: 'foo#bar', constraints: { id: /\d+/ }
end
/1 使用 ID #1 加载我的记录。问题是我的路由与 Rails 默认静态页面(404、500 等...)冲突。
我怎样才能让静态错误页面与我的动态路由一起工作?
如果可能的话,我不介意将我的静态页面移动到 /errors/404 这样的路由。
编辑 1:
重新打开 ActionDispatch::ShowExceptions class 并更改私有方法 render_exception 是一个非常 hacky 的解决方案:
config/application.rb:
require_relative 'boot'
require 'rails/all'
Bundler.require(*Rails.groups)
module MyApp
class Application < Rails::Application
config.load_defaults 5.2
config.exceptions_app = self.routes
end
end
module ActionDispatch
class ShowExceptions
private
def render_exception(request, exception)
backtrace_cleaner = request.get_header "action_dispatch.backtrace_cleaner"
wrapper = ExceptionWrapper.new(backtrace_cleaner, exception)
status = wrapper.status_code
request.set_header "action_dispatch.exception", wrapper.exception
request.set_header "action_dispatch.original_path", request.path_info
request.path_info = "/errors/#{status}"
response = @exceptions_app.call(request.env)
response[1]["X-Cascade"] == "pass" ? pass_response(status) : response
rescue Exception => failsafe_error
$stderr.puts "Error during failsafe response: #{failsafe_error}\n #{failsafe_error.backtrace * "\n "}"
FAILSAFE_RESPONSE
end
end
end
我已将 request.path_info = "/#{status}"
更改为 request.path_info = "/errors/#{status}"
。
我根本不喜欢这个解决方案。
您可以更改呈现异常的目录。您将需要更改一些配置,例如,您可以将以下内容放入 Application
class 中的 config/application.rb
:
config.exceptions_app = ActionDispatch::PublicExceptions.new(Rails.public_path.join('errors'))
然后将那些静态 404.html
和 500.html
从 public
移动到新创建的 public/errors
目录。
我有以下路线:
Rails.application.routes.draw do
get '/:id', to: 'foo#bar', constraints: { id: /\d+/ }
end
/1 使用 ID #1 加载我的记录。问题是我的路由与 Rails 默认静态页面(404、500 等...)冲突。
我怎样才能让静态错误页面与我的动态路由一起工作?
如果可能的话,我不介意将我的静态页面移动到 /errors/404 这样的路由。
编辑 1:
重新打开 ActionDispatch::ShowExceptions class 并更改私有方法 render_exception 是一个非常 hacky 的解决方案:
config/application.rb:
require_relative 'boot'
require 'rails/all'
Bundler.require(*Rails.groups)
module MyApp
class Application < Rails::Application
config.load_defaults 5.2
config.exceptions_app = self.routes
end
end
module ActionDispatch
class ShowExceptions
private
def render_exception(request, exception)
backtrace_cleaner = request.get_header "action_dispatch.backtrace_cleaner"
wrapper = ExceptionWrapper.new(backtrace_cleaner, exception)
status = wrapper.status_code
request.set_header "action_dispatch.exception", wrapper.exception
request.set_header "action_dispatch.original_path", request.path_info
request.path_info = "/errors/#{status}"
response = @exceptions_app.call(request.env)
response[1]["X-Cascade"] == "pass" ? pass_response(status) : response
rescue Exception => failsafe_error
$stderr.puts "Error during failsafe response: #{failsafe_error}\n #{failsafe_error.backtrace * "\n "}"
FAILSAFE_RESPONSE
end
end
end
我已将 request.path_info = "/#{status}"
更改为 request.path_info = "/errors/#{status}"
。
我根本不喜欢这个解决方案。
您可以更改呈现异常的目录。您将需要更改一些配置,例如,您可以将以下内容放入 Application
class 中的 config/application.rb
:
config.exceptions_app = ActionDispatch::PublicExceptions.new(Rails.public_path.join('errors'))
然后将那些静态 404.html
和 500.html
从 public
移动到新创建的 public/errors
目录。