2011-07-11 35 views
5

Tôi đang cố gắng bố cục ứng dụng Rails bằng Devise for authentication. Tôi muốn có trang đích ban đầu nơi mọi người có thể nhập địa chỉ email sau đó. Tôi muốn tạo một tài khoản ngay sau khi tôi nhận được địa chỉ email và sau đó cho phép người dùng hoàn tất quá trình xác thực sau này. Có một số tài liệu đó sẽ cho thấy làm thế nào để làm điều này?Phát sinh: Tạo Người dùng không có Mật khẩu, sau đó Yêu cầu Mật khẩu để Sử dụng Tài khoản?

Cảm ơn!

Trả lời

7

Tôi đã giải quyết điều này bằng cách sử dụng đá quý "devise_invitable". Điều duy nhất tôi phải mở rộng để làm việc này là đảm bảo rằng người dùng không cần phải được xác thực để gửi lời mời. Vượt quá giới hạn lời mời và nó hoạt động rất tốt:

class InvitationsController < Devise::InvitationsController 
    include Devise::Controllers::InternalHelpers 

    skip_filter :authenticate_inviter! 
    skip_filter :authenticate! 

    def current_inviter 
    @current_inviter ||= User.new(params[:user]) 
    end 
end 
3

Tôi không chắc liệu tài liệu hay về cách thực hiện điều này, nhưng sẽ không khó. Chỉ cần không yêu cầu xác thực trên trang đích của bạn hoặc trên bài đăng từ biểu mẫu đăng nhập trên trang đó. Thu thập địa chỉ email trong biểu mẫu đăng nhập. Gửi cho người dùng một thư đến địa chỉ họ đăng nhập. Trong email, bao gồm liên kết 'quên mật khẩu' (được đổi tên thành 'nhấp vào đây để đăng nhập' ... hoặc bất kỳ thứ gì) để buộc người dùng đăng nhập và chọn mật khẩu. Điều đó có hiệu quả với bạn hay tôi đã bỏ lỡ điều gì đó?

+0

Yup, đó là cơ bản những gì tôi đang cố gắng làm. Tôi sẽ thử nghiệm để xem cách hoạt động của nó. – spinlock

+0

chúc may mắn - Tôi đã thực hiện một cái gì đó như thế này và nó hoạt động tốt - giờ đi ngủ ở đây nhưng sẽ kiểm tra lại vào buổi sáng và cố gắng trả lời bất kỳ truy vấn nếu không ai khác chọn chúng – chrispanda

3

Tôi nhận ra điều này là muộn, nhưng điều này có thể hữu ích cho người khác. Tôi đã có một yêu cầu tương tự như bạn. Về cơ bản, tôi muốn người dùng nhập địa chỉ email và tiếp tục sử dụng với tư cách khách. Khi người dùng được thăng cấp thành người dùng 'thông thường', tôi bật lại xác thực mật khẩu. Đầu tiên, tôi tạo ra một chiến lược bảo vệ dựa trên đá quý devise-gullible. Tôi đã thực hiện một thay đổi phương pháp authenticate:

class Guest < Authenticatable 
    def authenticate! 
    resource = mapping.to.find_for_database_authentication(authentication_hash) 
    if resource 
     if resource.respond_to?(:guest?) and resource.guest? 
     success!(resource) 
     else 
     fail(:regular_user) 
     end 
    else 
     fail(:invalid) 
    end 
    end 
end 

tôi xác định một người dùng khách trong mô hình của tôi sử dụng như sau:

def guest? 
    self.roles.length == 0 
end 

Tôi đang sử dụng Cancan với devise và một HABTM để xử lý các vai trò. Hiện tại, tôi có người dùng 'thông thường' và người dùng 'quản trị'. Người dùng là khách nếu anh ấy chưa có vai trò được chỉ định nào.

Sau đó, bạn cần phải ghi đè bộ điều khiển đăng ký devise:

