2016-04-29 61 views
2

我試圖將未登錄的用戶直接重定向到登錄窗口,這是一個引導模態窗口。Rails:重定向到調用Ajax

我在ApplicationController寫了一個稱爲logged_in_user方法:

def logged_in_user 
    unless !current_user.nil? 
    flash[:danger] = "Please log in" 
    redirect_to root_url 
    end 
end 

login_url路線sessions#new,我定義如下:

(sessions_controller.rb) 

def new 
    respond_to do |format| 
    format.html 
    format.js 
    end 
end 

這裏認爲,redirect_to root_url點:

<!-- Login Window --> 
    <div id="login-window" class="modal fade" role="dialog" aria-labelledby="login" aria-hidden="true"></div> 

這裏是new.js.erbsessions#new稱爲該被執行:

$("#login-window").html("<%= escape_javascript(render 'sessions/new') %>"); 

因此登錄表單,這是在app/views/sessions_new.html.erb,將顯示爲彈出窗口一旦sessions#new被調用。

除了它必須被處理爲JS而不是HTML。所以,我有下面的鏈接,這是在_header.html.erb和可用的所有意見,以確保這樣的話:

<%= link_to "Log in", login_path, {remote: true, 'data-toggle' => "modal", 'data-target' => '#login-window'} %> 

鏈接被點擊時,這工作得很好。這就是爲什麼我選擇做redirect_to root_url而不是redirect_to login_urllogged_in_user方法,因爲後一種方法導致「缺少模板錯誤」。

但我真正想要的是將用戶直接重定向到彈出窗口,而不是先將它們重定向到root_url,並且必須單擊「登錄」鏈接才能輸入表單。 換句話說,我需要一種方式來通過發出Ajax請求將用戶重定向到sessions#new,以便sessions#new可以作爲JS處理。

我試過logged_in_user方法中所希望的重定向下面的方法,其中沒有工作:

render js: "window.location = <%= escape_javascript(render 'sessions/new') %>" 

render js: "window.location = '/sessions/new'" 

redirect_to login_url, format: "js" 

任何建議,將不勝感激!

回答

1

只需添加通過修改下列文件這

<script type="text/javascript"> 
    $(document).ready(function() { 

    if(window.location.href.indexOf('#login-window') != -1) { 
    $('#login-window').modal('show'); 
    } 

}); 

</script> 

而且

redirect_to root_url+"#login-window" 
+0

謝謝你的回答。它很接近!雖然所需的視覺效果(即淡入淡出)是通過您的代碼實現的,但表單本身並未出現。 – Taiga

+0

什麼是點加載會話/新由'$(「#login-window」)。html(「<%= escape_javascript(render'sessions/new')%>」);'? 當數據是動態的時候使用ajax。你'會議/新'是動態的HTML?我想不是。 只需通過渲染加載html.erb。 表單必須出現,如果它的模態引導和沒有JS錯誤。 – cruncher

+0

那麼,這只是讓用戶「登錄」名爲「登錄」的鏈接。無論如何,這個問題是從你的建議中解決的。我會自己發佈答案。非常感謝您提出富有洞察力的建議! – Taiga

1

這個問題得到了解決:


application_controller.rb

def logged_in_user 
    unless !current_user.nil? 
    session[:modal] = true 
    redirect_to !request.referrer.nil? ? (request.referer + "#login-window") : "#login-window" 
    end 
end 

我省略了flash[:danger],因爲它顯示在「褪色的 」屏幕後面。我添加了request.referer以確保登錄彈出窗口出現在用戶發出請求的地方,而不是將它們重定向到root_path。我認爲這對用戶體驗會更好。 (該三元只是爲了處理request.referer可以是nil的情況,在這種情況下代碼發出錯誤。) session[:modal] = true背後的主題在下面解釋。


(在application.html.erb的底部)

<% if session[:modal] == true %> 
    <script type="text/javascript"> 
    $(document).ready(function() { 
     if(window.location.href.indexOf('#login-window') != -1) { 
     $('#login-window').modal('show'); 
     $("#login-window").html("<%= escape_javascript(render 'sessions/new') %>"); 
     } 
    }); 
    </script> 
    <% session[:modal] = false %> 
<% end %> 

在這裏,我直接使用視圖模板內的JavaScript。由於彈出窗口出現的視圖模板不限於一個特定的模板,因此我在application.html.erb內部使用了適用於所有視圖模板的腳本。它的前半部分受到cruncher的回答啓發。 (謝謝cruncher!)然後,我添加了$("#login-window").html("<%= escape_javascript(render 'sessions/new') %>");以確保登錄窗體(``app/views/sessions/_new.html.erb)確實出現。

現在,因爲我要顯示的登錄彈出窗口,只有當非登錄用戶試圖訪問需要登錄的網頁,我繼續加session[:modal] = true,表明logged_in_user方法確實叫,這意味着確實發生了上述情況。

然後,在application.html.erb裏面我可以檢查彈出窗口是否應該出現<% if session[:modal] == true %>。如果是這樣,那麼腳本將被執行,之後我將session[:modal]的值設置爲false

session[:modal]邏輯可能不是必要的(事實上,沒有它,它工作得很好),但我已經添加它以防萬一。


就是這樣:)

此外,對於那些你們誰想要實現自舉這個彈出窗口的功能,這裏是一個博客,我發現真正有用的:

https://coderwall.com/p/ej0mhg/open-a-rails-form-with-twitter-bootstrap-modals

快樂編碼!

+0

所以模式只顯示需要用戶登錄的頁面/鏈接是否打開? –

+0

在我的應用程序中,它也會在用戶單擊標題中的「登錄」鏈接時打開。 – Taiga

+0

如果在其瀏覽器上未啓用Java腳本,會發生什麼 –