commontator 4.5.4 → 4.6.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (141) hide show
  1. checksums.yaml +5 -13
  2. data/MIT-LICENSE +2 -1
  3. data/README.md +31 -34
  4. data/Rakefile +3 -2
  5. data/app/assets/stylesheets/commontator/application.css +1 -0
  6. data/app/assets/stylesheets/commontator/comments.css +1 -0
  7. data/app/assets/stylesheets/commontator/threads.css +13 -7
  8. data/{spec/dummy/tmp/cache/assets/test/sprockets/a473b3873e554893372a53d71f5e9879 → app/assets/stylesheets/commontator/threads.css~} +0 -0
  9. data/app/controllers/commontator/application_controller.rb +14 -14
  10. data/app/controllers/commontator/application_controller.rb~ +35 -0
  11. data/app/controllers/commontator/comments_controller.rb +8 -7
  12. data/app/controllers/commontator/comments_controller.rb~ +153 -0
  13. data/app/controllers/commontator/subscriptions_controller.rb +1 -0
  14. data/app/controllers/commontator/threads_controller.rb +7 -2
  15. data/app/helpers/commontator/application_helper.rb +1 -0
  16. data/app/mailers/commontator/subscriptions_mailer.rb +8 -10
  17. data/app/mailers/commontator/subscriptions_mailer.rb~ +44 -0
  18. data/app/models/commontator/comment.rb +14 -13
  19. data/app/models/commontator/comment.rb~ +119 -0
  20. data/app/models/commontator/subscription.rb +8 -4
  21. data/app/models/commontator/thread.rb +64 -43
  22. data/app/models/commontator/thread.rb~ +159 -0
  23. data/app/views/commontator/comments/_actions.html.erb +1 -0
  24. data/app/views/commontator/comments/_body.html.erb +2 -1
  25. data/app/views/commontator/comments/_form.html.erb +5 -1
  26. data/app/views/commontator/comments/_form.html.erb~ +39 -0
  27. data/app/views/commontator/comments/_list.html.erb +1 -1
  28. data/app/views/commontator/comments/_show.html.erb +5 -3
  29. data/app/views/commontator/comments/_show.html.erb~ +49 -0
  30. data/app/views/commontator/comments/_votes.html.erb +2 -1
  31. data/app/views/commontator/comments/_votes.html.erb~ +69 -0
  32. data/app/views/commontator/comments/cancel.js.erb +1 -0
  33. data/app/views/commontator/comments/create.js.erb +6 -4
  34. data/app/views/commontator/comments/create.js.erb~ +14 -0
  35. data/app/views/commontator/comments/delete.js.erb +1 -0
  36. data/app/views/commontator/comments/edit.js.erb +1 -0
  37. data/app/views/commontator/comments/new.js.erb +3 -1
  38. data/app/views/commontator/comments/new.js.erb~ +13 -0
  39. data/app/views/commontator/comments/update.js.erb +1 -0
  40. data/app/views/commontator/comments/vote.js.erb +1 -0
  41. data/app/views/commontator/shared/_thread.html.erb +4 -5
  42. data/app/views/commontator/subscriptions/_link.html.erb +2 -1
  43. data/app/views/commontator/subscriptions/_link.html.erb~ +16 -0
  44. data/app/views/commontator/subscriptions/subscribe.js.erb +1 -0
  45. data/app/views/commontator/subscriptions_mailer/comment_created.html.erb +1 -0
  46. data/app/views/commontator/threads/_reply.html.erb +4 -2
  47. data/app/views/commontator/threads/_reply.html.erb~ +19 -0
  48. data/app/views/commontator/threads/_show.html.erb +44 -9
  49. data/app/views/commontator/threads/_show.html.erb~ +95 -0
  50. data/app/views/commontator/threads/_show.js.erb +19 -0
  51. data/app/views/commontator/threads/show.js.erb +4 -4
  52. data/config/initializers/commontator.rb +169 -132
  53. data/config/initializers/commontator.rb~ +238 -0
  54. data/config/locales/commontator/en.yml +12 -3
  55. data/config/locales/commontator/en.yml~ +104 -0
  56. data/config/routes.rb +1 -0
  57. data/db/migrate/0_install_commontator.rb +9 -11
  58. data/db/migrate/0_install_commontator.rb~ +54 -0
  59. data/lib/commontator.rb +57 -16
  60. data/lib/commontator.rb~ +142 -0
  61. data/lib/commontator/acts_as_commontable.rb +12 -14
  62. data/lib/commontator/acts_as_commontator.rb +1 -16
  63. data/lib/commontator/commontable_config.rb +1 -0
  64. data/lib/commontator/commontator_config.rb +1 -0
  65. data/lib/commontator/controller_includes.rb +3 -3
  66. data/lib/commontator/engine.rb +1 -0
  67. data/lib/commontator/link_renderer.rb +29 -0
  68. data/lib/commontator/security_transgression.rb +1 -0
  69. data/lib/commontator/shared_helper.rb +7 -5
  70. data/lib/commontator/version.rb +2 -1
  71. data/lib/tasks/commontator_tasks.rake +1 -0
  72. data/spec/app/controllers/commontator/comments_controller_spec.rb +12 -11
  73. data/spec/app/controllers/commontator/subscriptions_controller_spec.rb +2 -1
  74. data/spec/app/controllers/commontator/threads_controller_spec.rb +2 -1
  75. data/spec/app/helpers/commontator/application_helper_spec.rb +2 -1
  76. data/spec/app/mailers/commontator/subscriptions_mailer_spec.rb +2 -1
  77. data/spec/app/models/commontator/comment_spec.rb +18 -11
  78. data/spec/app/models/commontator/comment_spec.rb~ +74 -0
  79. data/spec/app/models/commontator/subscription_spec.rb +18 -8
  80. data/spec/app/models/commontator/thread_spec.rb +28 -42
  81. data/spec/dummy/README.md +1 -0
  82. data/spec/dummy/Rakefile +1 -0
  83. data/spec/dummy/app/assets/javascripts/application.js +1 -0
  84. data/spec/dummy/app/assets/stylesheets/application.css +1 -0
  85. data/spec/dummy/app/controllers/application_controller.rb +1 -0
  86. data/spec/dummy/app/controllers/dummy_models_controller.rb +1 -0
  87. data/spec/dummy/app/helpers/application_helper.rb +1 -0
  88. data/spec/dummy/app/models/dummy_model.rb +1 -0
  89. data/spec/dummy/app/models/dummy_user.rb +7 -2
  90. data/spec/dummy/app/models/dummy_user.rb~ +16 -0
  91. data/spec/dummy/app/views/dummy_model/show.html.erb +1 -0
  92. data/spec/dummy/app/views/layouts/application.html.erb +1 -0
  93. data/spec/dummy/config.ru +1 -0
  94. data/spec/dummy/config/boot.rb +1 -0
  95. data/spec/dummy/config/database.yml +1 -0
  96. data/spec/dummy/config/environment.rb +1 -0
  97. data/spec/dummy/config/environments/development.rb +1 -0
  98. data/spec/dummy/config/environments/production.rb +1 -0
  99. data/spec/dummy/config/environments/test.rb +1 -0
  100. data/spec/dummy/config/initializers/backtrace_silencers.rb +1 -0
  101. data/spec/dummy/config/initializers/commontator.rb +6 -1
  102. data/spec/dummy/config/initializers/commontator.rb~ +15 -0
  103. data/spec/dummy/config/initializers/filter_parameter_logging.rb +1 -0
  104. data/spec/dummy/config/initializers/inflections.rb +1 -0
  105. data/spec/dummy/config/initializers/mime_types.rb +1 -0
  106. data/spec/dummy/config/initializers/secret_token.rb +1 -0
  107. data/spec/dummy/config/initializers/session_store.rb +1 -0
  108. data/spec/dummy/config/initializers/wrap_parameters.rb +1 -0
  109. data/spec/dummy/config/routes.rb +1 -0
  110. data/spec/dummy/db/development.sqlite3 +0 -0
  111. data/spec/dummy/db/migrate/1_create_dummy_models.rb +1 -0
  112. data/spec/dummy/db/migrate/2_create_dummy_users.rb +1 -0
  113. data/spec/dummy/db/migrate/3_acts_as_votable_migration.rb +1 -0
  114. data/spec/dummy/db/schema.rb +10 -13
  115. data/spec/dummy/db/test.sqlite3 +0 -0
  116. data/spec/dummy/public/404.html +1 -0
  117. data/spec/dummy/public/422.html +1 -0
  118. data/spec/dummy/public/500.html +1 -0
  119. data/spec/dummy/script/rails +1 -0
  120. data/spec/dummy/tmp/cache/assets/test/sprockets/{72b63dddbc5c995f79af8e3c94904fd9 → 02d4b791eb831cf2057bf4703a1218d1} +0 -0
  121. data/spec/dummy/tmp/cache/assets/test/sprockets/{a77b1a9223d168112e1705c29220116f → 0f196a1a50363b0a076ec6e1ee5417f6} +0 -0
  122. data/spec/dummy/tmp/cache/assets/test/sprockets/a3fb9025f90ff05a6fd4afc7ded2692c +0 -0
  123. data/spec/dummy/tmp/cache/assets/test/sprockets/a41c8be5379abec3c0d0d98e2f0d5609 +0 -0
  124. data/spec/dummy/tmp/cache/assets/test/sprockets/c69ee3cc5796188d873574179290a6ef +0 -0
  125. data/spec/dummy/tmp/cache/assets/test/sprockets/{f721383d531f067d82b071e14aed7a92 → e1f674c11941d62aac1764ef3a7134e4} +0 -0
  126. data/spec/dummy/tmp/cache/assets/test/sprockets/{d2244ccef8e05bb993f75715af0344cc → e85565206c3e5fdf9dfeb367c85557b1} +0 -0
  127. data/spec/lib/commontator/acts_as_commontable_spec.rb +3 -2
  128. data/spec/lib/commontator/acts_as_commontator_spec.rb +2 -5
  129. data/spec/lib/commontator/commontable_config_spec.rb +8 -5
  130. data/spec/lib/commontator/commontator_config_spec.rb +2 -1
  131. data/spec/lib/commontator/controller_includes_spec.rb +2 -1
  132. data/spec/lib/commontator/shared_helper_spec.rb +2 -1
  133. data/spec/lib/commontator_spec.rb +2 -1
  134. data/spec/{test_helper.rb → spec_helper.rb} +0 -0
  135. metadata +154 -135
  136. data/lib/commontator/remote_link_renderer.rb +0 -10
  137. data/spec/dummy/config/locales/en.yml +0 -23
  138. data/spec/dummy/log/development.log +0 -36
  139. data/spec/dummy/log/test.log +0 -22683
  140. data/spec/dummy/tmp/cache/assets/test/sprockets/afa63eb365bdf4f42584b17ac9176b9d +0 -0
  141. data/spec/dummy/tmp/cache/assets/test/sprockets/decb63cac838a5314aa0c22a979f5ac9 +0 -0
