Ruby on Rails:提交注册表单时存储访客IP至PostgreSQL数据库
解决Devise注册时存储访客IP的问题
核心问题:你的注册请求由Devise自带的Devise::RegistrationsController处理,而非你自定义的UsersController,因此你在UsersController#create中设置IP的代码并未执行,这是ip_address字段始终为nil的根本原因。
推荐方案:在Devise注册控制器中直接设置IP(安全防篡改)
无需修改表单,直接在控制器层面获取并赋值IP,避免用户篡改参数:
1. 生成自定义Devise注册控制器
在终端执行命令:
rails generate devise:controllers users -c registrations
该命令会生成app/controllers/users/registrations_controller.rb文件。
2. 重写create方法设置IP
打开生成的控制器,添加IP赋值逻辑:
class Users::RegistrationsController < Devise::RegistrationsController def create super do |resource| # 保存用户前设置访客IP resource.ip_address = request.remote_ip end end end
3. 更新路由指向自定义控制器
修改config/routes.rb,将Devise注册路由指向自定义控制器:
devise_for :users, controllers: { registrations: "users/registrations" }
4. 保留已有参数许可(如需要)
如果注册表单包含first_name、last_name等字段,继续在ApplicationController中保留参数许可:
class ApplicationController < ActionController::Base before_action :configure_permitted_parameters, if: :devise_controller? protected def configure_permitted_parameters devise_parameter_sanitizer.permit(:sign_up, keys: [:first_name, :last_name]) end end
备选方案:通过表单传递IP(不推荐,易被篡改)
若需通过表单传递IP,需修正以下问题:
1. 修正表单字段渲染
修改app/views/devise/registrations/new.html.erb中的IP字段部分,改为隐藏字段并确保正确渲染(添加=):
<%= form.hidden_field :ip_address, value: request.remote_ip %>
2. 允许Devise接收ip_address参数
更新ApplicationController的参数许可,加入:ip_address:
def configure_permitted_parameters devise_parameter_sanitizer.permit(:sign_up, keys: [:first_name, :last_name, :ip_address]) end
验证效果
完成配置后重启服务器,注册新用户即可看到数据库user.ip_address字段已正确存储访客IP。
内容的提问来源于stack exchange,提问作者OUIC
相关产品推荐
相关产品推荐

