From 8a3f2ee0fb2a974e4483a174805d54725b0a2775 Mon Sep 17 00:00:00 2001 From: KMY Date: Sun, 24 Sep 2023 20:29:36 +0900 Subject: [PATCH] Refactoring searchability to StatusParser --- app/lib/activitypub/activity/create.rb | 100 +------------------- app/lib/activitypub/parser/status_parser.rb | 72 ++++++++++++++ 2 files changed, 74 insertions(+), 98 deletions(-) diff --git a/app/lib/activitypub/activity/create.rb b/app/lib/activitypub/activity/create.rb index 6b8a715330..1f81fcda6c 100644 --- a/app/lib/activitypub/activity/create.rb +++ b/app/lib/activitypub/activity/create.rb @@ -72,12 +72,6 @@ class ActivityPub::Activity::Create < ActivityPub::Activity as_array(@object['cc'] || @json['cc']).map { |x| value_or_id(x) } end - def audience_searchable_by - return nil if @object['searchableBy'].nil? - - @audience_searchable_by = as_array(@object['searchableBy']).map { |x| value_or_id(x) } - end - def process_status @tags = [] @mentions = [] @@ -120,7 +114,7 @@ class ActivityPub::Activity::Create < ActivityPub::Activity end def process_status_params - @status_parser = ActivityPub::Parser::StatusParser.new(@json, followers_collection: @account.followers_url, object: @object) + @status_parser = ActivityPub::Parser::StatusParser.new(@json, followers_collection: @account.followers_url, object: @object, account: @account) @params = { uri: @status_parser.uri, @@ -136,7 +130,7 @@ class ActivityPub::Activity::Create < ActivityPub::Activity sensitive: @account.sensitized? || @status_parser.sensitive || false, visibility: @status_parser.visibility, limited_scope: @status_parser.limited_scope, - searchability: searchability, + searchability: @status_parser.searchability, thread: replied_to_status, conversation: conversation_from_uri(@object['conversation']), media_attachment_ids: process_attachments.take(MediaAttachment::ACTIVITYPUB_STATUS_ATTACHMENT_MAX).map(&:id), @@ -500,94 +494,4 @@ class ActivityPub::Activity::Create < ActivityPub::Activity def join_group! GroupReblogService.new.call(@status) end - - def searchability_from_audience - if audience_searchable_by.nil? - nil - elsif audience_searchable_by.any? { |uri| ActivityPub::TagManager.instance.public_collection?(uri) } - :public - elsif audience_searchable_by.include?('as:Limited') - :limited - elsif audience_searchable_by.include?(@account.followers_url) - :private - else - :direct - end - end - - SCAN_SEARCHABILITY_RE = /\[searchability:(public|followers|reactors|private)\]/ - SCAN_SEARCHABILITY_FEDIBIRD_RE = /searchable_by_(all_users|followers_only|reacted_users_only|nobody)/ - - def searchability - from_audience = searchability_from_audience - return from_audience if from_audience - return nil if default_searchability_from_bio? - - searchability_from_bio || (misskey_software? ? misskey_searchability : nil) - end - - def default_searchability_from_bio? - note = @account.note - return false if note.blank? - - note.include?('searchable_by_default_range') - end - - def searchability_from_bio - note = @account.note - return nil if note.blank? - - searchability_bio = note.scan(SCAN_SEARCHABILITY_FEDIBIRD_RE).first || note.scan(SCAN_SEARCHABILITY_RE).first - return nil unless searchability_bio - - searchability = searchability_bio[0] - return nil if searchability.nil? - - searchability = :public if %w(public all_users).include?(searchability) - searchability = :private if %w(followers followers_only).include?(searchability) - searchability = :direct if %w(reactors reacted_users_only).include?(searchability) - searchability = :limited if %w(private nobody).include?(searchability) - - searchability - end - - def instance_info - @instance_info ||= InstanceInfo.find_by(domain: @account.domain) - end - - def misskey_software? - info = instance_info - return false if info.nil? - - %w(misskey calckey).include?(info.software) - end - - def misskey_searchability - visibility = visibility_from_audience - %i(public unlisted).include?(visibility) ? :public : :limited - end - - def visibility_from_audience - if audience_to.any? { |to| ActivityPub::TagManager.instance.public_collection?(to) } - :public - elsif audience_cc.any? { |cc| ActivityPub::TagManager.instance.public_collection?(cc) } - :unlisted - elsif audience_to.include?('as:LoginOnly') || audience_to.include?('LoginUser') - :login - elsif audience_to.include?(@account.followers_url) - :private - else - :direct - end - end - - def visibility_from_audience_with_silence - visibility = visibility_from_audience - - if @account.silenced? && %i(public).include?(visibility) - :unlisted - else - visibility - end - end end diff --git a/app/lib/activitypub/parser/status_parser.rb b/app/lib/activitypub/parser/status_parser.rb index 852578721c..4ffec58ae3 100644 --- a/app/lib/activitypub/parser/status_parser.rb +++ b/app/lib/activitypub/parser/status_parser.rb @@ -10,6 +10,7 @@ class ActivityPub::Parser::StatusParser @json = json @object = magic_values[:object] || json['object'] || json @magic_values = magic_values + @account = magic_values[:account] end def uri @@ -86,6 +87,14 @@ class ActivityPub::Parser::StatusParser end end + def searchability + from_audience = searchability_from_audience + return from_audience if from_audience + return nil if default_searchability_from_bio? + + searchability_from_bio || (misskey_software? ? misskey_searchability : nil) + end + def limited_scope case @object['limitedScope'] when 'Mutual' @@ -117,6 +126,12 @@ class ActivityPub::Parser::StatusParser as_array(@object['cc'] || @json['cc']).map { |x| value_or_id(x) } end + def audience_searchable_by + return nil if @object['searchableBy'].nil? + + @audience_searchable_by = as_array(@object['searchableBy']).map { |x| value_or_id(x) } + end + def summary_language_map? @object['summaryMap'].is_a?(Hash) && !@object['summaryMap'].empty? end @@ -128,4 +143,61 @@ class ActivityPub::Parser::StatusParser def name_language_map? @object['nameMap'].is_a?(Hash) && !@object['nameMap'].empty? end + + def instance_info + @instance_info ||= InstanceInfo.find_by(domain: @account.domain) + end + + def misskey_software? + info = instance_info + return false if info.nil? + + %w(misskey calckey).include?(info.software) + end + + def misskey_searchability + %i(public unlisted).include?(visibility) ? :public : :limited + end + + SCAN_SEARCHABILITY_RE = /\[searchability:(public|followers|reactors|private)\]/ + SCAN_SEARCHABILITY_FEDIBIRD_RE = /searchable_by_(all_users|followers_only|reacted_users_only|nobody)/ + + def default_searchability_from_bio? + note = @account.note + return false if note.blank? + + note.include?('searchable_by_default_range') + end + + def searchability_from_bio + note = @account.note + return nil if note.blank? + + searchability_bio = note.scan(SCAN_SEARCHABILITY_FEDIBIRD_RE).first || note.scan(SCAN_SEARCHABILITY_RE).first + return nil unless searchability_bio + + searchability = searchability_bio[0] + return nil if searchability.nil? + + searchability = :public if %w(public all_users).include?(searchability) + searchability = :private if %w(followers followers_only).include?(searchability) + searchability = :direct if %w(reactors reacted_users_only).include?(searchability) + searchability = :limited if %w(private nobody).include?(searchability) + + searchability + end + + def searchability_from_audience + if audience_searchable_by.nil? + nil + elsif audience_searchable_by.any? { |uri| ActivityPub::TagManager.instance.public_collection?(uri) } + :public + elsif audience_searchable_by.include?('as:Limited') + :limited + elsif audience_searchable_by.include?(@account.followers_url) + :private + else + :direct + end + end end