@@ -30,3 +30,4 @@ module Commontator
30
30
  end
31
31
  end
32
32
  end
33
+
@@ -3,14 +3,14 @@ module Commontator
3
3
  skip_before_filter :ensure_user, :only => :show
4
4
 
5
5
  before_filter :get_thread
6
- before_filter :set_commontable_url, :only => :show
7
6
 
8
7
  # GET /threads/1
9
8
  def show
10
9
  commontator_thread_show(@thread.commontable)
10
+ @show_all = params[:show_all] && @thread.can_be_edited_by?(@user)
11
11
 
12
12
  respond_to do |format|
13
- format.html { redirect_to commontable_url }
13
+ format.html { redirect_to main_app.polymorphic_path(@thread.commontable) }
14
14
  format.js
15
15
  end
16
16
  end
@@ -22,6 +22,8 @@ module Commontator
22
22
  @thread.errors.add(:base, t('commontator.thread.errors.already_closed')) \
23
23
  unless @thread.close(@user)
24
24
 
25
+ @show_all = true
26
+
25
27
  respond_to do |format|
26
28
  format.html { redirect_to @thread }
27
29
  format.js { render :show }
@@ -35,6 +37,8 @@ module Commontator
35
37
  @thread.errors.add(:base, t('commontator.thread.errors.not_closed')) \