class Users::RegistrationsController < Devise::RegistrationsController 
    prepend_before_filter :allow_params_authentication!, :only => :create 

    def create 
    resource = warden.authenticate(:guest, 
            { scope: resource_name, 
            recall: "#{controller_path}#new" }) 
    if resource 
     set_flash_message(:notice, :signed_in) if is_navigational_format? 
     sign_in(resource_name, resource) 
     respond_with resource, :location => after_sign_in_path_for(resource) 
    elsif warden.winning_strategy.message == :regular_user 
     set_flash_message :notice, :regular_user if is_navigational_format? 
     redirect_to new_session_path(resource_name) 
    else 
     super 
    end 
    end 
end 

Lưu ý rằng ý tưởng là chúng tôi cố gắng để xác thực người dùng chạy các chiến lược của khách mà thôi. Nếu anh ta đã đăng ký với tư cách khách, chỉ cần đăng nhập anh ấy bình thường. Nếu chiến lược khách thất bại vì anh ta đã được đăng ký nhưng hiện là người dùng thông thường, hãy chuyển hướng đến trang đăng nhập thông thường.

Bây giờ, có thể tồn tại một số thông tin giới hạn mà tôi có thể muốn thu thập từ khách và không yêu cầu anh ta phải đăng ký đầy đủ. Tôi sử dụng kiểu người dùng bình thường:

class User < ActiveRecord::Base 
    devise :database_authenticatable, :registerable, :confirmable, 
    :recoverable, :rememberable, :trackable, :omniauthable, 
    :token_authenticatable 

    # Setup accessible (or protected) attributes for your model 
    attr_accessible :email, :password, :password_confirmation, :remember_me 

    has_and_belongs_to_many :roles 

    def self.new_with_session(params, session) 
    super.tap do |user| 
     if user.password.blank? 
     user.password = Devise.friendly_token[0,31] 
     # Also, we don't need to do email confirmation in this case. 
     # The user will have the guest role, and we'll do a confirmation 
     # when we promote him to a 'regular' user. 
     user.skip_confirmation! 
     end 
    end 
    end 

    def has_role?(role) 
    !!self.roles.find_by_name(role.to_s.camelize) 
    end 
end 

Lưu ý rằng tôi tự động tạo mật khẩu trong build_with_session. Bạn có thể gửi mã thông báo xác thực tại thời điểm bạn chọn và sau đó yêu cầu người dùng đặt mật khẩu mới tại thời điểm đó. Bạn cũng sẽ muốn sau đó thay đổi vai trò của mình để trở thành người dùng thông thường (hoặc làm bất cứ điều gì bạn muốn lưu ý anh ấy không còn là khách).

Dưới đây là một phần của tôi xuất hiện trên trang đầu:

<%= simple_form_for(resource, 
        as: resource_name, 
        url: user_registration_path, 
        defaults: { required: false }, 
        html: { class: 'well' }, 
        wrapper: :bootstrap, 
        validate: true) do |f| %> 
    <%= f.error_notification %> 
    <fieldset> 
    <legend>New here? Let's get started!</legend> 
    <%= f.input :email, placeholder: '[email protected]', validate: { uniqueness: false } %> 
    <%= f.button :submit, "Get my quote!", class: 'btn-primary' %> 
    </fieldset> 
<% end %> 

Vì vậy, hình thức này có chức năng như cả một đăng ký khách và mẫu đăng nhập.Chỉ nghĩ rằng tôi không thực sự quan tâm cho đến nay là bộ điều khiển đăng ký đang xử lý một xác thực, nhưng tôi đã không nhìn thấy một cách ngay lập tức xung quanh này.

Tôi đã triển khai chiến lược này trong thư mục lib cục bộ của mình. Đảm bảo đặt đường dẫn tải của bạn một cách thích hợp và thêm require 'devise_guest' vào config/initializers/devise.rb.

Các vấn đề liên quan