Ruby on rails Rails:根据存储位置为设备登录呈现不同的视图

Ruby on rails Rails:根据存储位置为设备登录呈现不同的视图,ruby-on-rails,devise,Ruby On Rails,Devise,我正在使用加载iframe的bookmarklet。我正在使用Desive进行身份验证。如果iframe加载并尝试点击“bookmark”操作,但需要进行身份验证,则它显然会在转发到“bookmark”操作之前将iframe重定向到登录路径。我希望“sessions/new”操作(登录页面)此时以不同的布局呈现,以便登录页面适合iframe。Deviate使用带有作用域的渲染方法,而不是标准的渲染方法,并向其传递:layout=>“我的iframe\u布局”选项不起作用。我尝试将render\u

我正在使用加载iframe的bookmarklet。我正在使用Desive进行身份验证。如果iframe加载并尝试点击“bookmark”操作,但需要进行身份验证,则它显然会在转发到“
bookmark
”操作之前将iframe重定向到登录路径。我希望“
sessions/new
”操作(登录页面)此时以不同的布局呈现,以便登录页面适合iframe。Deviate使用带有作用域的
渲染方法,而不是标准的渲染方法,并向其传递
:layout=>“我的iframe\u布局”
选项不起作用。我尝试将
render\u with_scope
方法从
lib
模块文件中取出,并将其放入控制器中,但它在堆栈中创建了错误,导致服务器崩溃

我想我需要一个会话控制器方法,它看起来像这样:

    def new
    resource = build_resource
    clean_up_passwords(resource)
    #test whether the destination of this request is the bookmark action (mapped to /add_site)
    if after_sign_in_path_for(resource)[0..8] == '/add_site'
      respond_with_navigational(resource, stub_options(resource)){ render_with_scope :new }
  :layout => "bookmark_layout"    
    else
      respond_with_navigational(resource, stub_options(resource)){ render_with_scope :new }
    end
end

我想到的唯一一个方法是为我的“
书签”操作使用一种特殊的身份验证方法,该方法测试目标操作是什么,然后进行相应的身份验证,但这似乎不是很枯燥。

尝试使用自定义会话控制器并传递所需的布局

,因此完整的解决方案是采用
render_with_scopes
method从它的lib文件中取出,重命名它并将它放在应用程序控制器中(不像我以前那样放在会话控制器中)。方法中添加了一个
:layout=>“bookmark\u layout
选项

 def render_with_scope_bookmark(action, path=self.controller_path)
    if self.class.scoped_views?
      begin
        render :template => "#{devise_mapping.scoped_path}/#{path.split("/").last}/#{action}", :layout => 'bookmark_layout'
      rescue ActionView::MissingTemplate
        render :template => "#{path}/#{action}", :layout => 'bookmark_layout'
      end
    else
      render :template => "#{path}/#{action}", :layout => 'bookmark_layout'
    end
  end
然后,我修改了会话控制器,以便在我的bookmarklet访问
会话/new
操作时调用新的
render\u with_scopes\u bookmark
方法。当主站点访问操作时,将使用原始的
render\u with_scope
方法。我的bookmarklet总是点击“/add\u site”位置,所以为了测试,我使用
会话[:resource\u return\u to]
(在我的例子中,资源是用户)
存储位置
登录路径后
是检索请求的最终目的地,然后重置
会话[:resource\u return\u to]
变量的方法,因此这两种方法都不适合测试目的地

def new
    resource = build_resource
    clean_up_passwords(resource)
    @location = session[:user_return_to]
    if @location == nil
      respond_with_navigational(resource, stub_options(resource)){ render_with_scope :new }
    elsif @location[0..8] == '/add_site'
      respond_with_navigational(resource, stub_options(resource)){ render_with_scope_bookmark :new }
    else
      respond_with_navigational(resource, stub_options(resource)){ render_with_scope :new }
    end
  end

我的下一步将是修改
render\u with_scopes
方法以接受布局选项,这样我就不会有本质上相同方法的两个版本。

感谢您的回复。我已经创建了一个自定义会话控制器,但还没有找到一种方法来设置“新建”操作在渲染视图时的布局。上面的例子是我想做的,但实际上不起作用。我是否可以将布局选项传递到“respond_with_navigational…”行?要设置布局,请查看标题为“2.2.12.1基于每个控制器指定布局”的部分,这很好。现在,我可以为给定的操作设置布局,但我需要根据存储的\u位置或登录后的路径设置布局。如何从会话控制器或会话助手中执行此操作?您应该能够使用简单的
if
条件来查看属性(例如
存储位置
登录路径后
)并呈现适当的布局。