36
38
  unless @thread.reopen
37
39
 
40
+ @show_all = true
41
+
38
42
  respond_to do |format|
39
43
  format.html { redirect_to @thread }
40
44
  format.js { render :show }
@@ -42,3 +46,4 @@ module Commontator
42
46
  end
43
47
  end
44
48
  end
49
+
@@ -5,3 +5,4 @@ module Commontator
5
5
  end
6
6
  end
7
7
  end
8
+
@@ -19,28 +19,26 @@ module Commontator
19
19
  @thread = @comment.thread
20
20
  @creator = @comment.creator
21
21
 
22
- @commontable = @thread.commontable
23
- @config = @thread.config
22
+ @creator_name = Commontator.commontator_name(@creator)
24
23
 
25
- @creator_name = @creator.commontator_name
24
+ @commontable_name = Commontator.commontable_name(@thread)
26
25
 
27
- @commontable_name = @commontable.commontable_name
28
-
29
- @commontable_url = ApplicationController.commontable_url
26
+ @commontable_url = Commontator.commontable_url(@thread)
30
27
 
31
28
  params = Hash.new
32
29
  params[:comment] = @comment
33
30
  params[:thread] = @thread
34
31
  params[:creator] = @creator
35
- params[:commontable] = @commontable
36
- params[:config] = @config
37
32
  params[:creator_name] = @creator_name
