2012-05-01 36 views
5

Tôi muốn mô-đun có thể thu hồi để gửi "mời" các email với các liên kết thiết lập lại mật khẩu cho người dùng của tôi (ứng dụng trên chỉ mời), tôi một phần tuyên bố phương pháp trong initializer:Làm thế nào để mở rộng chính xác Devise Recoverable?

module Devise 
    class Mailer 
    def invite_new_user(record) 
     devise_mail(record, :invitation_instructions) 
    end 
    end 
end 

module Devise 
    module Models 
    module Recoverable 
     def send_invite_user_instructions! 
     return unless status == User::STATUS_PENDING 
     generate_reset_password_token! 
     ::Devise.mailer.invite_new_user(self).deliver 
     end 
    end 
    end 
end 

Và thu hồi được mở rộng độc đáo, nhưng nó nói rằng bưu phẩm của tôi không có phương pháp invite_new_user (đường ray giao diện điều khiển đầu ra):

1.9.2p290 :002 > user.send_invite_user_instructions! 
    User Load (1.4ms) SELECT "users".* FROM "users" WHERE "users"."reset_password_token" = 'zMQK1CEXYupjNKpH8dph' LIMIT 1 
    (0.3ms) BEGIN 
    (15.0ms) UPDATE "users" SET "reset_password_token" = 'zMQK1CEXYupjNKpH8dph', "updated_at" = '2012-05-01 17:40:32.085256' WHERE "users"."id" = 59 
    (4.5ms) COMMIT 
NoMethodError: undefined method `invite_new_user' for Devise::Mailer:Class 

nhưng tính năng gọi có phương pháp trong phiên giao diện điều khiển giống nhau:

1.9.2p290 :003 > ::Devise.mailer.method_defined? 'invite_new_user' 
=> true 

Tôi đang thiếu gì?

+2

Có vẻ 'Devise.mailer' trả về' Devise :: Mailer', là một lớp, không phải là một thể hiện. Do đó, bạn nên định nghĩa 'invite_new_user' là' self.invite_new_user'. – Casper

+0

Cảm ơn gợi ý, điều đó khiến tôi suy nghĩ. Dường như phương thức này hoạt động tốt trong khi truy cập từ các bộ điều khiển, nhưng khi chỉ tải mô hình trong giao diện điều khiển - nó có vẻ trả về lớp thay vì đối tượng như bạn đã nói. – meta

Trả lời

2

lập mưu có thể được thiết lập cho những gì bạn cần:

1- Tạo một lớp Mailer trong app/bưu phẩm/file auth_mailer.rb và làm cho nó kế thừa từ Devise::Mailer

class AuthMailer < Devise::Mailer 
    def invite_new_user(record) 
    devise_mail(record, :invitation_instructions) 
    end 
end 

2- Hướng dẫn Phát triển để sử dụng lớp học của bạn bằng cách chỉnh sửa tệp config/initializers/devise.rb và thêm

config.mailer = 'AuthMailer' 

3- (không bắt buộc) Nếu (và chỉ nếu) bạn sử dụng một email chậm trễ gửi như SideKiq hoặc DelayedJob bạn có thể cần phải tải háo hức trong việc phát triển, hoặc công việc trì hoãn có thể không tìm thấy lớp AuthMailer của bạn. Trong config/môi trường/development.rb

config.eager_load = true 

4- Cá nhân tôi sẽ xác định phương pháp send_invite_user_instructions! bạn trong lớp User của tôi thay vì vá Vạch lớp


Side lưu ý: Tôi không phải là fan lớn hoặc thực hiện khai báo một phần của class trong Rails initializer, bởi vì tùy thuộc vào cách gem được thiết kế, bạn có thể gặp vấn đề với autoload: Có một gem (Monologue) tải lại các đối tượng trong thời gian chạy, mà không cần chạy initializers, khỉ vá hoạt động tốt trên các cuộc gọi đầu tiên, nhưng không phải trên cuộc gọi tiếp theo.

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