8

Zastanawiam się, czy istnieje sposób nazywając „zapomniałem hasła” procedurę bez wymuszania moje użytkownikowi wylogowaćDevise Przypomnienie hasła dla zalogowanego użytkownika

przypadku biegnę na to: 1. użytkownik loguje się na facebooku, generowane jest fałszywe hasło 2. użytkownik następnie chce zmienić swój adres e-mail/nazwę/hasło, lub po prostu użyć logowania poza facebookiem

odkąd wymyślenie wymaga hasła do zmiany tych pól, tak jak powinien, użytkownik nie może ich zmodyfikować

Myślałem o tym, że nie po prostu forc Aby ustawić hasło, które ma być ustawione, ale nie ma sensu bezpieczeństwa, dlatego zamiast wyświetlać pola jako tekst i powiadamiać użytkownika, aby postępował zgodnie z procedurą "Nie pamiętam hasła" w celu ustawienia hasła, a następnie może zmienić pola

kwestia jest więc, że nie mogę po prostu odwołują się do tego z profilu użytkownika od Devise pokaże użytkownikowi, że nie można zrobić tego czasu już zalogowany.

Więc jest jakiś sposób przesłanianie zapomniałem hasła lub/users/password/edit method, aby zalogowany użytkownik mógł również wykonać tę akcję?

Odpowiedz

2

Moje kompletne rozwiązanie tutaj, ponieważ dowiedziałem się również, że użytkownik musiałby się wylogować po kliknięciu łącza w wiadomości e-mail, było dodanie niektórych dodatkowych akcji UserController do rzeczywistej edycji hasła, a także jego zapisania. Nie jest to idealne rozwiązanie, a przeziębienie powinno być wykonane w lepszy sposób, ale działa dla mnie.

kontroler użytkowników; dodane metody przeprowadzania resetowaniawidoki/devise/rejestracje/edycja; zmienił pogląd nie pozwolić polach edycyjnych użytkownika, które wymagają podania hasła

<%= form_for(resource, :as => resource_name, :url => registration_path(resource_name), :html => { :method => :put }) do |f| %> 
     <%= devise_error_messages! %> 

     <% if !resource.hasSetPassword %>           
      <%= f.label :name %><br /> 
      <p style="line-height:24px;"><b><%= @user.name %></b></p>    
      <div><%= f.label :email %><br /> 
       <p style="line-height:24px;"><b><%= @user.email %> </b></p> 
       <p style="position:relative; left:150px; width:420px;"> 
       <i>you cannot change any settings because you have not set a password <br />yet, you can do so by following the </i> 
       <%= link_to "Forgot your password", "https://stackoverflow.com/users/reset_password" %> <i> procedure</i> 
       </p> 
      </div> 
     <% else %>      
      <p><%= f.label :name %><br /> 
      <%= f.text_field :name %></p>   
      <div><%= f.label :email %><br /> 
      <%= f.email_field :email %></div> 

      <div><%= f.label :password %> <br /> 
      <%= f.password_field :password %><i>(leave blank if you don't want to change it)</i></div> 

      <div><%= f.label :password_confirmation %><br /> 
      <%= f.password_field :password_confirmation %></div> 

      <div><%= f.label :current_password %> <br /> 
      <%= f.password_field :current_password %> 
      <i>(we need your current password to confirm your changes)</i> 
      </div> 
     <div><%= f.submit "Update" %></div> 
     <% end %> 
    <% end %> 

views/opracować/Mailer/reset_password_instructions; musiał zmienić go zwrócić do właściwego adresu URL w naszym nowym przypadku

<p>Hello <%= @resource.email %>!</p> 

    <p>Someone has requested a link to change your password, and you can do this through the link below.</p> 

    <% if [email protected] %> 
     <p><%= link_to 'Change my password', 'http://streetsbehind.me/users/reset_password_edit?reset_password_token='[email protected]_password_token %></p> 
    <!-- todo: there's probably a better way of doing this than just hardcoding streetsbehind.me --> 
    <% else %> 
     <p><%= link_to 'Change my password', edit_password_url(@resource, :reset_password_token => @resource.reset_password_token) %></p> 
    <% end %> 
    <p>If you didn't request this, please ignore this email.</p> 
    <p>Your password won't change until you access the link above and create a new one.</p> 

views/users/reset_password_edit.erb

<%= form_for(@user, :url => url_for(:action => :do_reset_password) , :html => { :method => :post }) do |f| %> 

    <%= f.hidden_field :reset_password_token %> 

    <div><%= f.label :password, "New password" %><br /> 
    <%= f.password_field :password %></div> 

    <div><%= f.label :password_confirmation, "Confirm new password" %><br /> 
    <%= f.password_field :password_confirmation %></div> 

    <div><%= f.submit "Change my password" %></div> 
<% end %> 

config/routes.rb

get "users/reset_password" 
get "users/reset_password_edit" 

resource :users do 
    post 'do_reset_password' 
end 
4

Możesz użyć @user.send_reset_password_instructions, aby wygenerować token resetowania hasła i wysłać wiadomość e-mail. Jeśli po prostu bezpośrednio wywołasz program pocztowy, token resetowania hasła nie zostanie wygenerowany w celu uwierzytelnienia resetowania.

+0

To wyszło dużo lepiej. – fiestacasey

15

Dlatego, że nie możesz zresetować hasła, ponieważ program próbuje uwierzytelnić użytkownika przy bieżącej sesji, a po jego zakończeniu automatycznie przekierowywany jest na dowolną ścieżkę, do której ma przejść. Musisz zastąpić edycję i aktualizację akcji kontrolera haseł, aby pominąć ten krok.

Oto kod. W kontrolerze haseł dodaj następujące kody (możesz poprosić programistę, aby wygenerował dla ciebie kontrolery, lub możesz po prostu utworzyć następujący kontroler). Zastąpienie aktualizacji jest konieczne, ponieważ w przeciwnym razie zalogowany użytkownik zostanie automatycznie wylogowany po zresetowaniu hasła.(Lub jeśli ma to być tak można pozbyć się ręcznym #update)

class PasswordsController < Devise::PasswordsController 
    # here we need to skip the automatic authentication based on current session for the following two actions 
    # edit: shows the reset password form. need to skip, otherwise it will go directly to root 
    # update: updates the password, need to skip otherwise it won't even reset if already logged in 
    skip_before_filter :require_no_authentication, :only => [:edit, :update] 

    # we need to override the update, too. 
    # After a password is reset, all outstanding sessions are gone. 
    # When already logged in, sign_in is a no op, so the session will expire, too. 
    # The solution is to logout and then re-login which will make the session right. 
    def update 
    super 
    if resource.errors.empty? 
     sign_out(resource_name) 
     sign_in(resource_name, resource) 
    end 
    end 
end 

Trasy są jak następującej

# config/routes.rb 
devise_for :users, :controllers => {:passwords => 'passwords'} 
Powiązane problemy