38
33
  params[:commontable_name] = @commontable_name
39
34
  params[:commontable_url] = @commontable_url
40
35
 
41
36
  @to = t('commontator.email.undisclosed_recipients')
42
- @bcc = recipients.collect{|s| s.commontator_email(self)}
43
- @from = @config.email_from_proc.call(self)
37
+ @bcc = recipients.collect{|s| Commontator.commontator_email(s, self)}
38
+ @from = @thread.config.email_from_proc.call(@thread)
44
39
  end
40
+
41
+
45
42
  end
46
43
  end
44
+
@@ -0,0 +1,44 @@
1
+ module Commontator
2
+ class SubscriptionsMailer < ActionMailer::Base
3
+ def comment_created(comment, recipients)
4
+ setup_variables(comment, recipients)
5
+
6
+ mail :to => @to,
7
+ :bcc => @bcc,
8
+ :from => @from,
9
+ :subject => t('commontator.email.comment_created.subject',
10
+ :creator_name => @creator_name,
11
+ :commontable_name => @commontable_name,
12
+ :commontable_url => @commontable_url)
13
+ end
14
+
15
+ protected
16
+
17
+ def setup_variables(comment, recipients)
18
+ @comment = comment
19
+ @thread = @comment.thread
20
+ @creator = @comment.creator
21
+
22
+ @creator_name = Commontator.commontator_name(@creator)
23
+
24
+ @commontable_name = Commontator.commontable_name(@thread)
25
+
26
+ @commontable_url = Commontator.commontable_url(@thread)
27
+
28
+ params = Hash.new
29
+ params[:comment] = @comment
30
+ params[:thread] = @thread
31
+ params[:creator] = @creator
32
+ params[:creator_name] = @creator_name
33
+ params[:commontable_name] = @commontable_name
34
+ params[:commontable_url] = @commontable_url
35
+
36
+ @to = t('commontator.email.undisclosed_recipients')
37
+ @bcc = recipients.collect{|s| Commontator.commontator_email(s, self)}
38
+ @from = @config.email_from_proc.call(@thread)
39
+ end
40
+
41
+
42
+ end
43
+ end
44
+
@@ -41,6 +41,11 @@ module Commontator
41
41
  votes.where(:voter_type => user.class.name, :voter_id => user.id).first
