自定义设计控制器和视图

Customize devise controller and views

我对ROR很天真。我正在尝试使用设计仅使用电子邮件登录用户。如果提供电子邮件的用户不存在,我想呈现登录页面。但是,当我尝试呈现 'new' 时,在检查数据库中不存在该用户之后。这样做时出现错误 - “表单中的第一个参数不能包含 nil 或为空”。请帮我解决这个问题。提前致谢!!!

rails/app/controllers/users/sessions_controller.rb

# frozen_string_literal: true

# Users sessions controller
class Users::SessionsController < Devise::SessionsController
  include ExpireExistingToken
  
  layout 'devise'

  def new
    super
  end

  def create
    # self.resource = warden.authenticate!(auth_options)
    self.resource = User.find_by(email: params[:user][:email])
    if resource.nil?
      render 'new'
    else
      set_flash_message!(:notice, :signed_in)
      sign_in(resource_name, resource)
      yield resource if block_given?
      resource.update(language: Constant::SUPPORTED_LANGUAGES.key(params['locale'])) if params['locale'].present?
      resource.send_otp(force_expire: true) if resource.email_verified?
      respond_with resource, location: after_sign_in_path_for(resource)
      flash.delete(:notice)
    end  
  end

  def destroy
    session.delete(:is_otp_verified)
    super
  end
end

rails/app/controllers/concerns/expire_existing_token.rb

# frozen_string_literal: true

# Responsible for token expiration
module ExpireExistingToken
  extend ActiveSupport::Concern

  included do
    before_action :remove_existing_token, only: :new
  end

  protected

  def remove_existing_token
    uuid = session[:uuid]
    usr = User.find_by(uuid: uuid) if uuid
    return unless usr
    usr.send(:clear_reset_password_token)
    usr.save
    session.delete(:uuid)
  end
end

rails/app/views/devise/sessions/new.html.haml

.authentication-wrapper
  .gatway
    .brand-icon
      = image_pack_tag('packs/images/logo.png')
    .title
      Merchant Login
    .caption
      Make every moment special with WadzPay.
    = form_for(resource, as: resource_name, url: session_path(resource_name),
      html: { class: 'user-session-form new_user' }) do |f|
      .form-group
        = f.email_field :email, placeholder: 'Enter Email Address',
                                                type: 'email', class: 'form-control'
        %span
          = image_pack_tag('packs/images/mail.svg')
      .auth-btn-set
        = f.button 'Log in', class: 'btn-primery-grdient w-100'
        %a.btn-white-link.w-100{href: "register.html"} Register
  .auth-footer
    %a{href: "#"} Terms &amp; Condition
    |
    %a{href: "#"} Privacy Policy

new 视图显示当前 resource 的表单,应在操作 new 中初始化。

此时你最好的选择是通过调用 new 本身来替换 render 'new',这应该可以解决你的问题。

使用 render 'new' 将使您的应用程序加载 new html,在这种情况下您想要的是将您的用户重定向到注册页面。 将 render 'new' 替换为 redirect_to action: :new 应该可以解决问题。

“render”仅渲染模板,但如果您想获得对象访问权限以执行某些操作,那么“redirect_to”就会出现。

所以只需将 render: new 替换为 redirect_to: new