diff --git a/app/models/post.rb b/app/models/post.rb index a1174b078..3a1b372af 100644 --- a/app/models/post.rb +++ b/app/models/post.rb @@ -10,6 +10,32 @@ class Post < ActiveRecord::Base # also has_many notifications, but kinda meaningless to get at them # from this direction, so we won't set up an association for now. + after_create do + recipients = Array.new + sender = self.author.id + self.body.scan(Haml::Filters::GrowstuffMarkdown::MEMBER_REGEX) do |m| + # find member case-insensitively and add to list of recipients + member = Member.where('lower(login_name) = ?', $1.downcase).first + recipients << member if member and not recipients.include?(member) + end + self.body.scan(Haml::Filters::GrowstuffMarkdown::MEMBER_AT_REGEX) do |m| + # find member case-insensitively and add to list of recipients + member = Member.where('lower(login_name) = ?', $1[1..-1].downcase).first + recipients << member if member and not recipients.include?(member) + end + # don't send notifications to yourself + recipients.map{ |r| r.id }.each do |recipient| + if recipient != sender + Notification.create( + :recipient_id => recipient, + :sender_id => sender, + :subject => "#{self.author} mentioned you in their post #{self.subject}", + :body => self.body, + ) + end + end + end + default_scope { order("created_at desc") } validates :subject, diff --git a/spec/models/post_spec.rb b/spec/models/post_spec.rb index c56a5b301..61eb24bc1 100644 --- a/spec/models/post_spec.rb +++ b/spec/models/post_spec.rb @@ -96,6 +96,38 @@ describe Post do end end + context "notifications" do + let(:member2) { FactoryGirl.create(:member) } + + it "sends a notification when a member is mentioned" do + expect { + FactoryGirl.create(:post, :author => member, :body => "Hey @" << member2.login_name) + }.to change(Notification, :count).by(1) + end + + it "sets the notification field" do + @p = FactoryGirl.create(:post, :author => member, :body => "Hey @" << member2.login_name) + @n = Notification.first + @n.sender.should eq member + @n.recipient.should eq member2 + @n.subject.should match /mentioned you in their post/ + @n.body.should eq @p.body + end + + it "sends notifications to all members mentioned" do + @member3 = FactoryGirl.create(:member) + expect { + FactoryGirl.create(:post, :author => member, :body => "Hey @" << member2.login_name << " & @" << @member3.login_name) + }.to change(Notification, :count).by(2) + end + + it "doesn't send notifications if you mention yourself" do + expect { + FactoryGirl.create(:post, :author => member, :body => "@" << member.login_name) + }.to change(Notification, :count).by(0) + end + end + context "crop-post association" do let!(:tomato) { FactoryGirl.create(:tomato) } let!(:maize) { FactoryGirl.create(:maize) }