42
42
  end
43
43
 
44
+ def update_cached_votes(vote_scope = nil)
45
+ self.update_column(:cached_votes_up, count_votes_up(true))
46
+ self.update_column(:cached_votes_down, count_votes_down(true))
47
+ end
48
+
44
49
  def is_deleted?
45
50
  !deleted_at.blank?
46
51
  end
@@ -65,10 +70,8 @@ module Commontator
65
70
  end
66
71
 
67
72
  def updated_timestamp
68
- return '' if editor.nil?
69
-
70
73
  I18n.t 'commontator.comment.status.updated_at',
71
- :editor_name => editor.commontator_name,
74
+ :editor_name => Commontator.commontator_name(editor || creator),
72
75
  :updated_at => I18n.l(updated_at, :format => :commontator)
73
76
  end
74
77
 
@@ -76,20 +79,14 @@ module Commontator
76
79
  # Access Control #
77
80
  ##################
78
81
 
79
- def can_be_read_by?(user)
80
- return true if thread.can_be_edited_by?(user)
81
- (!is_deleted? || !thread.config.hide_deleted_comments) &&\
82
- thread.can_be_read_by?(user)
83
- end
84
-
85
82
  def can_be_created_by?(user)
86
83
  user == creator && user.is_commontator &&\
87
84
  !thread.is_closed? && thread.can_be_read_by?(user)
88
85
  end
89
86
 
90
87
  def can_be_edited_by?(user)
91
- return true if thread.config.moderators_can_edit_comments &&\
92
- thread.can_be_edited_by?(user)
88
+ return true if thread.can_be_edited_by?(user) &&\
89
+ thread.config.moderator_permissions.to_sym == :e
93
90
  comment_edit = thread.config.comment_editing.to_sym
94
91
  !thread.is_closed? && !is_deleted? && user == creator &&\
95
92
  comment_edit != :n && (is_latest? || comment_edit == :a) &&\
@@ -97,7 +94,10 @@ module Commontator
97
94
  end
98
95
 
99
96
  def can_be_deleted_by?(user)
100
- return true if thread.can_be_edited_by?(user)
97
+ mod_perm = thread.config.moderator_permissions.to_sym
98
+ return true if thread.can_be_edited_by?(user) &&\
99
+ (mod_perm == :e ||\
100
+ mod_perm == :d)
101
101
  comment_del = thread.config.comment_deletion.to_sym
102
102
  !thread.is_closed? && (!is_deleted? || editor == user) &&\
103
103
  user == creator && comment_del != :n &&\
@@ -107,7 +107,7 @@ module Commontator
107
107
 
108
108
  def can_be_voted_on?
109
109
  !thread.is_closed? && !is_deleted? &&\
110
- thread.config.comment_voting != :n && is_votable?
110
+ thread.config.comment_voting.to_sym != :n && is_votable?
111
111
  end
112
112
 
113
113
  def can_be_voted_on_by?(user)
@@ -116,3 +116,4 @@ module Commontator
116
116
  end
117
117
  end
118
118
  end
