about summary refs log tree commit diff
path: root/app/lib/activitypub/tag_manager.rb
diff options
context:
space:
mode:
Diffstat (limited to 'app/lib/activitypub/tag_manager.rb')
-rw-r--r--app/lib/activitypub/tag_manager.rb84
1 files changed, 36 insertions, 48 deletions
diff --git a/app/lib/activitypub/tag_manager.rb b/app/lib/activitypub/tag_manager.rb
index 3f2ae1106..383f182d2 100644
--- a/app/lib/activitypub/tag_manager.rb
+++ b/app/lib/activitypub/tag_manager.rb
@@ -64,29 +64,21 @@ class ActivityPub::TagManager
   # Public statuses go out to primarily the public collection
   # Unlisted and private statuses go out primarily to the followers collection
   # Others go out only to the people they mention
-  def to(status)
-    case status.visibility
-    when 'public'
-      [COLLECTIONS[:public]]
-    when 'unlisted', 'private'
-      [account_followers_url(status.account)]
-    when 'direct', 'limited'
-      if status.account.silenced?
-        # Only notify followers if the account is locally silenced
-        account_ids = status.active_mentions.pluck(:account_id)
-        to = status.account.followers.where(id: account_ids).each_with_object([]) do |account, result|
-          result << uri_for(account)
-          result << account_followers_url(account) if account.group?
-        end
-        to.concat(FollowRequest.where(target_account_id: status.account_id, account_id: account_ids).each_with_object([]) do |request, result|
-          result << uri_for(request.account)
-          result << account_followers_url(request.account) if request.account.group?
-        end)
-      else
-        status.active_mentions.each_with_object([]) do |mention, result|
-          result << uri_for(mention.account)
-          result << account_followers_url(mention.account) if mention.account.group?
-        end
+  def to(status, domain)
+    visibility = status.visibility_for_domain(domain)
+    case visibility
+    when 'public', 'unlisted'
+      [status.tags.present? ? COLLECTIONS[:public] : account_followers_url(status.account)]
+    else
+      account_ids = status.active_mentions.pluck(:account_id)
+      account_ids |= status.account.follower_ids if visibility == 'private'
+
+      accounts = status.account.silenced? ? status.account.followers.where(id: account_ids) : Account.where(id: account_ids)
+      accounts = accounts.where(domain: domain) if domain.present?
+
+      accounts.each_with_object([]) do |account, result|
+        result << uri_for(account)
+        result << account_followers_url(account) if account.group?
       end
     end
   end
@@ -96,36 +88,32 @@ class ActivityPub::TagManager
   # Unlisted statuses go to the public as well
   # Both of those and private statuses also go to the people mentioned in them
   # Direct ones don't have a secondary audience
-  def cc(status)
+  def cc(status, domain)
     cc = []
-
     cc << uri_for(status.reblog.account) if status.reblog?
 
-    case status.visibility
-    when 'public'
-      cc << account_followers_url(status.account)
-    when 'unlisted'
-      cc << COLLECTIONS[:public]
+    visibility = status.visibility_for_domain(domain)
+
+    case visibility
+    when 'public', 'unlisted'
+      cc << (status.tags.present? ? account_followers_url(status.account) : COLLECTIONS[:public])
+      account_ids = status.active_mentions.pluck(:account_id)
+    when 'private', 'limited'
+      # Work around Mastodon visibility heuritic bug by addressing instance actor.
+      cc << instance_actor_url
+      account_ids = status.silent_mentions.pluck(:account_id)
+    else
+      account_ids = []
     end
 
-    unless status.direct_visibility? || status.limited_visibility?
-      if status.account.silenced?
-        # Only notify followers if the account is locally silenced
-        account_ids = status.active_mentions.pluck(:account_id)
-        cc.concat(status.account.followers.where(id: account_ids).each_with_object([]) do |account, result|
-          result << uri_for(account)
-          result << account_followers_url(account) if account.group?
-        end)
-        cc.concat(FollowRequest.where(target_account_id: status.account_id, account_id: account_ids).each_with_object([]) do |request, result|
-          result << uri_for(request.account)
-          result << account_followers_url(request.account) if request.account.group?
-        end)
-      else
-        cc.concat(status.active_mentions.each_with_object([]) do |mention, result|
-          result << uri_for(mention.account)
-          result << account_followers_url(mention.account) if mention.account.group?
-        end)
-      end
+    if account_ids.present?
+      accounts = status.account.silenced? ? status.account.followers.where(id: account_ids) : Account.where(id: account_ids)
+      accounts = accounts.where(domain: domain) if domain.present?
+
+      cc.concat(accounts.each_with_object([]) do |account, result|
+        result << uri_for(account)
+        result << account_followers_url(account) if account.group?
+      end)
     end
 
     cc