##// END OF EJS Templates
Adds watch/unwatch functionality at forum topic level (#1912)....
Jean-Philippe Lang -
r1876:16e09bfd7744
parent child
Show More
@@ -0,0 +1,14
1 class SetTopicAuthorsAsWatchers < ActiveRecord::Migration
2 def self.up
3 # Sets active users who created/replied a topic as watchers of the topic
4 # so that the new watch functionality at topic level doesn't affect notifications behaviour
5 Message.connection.execute("INSERT INTO watchers (watchable_type, watchable_id, user_id)" +
6 " SELECT DISTINCT 'Message', COALESCE(messages.parent_id, messages.id), messages.author_id FROM messages, users" +
7 " WHERE messages.author_id = users.id AND users.status = 1")
8 end
9
10 def self.down
11 # Removes all message watchers
12 Watcher.delete_all("watchable_type = 'Message'")
13 end
14 end
@@ -24,7 +24,7 class MessagesController < ApplicationController
24 24 verify :method => :post, :only => [ :reply, :destroy ], :redirect_to => { :action => :show }
25 25 verify :xhr => true, :only => :quote
26 26
27
27 helper :watchers
28 28 helper :attachments
29 29 include AttachmentsHelper
30 30
@@ -33,11 +33,14 class Message < ActiveRecord::Base
33 33 {:id => o.parent_id, :anchor => "message-#{o.id}"})}
34 34
35 35 acts_as_activity_provider :find_options => {:include => [{:board => :project}, :author]}
36 acts_as_watchable
36 37
37 38 attr_protected :locked, :sticky
38 39 validates_presence_of :subject, :content
39 40 validates_length_of :subject, :maximum => 255
40 41
42 after_create :add_author_as_watcher
43
41 44 def validate_on_create
42 45 # Can not reply to a locked topic
43 46 errors.add_to_base 'Topic is locked' if root.locked? && self != root
@@ -68,4 +71,10 class Message < ActiveRecord::Base
68 71 def project
69 72 board.project
70 73 end
74
75 private
76
77 def add_author_as_watcher
78 Watcher.create(:watchable => self.root, :user => author)
79 end
71 80 end
@@ -17,8 +17,9
17 17
18 18 class MessageObserver < ActiveRecord::Observer
19 19 def after_create(message)
20 # send notification to the authors of the thread
21 recipients = ([message.root] + message.root.children).collect {|m| m.author.mail if m.author && m.author.active?}
20 recipients = []
21 # send notification to the topic watchers
22 recipients += message.root.watcher_recipients
22 23 # send notification to the board watchers
23 24 recipients += message.board.watcher_recipients
24 25 # send notification to project members who want to be notified
@@ -2,6 +2,7
2 2 link_to(h(@board.name), {:controller => 'boards', :action => 'show', :project_id => @project, :id => @board}) %>
3 3
4 4 <div class="contextual">
5 <%= watcher_tag(@topic, User.current) %>
5 6 <%= link_to_remote_if_authorized l(:button_quote), { :url => {:action => 'quote', :id => @topic} }, :class => 'icon icon-comment' %>
6 7 <%= link_to_if_authorized l(:button_edit), {:action => 'edit', :id => @topic}, :class => 'icon icon-edit' %>
7 8 <%= link_to_if_authorized l(:button_delete), {:action => 'destroy', :id => @topic}, :method => :post, :confirm => l(:text_are_you_sure), :class => 'icon icon-del' %>
@@ -3,4 +3,8 watchers_001:
3 3 watchable_type: Issue
4 4 watchable_id: 2
5 5 user_id: 3
6 watchers_002:
7 watchable_type: Message
8 watchable_id: 1
9 user_id: 1
6 10 No newline at end of file
@@ -1,7 +1,7
1 1 require File.dirname(__FILE__) + '/../test_helper'
2 2
3 3 class MessageTest < Test::Unit::TestCase
4 fixtures :projects, :boards, :messages
4 fixtures :projects, :boards, :messages, :users, :watchers
5 5
6 6 def setup
7 7 @board = Board.find(1)
@@ -20,6 +20,8 class MessageTest < Test::Unit::TestCase
20 20 # messages count incremented
21 21 assert_equal messages_count+1, @board[:messages_count]
22 22 assert_equal message, @board.last_message
23 # author should be watching the message
24 assert message.watched_by?(@user)
23 25 end
24 26
25 27 def test_reply
@@ -28,7 +30,8 class MessageTest < Test::Unit::TestCase
28 30 @message = Message.find(1)
29 31 replies_count = @message.replies_count
30 32
31 reply = Message.new(:board => @board, :subject => 'Test reply', :content => 'Test reply content', :parent => @message, :author => @user)
33 reply_author = User.find(2)
34 reply = Message.new(:board => @board, :subject => 'Test reply', :content => 'Test reply content', :parent => @message, :author => reply_author)
32 35 assert reply.save
33 36 @board.reload
34 37 # same topics count
@@ -40,13 +43,18 class MessageTest < Test::Unit::TestCase
40 43 # replies count incremented
41 44 assert_equal replies_count+1, @message[:replies_count]
42 45 assert_equal reply, @message.last_reply
46 # author should be watching the message
47 assert @message.watched_by?(reply_author)
43 48 end
44 49
45 50 def test_destroy_topic
46 51 message = Message.find(1)
47 52 board = message.board
48 53 topics_count, messages_count = board.topics_count, board.messages_count
49 assert message.destroy
54
55 assert_difference('Watcher.count', -1) do
56 assert message.destroy
57 end
50 58 board.reload
51 59
52 60 # Replies deleted
@@ -54,6 +62,7 class MessageTest < Test::Unit::TestCase
54 62 # Checks counters
55 63 assert_equal topics_count - 1, board.topics_count
56 64 assert_equal messages_count - 3, board.messages_count
65 # Watchers removed
57 66 end
58 67
59 68 def test_destroy_reply
General Comments 0
You need to be logged in to leave comments. Login now