Homeland Ruby China,对!没错!...不好意思,报告个 Bug

Peter · 2012年07月16日 · 最后由 Rei 回复于 2012年07月16日 · 3008 次阅读

各位管理员 @lgn21st @huacnlee

首先谢谢你们做了这样一个系统,给我们提供了一个好的学习样本。不过今天又发现个 bug, 或者说是上次报告的 bug 的衍生 bug

[Email 可以随便修改,用户可以随便自杀,不用提供密码](http://ruby-china.org/topics/4260),这些事弱爆了,用户自己头脑清醒点就没事了,出问题可以推给用户,因为他们自己没有登出,被改 Email 也怪不得谁。

我接受现实了,继续改用户系统,今天我想让用户从 Facebook 进来第一件事就是改掉系统给他们设置的随机用户名 (login) 和 密码。所以我在 user 表加了个字段,如果为 0 且用户不在修改用户名和密码的页面/account/edit,我就重定向 (redirect_to) 过来,代码写好了,测试: /topics /wiki /sites 都可以跳回 /account/edit

开心。

但点“会员” /users,出现 404, 好吧,自己技术不行,那就接受现实,到处 puts 吧,总会找到哪出的问题。

夜深了,我也挖得更深了,最后找到这个文件: .rvm/gems/ruby-1.9.3-p194/gems/actionpack-3.2.6/lib/action_controller/metal/redirecting.rb

def redirect_to(options = {}, response_status = {}) #:doc:
  raise ActionControllerError.new("Cannot redirect to nil!") unless options
  raise AbstractController::DoubleRenderError if response_body

  self.status        = _extract_redirect_to_status(options, response_status)
  self.location      = _compute_redirect_to_location(options)
  self.response_body = "<html><body>You are being <a href=\"#{ERB::Util.h(location)}\">redirected</a>.</body></html>"
end

一顿 puts 之后,发现只有/users 链接 self.location 为 nil,我直接赋值也不行:

self.location      = "http://localhost:3000/account/edit"

好吧,我想知道这个 location 是个什么东西,在.rvm/gems/ruby-1.9.3-p194/gems/ 目录下 ack 一顿乱找,无果。中间修改了其他文件后有好些出错信息,copy+google 也无果。

因为修改 gemset 里面的文件要重启rails s,时间就不知道浪费多少了,终于在今天,就在今天,突然想到在 app/controller/users_controller.rb里面看看,之前只关注过 UsersController 的 before_filter, 没有搜索过 location,一搜发现,果然有戏

  def location
    @location = Location.find_by_name(params[:id])
    if @location.blank?
      render_404
      return
    end
...
 end

原来 UsersController 自己有个 location 方法,redirect_to 函数里面想把一个链接字符串硬塞给 location,人家怎么可能要,人家又不傻,只有我傻了。

把这段注释掉,好了,可以跳转了,当然这只是发现问题,解决问题要做事还很多呢。这个 location 还导致了官方网站还有另一个 Bug,就是输入不在 location 表里的地名,比如“一个城市”,就会去 404。

============================================================ 所以请管理员们或各路高手指导一下吧,我觉得最好把 users 表里的 location 字段和这里的 location 方法最好改个名,比如"hometown", rails 里面不至于用这种词吧。

我想来修补这个 bug,不知道要修改些什么,如果你们能指点一下,不胜感激。

如果有高手想做,那就再好不过了。

这里应该只需要把 location 这个 Action 换一个名字就好了。 赞楼主的深入挖掘的精神。 BTW. 不需要搞 Facebook 登陆,这里没法接入,服务器再国内,OAuth 连不上的。

首先感谢楼主报 bug,不过信息量太大我没提炼出要点是什么。到底是:

  1. 做了什么修改?
  2. 出了什么错误?

谢谢 @huacnlee 回复,关于在 /account/edit中填的城市如果不在location表中,就会定位到 404 这个官方都存在的 bug 如何修复呢? app/controller/users_controller.rb

if @location.blank?
      render_404
      return
end

location 表中原来存在的城市应该也是大家填的吧,这个 bug 是不是最近才出现的, 原来计划应该是检测 location 表中有没有用户输入的城市, 有的话直接在 users 表中加入 location_id, 没有的话在 location 表加入城市名称,然后把该城市的 location_id 加入用户信息中。

@Rei 错误就是app/controller/users_controller.rb中有个def location, 但 rails 中会用到location这个字段,这样当 rails 给self.location赋值的时候,就会出错。

另外的 bug 就是在这个页面 http://ruby-china.org/account/edit 请在城市那输入 "九寨沟",你看一下是不是到 404 去了?

@yzhrain 的经验:

命名时请留意 Rails 下的关键字 http://yangzhihuan.iteye.com/blog/577657

把 action 的名字改掉就行了。

@Rei 我现在没看代码,难道改掉就可以了,这个 action 没有地方用吗?

@huacnlee @Rei 4 楼"九寨沟"的问题应该怎么改,指点一下,担心涉及很多文件,改了留下后患,谢谢

#7 楼 @Peter 还要改掉路由,把 /users/location 显式指到那个 action

match "users/location/:id", :to => "users#新action名", :as => :location_users

PS:这里应该用 get 不用 match,可以顺便改了

编码问题似乎是 moped 这个 gem 的问题,升到 1.0.1 解决。

bundle update moped

Peter 报告 Bug 提及了此话题。 04月03日 10:56
需要 登录 后方可回复, 如果你还没有账号请 注册新账号