(Go rails)使用Rescue_from(ActiveSupport:Rescuable::ClassMethods)来解决404(ActiveRecord::RecordNotFound)❌
https://gorails.com/episodes/handle-404-using-rescue_from?autoplay=1
我的git: https://github.com/chentianwei411/embeddable_comments/tree/rescue_from
Handle 404s Better Using Rescue_from
在controller层添加resuce_from方法。对ActiveRecord::RecordNotFound❌进行营救。
当用户拷贝链接错误或者其他导致错误的url,网页会弹出一个404.
Well, if we couldn't find the episode, or the forum thread or whatever they were looking for, if we can't find it directly with the perfect match, then we should take that and search the database and clean it up a little bit, but then go search the database。
rails g scaffold Episode name slug
在controller修改:
private def set_episode
//find_by! 如果没有找到匹配的记录会raise an ActiveRecord::RecordNotFound
@episode = Episode.find_by!(slug: params[id])
end
进入rails console ,增加2条记录:
Episode.create(name: "Star Wars", slug: "test-1")
Episode.create(name: "Lord of the Rings", slug: "test-2")
在浏览器地址栏输入了错误的网址episodes/text, (正确的是episodes/text-1或者text-2)
导致出现❌
在controller:
class EpisodesController <ApplicationController
before_action :set_episode, only: [:show, :edit, :update, :destroy] rescue_from ActiveRecord::RecordNotFound do |exception|
byebug //一个用于debug的gem中的方法,rails默认添加的
end
end
再刷新错误网页,然后看terminal的fservent_watch:
输入:
- exception查看❌提示的类
- params[:id]查看参数是什么
- c退出。
在controller中添加ActiveRecord::Rescuable::ClassMethods#erescue_from方法
加一个block,用于执行拯救:
- 第一行对参数params[:id]再次进行模糊的搜索,并把可能的记录存在@episodes集合内。
- 第二行渲染/search/show模版,并写一些提示信息给用户阅读
- class EpisodesController <ApplicationController before_action :set_episode, only: [:show, :edit, :update, :destroy] rescue_from ActiveRecord::RecordNotFound do |exception| @episodes = Episode.where("slug LIKE ?", "%#{params[:id]}%") render "/search/show" end end
新增一个views/search/show.html.erb
<h3>很抱歉,您要访问的页面不存在!</h3>
<% if @episodes.any? %>
<p>这里有一些相似的结果:</p> <% @episodes.each do |episode| %>
<div>
<%= link_to episode.name, episode %>
</div>
<% end %>
<% else %>
<%= link_to "Check out all our episodes", episodes_path %>
<% end %>
进一步完善功能
# 把第一字符替换为空. \w指[a-zA-z0-9_]
params[:id].gsub(/^[\w-]/, '')
class EpisodesController <ApplicationController
before_action :set_episode, only: [:show, :edit, :update, :destroy] rescue_from ActiveRecord::RecordNotFound do |exception|
@query = params[:id].gsub(/^[\w-]/, '')
@episodes = Episode.where("name LIKE ? OR slug LIKE ?", "%#{@query}%", "%#{@query}%")
render "/search/show"
end
end
可以把recue_from放到一个单独的模块SearchFallback中:
把这个模块放入app/controllers/concern/search_fallback.rb中:
module SearchFallback
//因为included方法是ActiveSupport::Concern模块中的方法,所以extend这个模块,就能用included了
extend ActiveSupport::Concern
//当这个模块被类包含后,则:
included do
rescue_from ActiveRecord::RecordNotFound do |exception|
@query = params[:id].gsub(/[^\w-]/, '')
@episodes = Episode.where("name LIKE ? OR slug LIKE ?", "%#{@query}%", "%#{@query}%")
@forum_threads = Episode.where("name LIKE ? OR slug LIKE ?", "%#{@query}%", "%#{@query}%")
render "/search/show"
end
end
end
然后EpisodesController, 加上include SearchFallback
class EpisodesController < ApplicationController
include SearchFallback
rescue_from(*klasses, with:nil, &block)
营救Rescue在controller actions中产生raise的exceptions。
- *klasses -一系列的exception classes 或者class names
- with选项 -方法名或一个Proc对象。用于处理*klasses。
- &block是可选的块。
无论是with,还是&block都接受一个参数exception.
最新文章
- jquery实现幻灯片
- mxnet的python包导入的前前后后
- bzoj4349: 最小树形图&;&;bzoj2260: 商店购物
- [原创]java WEB学习笔记47:Servlet 监听器简介, ServletContext(Application 对象), HttpSession (Session 对象), HttpServletRequest (request 对象) 监听器,利用listener理解 三个对象的生命周期
- Power Gating的设计(模块二)
- C#&;java重学笔记(变量与操作符)
- C# 微信支付证书使用
- NYOJ 16 矩形嵌套(动态规划)
- JAVA面试之集合框架(三)
- centos7.0安装教程
- python数据类型(一)
- Target JRE version (1.7.0_79) does not match project JDK version (java version ";1.8.0_171";), will use sources from JDK: 1.7
- [PA2012] Tax
- 关于ComponentName组件名称的使用
- 【python小练】0001
- 使用PrerenderSpaPlugin预渲染插件没有成功渲染
- Swagger介绍-一套流行的API框架
- 【delphi】delphi操作sqlite3
- shell 9test命令
- spring ioc 注解配置