119
+
@@ -0,0 +1,119 @@
1
+ module Commontator
2
+ class Comment < ActiveRecord::Base
3
+ belongs_to :creator, :polymorphic => true
4
+ belongs_to :editor, :polymorphic => true
5
+ belongs_to :thread
6
+
7
+ has_one :commontable, :through => :thread
8
+
9
+ validates_presence_of :creator, :on => :create
10
+ validates_presence_of :editor, :on => :update
11
+ validates_presence_of :thread
12
+ validates_presence_of :body
13
+
14
+ validates_uniqueness_of :body,
15
+ :scope => [:creator_type, :creator_id, :thread_id],
16
+ :message => I18n.t('commontator.comment.errors.double_posted')
17
+
18
+ protected
19
+
20
+ cattr_accessor :acts_as_votable_initialized
21
+
22
+ public
23
+
24
+ def is_modified?
25
+ !editor.nil?
26
+ end
27
+
28
+ def is_latest?
29
+ thread.comments.last == self
30
+ end
31
+
32
+ def is_votable?
33
+ return true if acts_as_votable_initialized
34
+ return false unless self.class.respond_to?(:acts_as_votable)
35
+ self.class.acts_as_votable
36
+ self.class.acts_as_votable_initialized = true
37
+ end
38
+
39
+ def get_vote_by(user)
40
+ return nil unless is_votable? && user && user.is_commontator
41
+ votes.where(:voter_type => user.class.name, :voter_id => user.id).first
42
+ end
43
+
44
+ def update_cached_votes(vote_scope = nil)
45
+ self.update_column(:cached_votes_up, count_votes_up(true)
46
+ self.update_column(:cached_votes_down, count_votes_down(true)
47
+ end
48
+
49
+ def is_deleted?
50
+ !deleted_at.blank?
51
+ end
52
+
53
+ def delete_by(user)
54
+ return false if is_deleted?
55
+ self.deleted_at = Time.now
56
+ self.editor = user
57
+ self.save
58
+ end
59
+
60
+ def undelete_by(user)
61
+ return false unless is_deleted?
62
+ self.deleted_at = nil
63
+ self.editor = user
64
+ self.save
65
+ end
66
+
67
+ def created_timestamp
68
+ I18n.t 'commontator.comment.status.created_at',
69
+ :created_at => I18n.l(created_at, :format => :commontator)
70
+ end
71
+
72
+ def updated_timestamp
73
+ I18n.t 'commontator.comment.status.updated_at',
74
+ :editor_name => Commontator.commontator_name(editor || creator),
75
+ :updated_at => I18n.l(updated_at, :format => :commontator)
76
+ end
77
+
78
+ ##################
79
+ # Access Control #
80
+ ##################
81
+
82
+ def can_be_created_by?(user)
83
+ user == creator && user.is_commontator &&\
84
+ !thread.is_closed? && thread.can_be_read_by?(user)
85
+ end
86
+
87
+ def can_be_edited_by?(user)
88
+ return true if thread.can_be_edited_by?(user) &&\
89
+ thread.config.moderator_permissions.to_sym == :e
90
+ comment_edit = thread.config.comment_editing.to_sym
91
+ !thread.is_closed? && !is_deleted? && user == creator &&\
92
+ comment_edit != :n && (is_latest? || comment_edit == :a) &&\
93
+ thread.can_be_read_by?(user)
94
+ end
95
+
96
+ def can_be_deleted_by?(user)
97
+ mod_perm = thread.config.moderator_permissions.to_sym
98
+ return true if thread.can_be_edited_by?(user) &&\
99
+ (mod_perm == :e ||\
100
+ mod_perm == :d)
101
+ comment_del = thread.config.comment_deletion.to_sym
102
+ !thread.is_closed? && (!is_deleted? || editor == user) &&\
103
+ user == creator && comment_del != :n &&\
104
+ (is_latest? || comment_del == :a) &&\
105
+ thread.can_be_read_by?(user)
106
+ end
107
+
108
+ def can_be_voted_on?
109
+ !thread.is_closed? && !is_deleted? &&\
110
+ thread.config.comment_voting.to_sym != :n && is_votable?
111
+ end
112
+
113
+ def can_be_voted_on_by?(user)
114
+ !user.nil? && user.is_commontator && user != creator &&\
115
+ thread.can_be_read_by?(user) && can_be_voted_on?
116
+ end
117
+ end
118
+ end
119
+
@@ -6,12 +6,16 @@ module Commontator
6
6
  validates_presence_of :subscriber, :thread
7
7
  validates_uniqueness_of :thread_id, :scope => [:subscriber_type, :subscriber_id]
8
8
 
9
- def mark_as_read
10
- update_attribute(:unread, 0)
9
+ def self.comment_created(comment)
10
+ recipients = comment.thread.subscribers.reject{|s| s == comment.creator}
11
+ SubscriptionsMailer.comment_created(comment, recipients).deliver \
12
+ unless recipients.empty?
11
13
  end
12
14
 
13
- def add_unread
14
- update_attribute(:unread, unread + 1)
15
+ def unread_comments
16
+ created_at = Comment.arel_table[:created_at]
17
+ thread.filtered_comments.where(created_at.gt(updated_at))
15
18
  end
16
19
  end
17
20
  end
21
+
@@ -12,34 +12,78 @@ module Commontator
12
12
  :allow_nil => true
13
13
 
14
14
  def config
15
- commontable.try(:commontable_config) || Commontator
15
+ @config ||= commontable.try(:commontable_config) || Commontator
16
16
  end
17
17
 
18
18
  def will_paginate?
19
19
  return false if config.comments_per_page.nil? || !comments.respond_to?(:paginate)
20
- require 'commontator/remote_link_renderer'
20
+ require 'commontator/link_renderer'
21
21
  true
22
22
  end
23
23
 
24
- def ordered_comments
24
+ def is_filtered?
25
+ will_paginate? || config.comment_filter
26
+ end
27
+
28
+ def filtered_comments
29
+ cf = config.comment_filter
30
+ return comments if cf.nil?
31
+ comments.where(cf)
32
+ end
33
+
34
+ def ordered_comments(unfiltered = false)
35
+ vc = unfiltered ? comments : filtered_comments
25
36
  case config.comment_order.to_sym
26
- when :l then comments.order('id DESC')
27
- when :ve then comments.order('cached_votes_down - cached_votes_up')
28
- when :vl then comments.order('cached_votes_down - cached_votes_up', 'id DESC')
29
- else comments
37
+ when :l then vc.order('id DESC')
38
+ when :ve then vc.order('cached_votes_down - cached_votes_up')
39
+ when :vl then vc.order('cached_votes_down - cached_votes_up', 'id DESC')
40
+ else vc
30
41
  end
31
42
  end
32
43
 
33
- def paginated_comments(page, per_page)
44
+ def paginated_comments(page = 1, per_page = config.comments_per_page)
34
45
  oc = ordered_comments
35
46
  return oc unless will_paginate?
36
47
  oc.paginate(:page => page, :per_page => per_page)
37
48
  end
38
49
 
50
+ def new_comment_page(per_page = config.comments_per_page)
51
+ return 1 if per_page.nil? || per_page.to_i <= 0
52
+ comment_index = \
53
+ case config.comment_order.to_sym
54
+ when :l
55
+ 1 # First comment
56
+ when :ve
57
+ comment_arel = Comment.arel_table
58
+ # Last comment with rating = 0
59
+ filtered_comments.where((comment_arel[:cached_votes_up] - comment_arel[:cached_votes_down]).gteq 0).count
60
+ when :vl
61
+ comment_arel = Comment.arel_table
62
+ # First comment with rating = 0
63
+ filtered_comments.where((comment_arel[:cached_votes_up] - comment_arel[:cached_votes_down]).gt 0).count + 1
64
+ else
65
+ filtered_comments.count # Last comment
66
+ end
67
+ (comment_index.to_f/per_page.to_i).ceil
68
+ end
69
+
39
70
  def is_closed?
40
71
  !closed_at.blank?
41
72
  end
42
73
 
74
+ def close(user = nil)
75
+ return false if is_closed?
76
+ self.closed_at = Time.now
77
+ self.closer = user
78
+ save
79
+ end
80
+
81
+ def reopen
82
+ return false unless is_closed? && !commontable.nil?
83
+ self.closed_at = nil
84
+ save
85
+ end
86
+
43
87
  def subscribers
44
88
  subscriptions.collect{|s| s.subscriber}
45
89
  end
@@ -49,12 +93,8 @@ module Commontator
49
93
  subscriber.subscriptions.where(:thread_id => self.id).first
50
94
  end
51
95
 
52
- def is_subscribed?(subscriber)
53
- !subscription_for(subscriber).blank?
54
- end
55
-
56
96
  def subscribe(subscriber)
57
- return false if is_subscribed?(subscriber) || !subscriber.is_commontator
97
+ return false unless subscriber.is_commontator && !subscription_for(subscriber)
58
98
  subscription = Subscription.new
59
99
  subscription.subscriber = subscriber
60
100
  subscription.thread = self
@@ -63,50 +103,30 @@ module Commontator
63
103
 
64
104
  def unsubscribe(subscriber)
65
105
  subscription = subscription_for(subscriber)
66
- return false if subscription.blank?
106
+ return false unless subscription
67
107
  subscription.destroy
68
108
  end
69
109
 
70
- def add_unread_except_for(subscriber)
71
- Subscription.transaction do
72
- subscriptions.each{|s| s.add_unread unless s.subscriber == subscriber}
73
- end
74
- end
75
-
76
110
  def mark_as_read_for(subscriber)
77
- return if !subscription_for(subscriber)
78
- subscription_for(subscriber).mark_as_read
79
- end
80
-
81
- def close(user = nil)
82
- return false if is_closed?
83
- self.closed_at = Time.now
84
- self.closer = user
85
- save
86
- end
87
-
88
- def reopen
89
- return false unless is_closed? && !commontable.nil?
90
- self.closed_at = nil
91
- save
111
+ subscription = subscription_for(subscriber)
112
+ return false unless subscription
113
+ subscription.touch
92
114
  end
93
115
 
94
116
  # Creates a new empty thread and assigns it to the commontable
95
117
  # The old thread is kept in the database for archival purposes
96
- def clear(user = nil)
97
- return if commontable.blank?
118
+ def clear
119
+ return if commontable.blank? || !is_closed?
98
120
  new_thread = Thread.new
99
121
  new_thread.commontable = commontable
122
+
100
123
  with_lock do
101
124
  self.commontable = nil
102
- self.closed_at = Time.now
103
- self.closer = user
104
125
  save!
105
126
  new_thread.save!
106
127
  subscriptions.each do |s|
107
128
  s.thread = new_thread
108
129
  s.save!
109
- s.mark_as_read
110
130
  end
111
131
  end
112
132
  end
@@ -115,10 +135,10 @@ module Commontator
115
135
  # Access Control #
116
136
  ##################
117
137
 
118
- # Reader capabilities (remember: user can be nil or false)
138
+ # Reader capabilities (user can be nil or false)
119
139
  def can_be_read_by?(user)
120
140
  return true if can_be_edited_by?(user)
121
- !commontable.nil? && (!is_closed? || !config.hide_closed_threads) &&\
141
+ !commontable.nil? &&\
122
142
  config.thread_read_proc.call(self, user)
123
143
  end
124
144
 
@@ -131,8 +151,9 @@ module Commontator
131
151
  def can_subscribe?(user)
132
152
  thread_sub = config.thread_subscription.to_sym
133
153
  !is_closed? && !user.nil? && user.is_commontator &&\
134
- thread_sub != :n && thread_sub != :a &&\
154
+ (thread_sub == :m || thread_sub == :b) &&\
135
155
  can_be_read_by?(user)
136
156
  end
137
157
  end
138
158
  end
159
+