【问题标题】:Rails: Use URL Helper in ObserverRails:在 Observer 中使用 URL Helper
【发布时间】:2011-09-19 01:32:48
【问题描述】:

我有一个看起来像这样的观察者:

class CommentObserver < ActiveRecord::Observer
    include ActionView::Helpers::UrlHelper

    def after_create(comment)
        message = "#{link_to comment.user.full_name, user_path(comment.user)} commented on #{link_to 'your photo',photo_path(comment.photo)} of #{comment.photo.location(:min)}"
        Notification.create(:user=>comment.photo.user,:message=>message)
    end

end

基本上,我使用它所做的只是在有人对他们的一张照片发表评论时为某个用户创建一条简单的通知消息。

此操作失败并显示错误消息:

NoMethodError (undefined method `link_to' for #<CommentObserver:0x00000102fe9810>):

我原以为包含ActionView::Helpers::UrlHelper 会解决这个问题,但它似乎没有任何效果。

那么,我怎样才能在我的观察者中包含 URL 帮助程序,或者以其他方式呈现呢?我很乐意将“消息视图”移动到部分或其他内容中,但是观察者没有关联的视图可以将其移动到...

【问题讨论】:

    标签: ruby-on-rails ruby-on-rails-3 observer-pattern link-to url-helper


    【解决方案1】:

    当消息被渲染到页面时,你为什么不构建消息,然后使用类似的东西缓存它?

    <% cache do %>
      <%= render user.notifications %>
    <% end %>
    

    这将使您不必在观察者中进行破解,并且在 Rails 中会更加“符合标准”。

    【讨论】:

    • 这不一定要发送电子邮件。我正在尝试创建一个可用于创建通知的简单模型(例如当有人发布您的问题的答案时堆栈溢出的通知)。根据用户的设置,通知可以通过电子邮件发送消息或只是将其放在用户仪表板上。该观察者只是创建与正在创建的评论相关的通知消息。如果您对整个系统有更好的建议,请告诉我,今天这让我很生气,我还没有找到这种通知系统的好例子来研究。
    • ...嗯,我想你是在我评论之后才编辑的... :) 我以前从未使用过“缓存”——它是如何工作的?
    【解决方案2】:

    为了处理这种类型的事情,我制作了一个 AbstractController 来生成电子邮件的正文,然后将其作为变量传递给邮件程序类:

      class AbstractEmailController < AbstractController::Base
    
        include AbstractController::Rendering
        include AbstractController::Layouts
        include AbstractController::Helpers
        include AbstractController::Translation
        include AbstractController::AssetPaths
        include Rails.application.routes.url_helpers
        include ActionView::Helpers::AssetTagHelper
    
        # Uncomment if you want to use helpers 
        # defined in ApplicationHelper in your views
        # helper ApplicationHelper
    
        # Make sure your controller can find views
        self.view_paths = "app/views"
        self.assets_dir = '/app/public'
    
        # You can define custom helper methods to be used in views here
        # helper_method :current_admin
        # def current_admin; nil; end
    
        # for the requester to know that the acceptance email was sent
        def generate_comment_notification(comment, host = ENV['RAILS_SERVER'])
            render :partial => "photos/comment_notification", :locals => { :comment => comment, :host => host }
        end
      end
    

    在我的观察者中:

      def after_create(comment)
         email_body = AbstractEmailController.new.generate_comment_notification(comment)
         MyMailer.new(comment.id, email_body)
      end
    

    【讨论】:

      【解决方案3】:

      因此,事实证明这不能完成,原因与您不能在邮件视图中使用 link_to 相同。观察者没有关于当前请求的信息,因此不能使用链接助手。你必须以不同的方式来做。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2019-02-23
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2022-01-23
        • 1970-01-01
        • 2011-05-22
        • 1970-01-01
        相关资源
        最近更新 更多