diff --git a/app/lib/activitypub/activity/accept.rb b/app/lib/activitypub/activity/accept.rb index 494400bffdfc19..649c3503f7d88a 100644 --- a/app/lib/activitypub/activity/accept.rb +++ b/app/lib/activitypub/activity/accept.rb @@ -45,7 +45,7 @@ def relay_follow? end def accept_follow_for_friend - friend.update!(active_state: :accepted) + friend.update!(active_state: :accepted, passive_state: :idle) end def friend diff --git a/app/lib/activitypub/activity/follow.rb b/app/lib/activitypub/activity/follow.rb index d02e9c01c6fd85..985356a7cb3ca5 100644 --- a/app/lib/activitypub/activity/follow.rb +++ b/app/lib/activitypub/activity/follow.rb @@ -49,8 +49,8 @@ def request_follow_for_friend already_accepted = false if friend.present? - already_accepted = friend.they_are_accepted? - friend.update!(passive_state: :pending, passive_follow_activity_id: @json['id']) + already_accepted = friend.accepted? + friend.update!(passive_state: :pending, active_state: :idle, passive_follow_activity_id: @json['id']) else @friend = FriendDomain.create!(domain: @account.domain, passive_state: :pending, passive_follow_activity_id: @json['id']) end diff --git a/app/lib/activitypub/activity/reject.rb b/app/lib/activitypub/activity/reject.rb index 0493400f864d30..e1eb3c2368cda6 100644 --- a/app/lib/activitypub/activity/reject.rb +++ b/app/lib/activitypub/activity/reject.rb @@ -39,7 +39,7 @@ def relay_follow? end def reject_follow_for_friend - friend.update!(active_state: :rejected) + friend.update!(active_state: :rejected, passive_state: :idle) end def friend diff --git a/app/lib/activitypub/activity/undo.rb b/app/lib/activitypub/activity/undo.rb index 2fc6bd25622610..973143d8d29659 100644 --- a/app/lib/activitypub/activity/undo.rb +++ b/app/lib/activitypub/activity/undo.rb @@ -103,7 +103,7 @@ def undo_follow end def remove_follow_from_friend - friend.update!(passive_state: :idle, passive_follow_activity_id: nil) + friend.destroy_without_signal! end def friend diff --git a/app/models/friend_domain.rb b/app/models/friend_domain.rb index cafb2070ca2ab4..ee2dafd68f2070 100644 --- a/app/models/friend_domain.rb +++ b/app/models/friend_domain.rb @@ -35,11 +35,23 @@ class FriendDomain < ApplicationRecord before_destroy :ensure_disabled after_commit :set_default_inbox_url + def accepted? + i_am_accepted? || they_are_accepted? + end + + def pending? + !accepted && (i_am_pending? || they_are_pending?) + end + + def idle? + (i_am_idle? || i_am_rejected?) && (they_are_idle? || they_are_rejected?) + end + def follow! activity_id = ActivityPub::TagManager.instance.generate_uri_for(nil) payload = Oj.dump(follow_activity(activity_id)) - update!(active_state: :pending, active_follow_activity_id: activity_id) + update!(active_state: :pending, passive_state: :idle, active_follow_activity_id: activity_id) DeliveryFailureTracker.reset!(inbox_url) ActivityPub::DeliveryWorker.perform_async(payload, some_local_account.id, inbox_url) end @@ -48,7 +60,7 @@ def unfollow! activity_id = ActivityPub::TagManager.instance.generate_uri_for(nil) payload = Oj.dump(unfollow_activity(activity_id)) - update!(active_state: :idle, active_follow_activity_id: nil) + update!(active_state: :idle, passive_state: :idle, active_follow_activity_id: nil) DeliveryFailureTracker.reset!(inbox_url) ActivityPub::DeliveryWorker.perform_async(payload, some_local_account.id, inbox_url) end @@ -59,7 +71,7 @@ def accept! activity_id = passive_follow_activity_id payload = Oj.dump(accept_follow_activity(activity_id)) - update!(passive_state: :accepted) + update!(passive_state: :accepted, active_state: :idle) DeliveryFailureTracker.reset!(inbox_url) ActivityPub::DeliveryWorker.perform_async(payload, some_local_account.id, inbox_url) end @@ -70,11 +82,17 @@ def reject! activity_id = passive_follow_activity_id payload = Oj.dump(reject_follow_activity(activity_id)) - update!(passive_state: :rejected, passive_follow_activity_id: nil) + update!(passive_state: :rejected, active_state: :idle, passive_follow_activity_id: nil) DeliveryFailureTracker.reset!(inbox_url) ActivityPub::DeliveryWorker.perform_async(payload, some_local_account.id, inbox_url) end + def destroy_without_signal! + self.active_state = :idle + self.passive_state = :idle + destroy! + end + private def default_inbox_url diff --git a/app/views/admin/friend_servers/_friend_domain.html.haml b/app/views/admin/friend_servers/_friend_domain.html.haml index a24ae0516a5f0b..f253800cc52e74 100644 --- a/app/views/admin/friend_servers/_friend_domain.html.haml +++ b/app/views/admin/friend_servers/_friend_domain.html.haml @@ -7,27 +7,12 @@ = t 'admin.friend_servers.disabled' %samp= friend.domain %td - - if friend.i_am_accepted? + - if friend.accepted? %span.positive-hint = fa_icon('check') = ' ' = t 'admin.friend_servers.enabled' - - elsif friend.i_am_pending? - = fa_icon('hourglass') - = ' ' - = t 'admin.friend_servers.pending' - - else - %span.negative-hint - = fa_icon('times') - = ' ' - = t 'admin.friend_servers.disabled' - %td - - if friend.they_are_accepted? - %span.positive-hint - = fa_icon('check') - = ' ' - = t 'admin.friend_servers.enabled' - - elsif friend.they_are_pending? + - elsif friend.pending? = fa_icon('hourglass') = ' ' = t 'admin.friend_servers.pending' diff --git a/app/views/admin/friend_servers/_friend_fields.html.haml b/app/views/admin/friend_servers/_friend_fields.html.haml index f2de4a1f60dcfa..ad508f1bf7ff1f 100644 --- a/app/views/admin/friend_servers/_friend_fields.html.haml +++ b/app/views/admin/friend_servers/_friend_fields.html.haml @@ -10,6 +10,9 @@ .fields-group = f.input :available, as: :boolean, wrapper: :with_label, label: t('admin.friend_servers.edit.available') +.fields-group + = f.input :pseudo_relay, as: :boolean, wrapper: :with_label, label: t('admin.friend_servers.edit.delivery_local'), hint: t('admin.friend_servers.edit.delivery_local_hint') + .fields-group = f.input :pseudo_relay, as: :boolean, wrapper: :with_label, label: t('admin.friend_servers.edit.pseudo_relay'), hint: t('admin.friend_servers.edit.pseudo_relay_hint') diff --git a/app/views/admin/friend_servers/edit.html.haml b/app/views/admin/friend_servers/edit.html.haml index ae057c296300b4..06cff11bfba69a 100644 --- a/app/views/admin/friend_servers/edit.html.haml +++ b/app/views/admin/friend_servers/edit.html.haml @@ -6,35 +6,14 @@ = render 'friend_fields', f: f, friend: @friend .fields-group - %h4= t('admin.friend_servers.active_status') + %h4= t('admin.friend_servers.status') .fields-group - - if @friend.i_am_accepted? + - if @friend.accepted? %span.positive-hint = fa_icon('check') = ' ' = t 'admin.friend_servers.enabled' - - elsif @friend.i_am_pending? - = fa_icon('hourglass') - = ' ' - = t 'admin.friend_servers.pending' - - else - %span.negative-hint - = fa_icon('times') - = ' ' - = t 'admin.friend_servers.disabled' - .action-buttons - %div - = link_to t('admin.friend_servers.follow'), follow_admin_friend_server_path(@friend), class: 'button', method: :post, data: { confirm: t('admin.accounts.are_you_sure') } if @friend.i_am_idle? || @friend.i_am_rejected? - = link_to t('admin.friend_servers.unfollow'), unfollow_admin_friend_server_path(@friend), class: 'button', method: :post, data: { confirm: t('admin.accounts.are_you_sure') } if @friend.i_am_pending? || @friend.i_am_accepted? - - %h4= t('admin.friend_servers.passive_status') - .fields-gtoup - - if @friend.they_are_accepted? - %span.positive-hint - = fa_icon('check') - = ' ' - = t 'admin.friend_servers.enabled' - - elsif @friend.they_are_pending? + - elsif @friend.pending? = fa_icon('hourglass') = ' ' = t 'admin.friend_servers.pending' @@ -45,6 +24,7 @@ = t 'admin.friend_servers.disabled' .action-buttons %div + = link_to t('admin.friend_servers.follow'), follow_admin_friend_server_path(@friend), class: 'button', method: :post, data: { confirm: t('admin.accounts.are_you_sure') } if @friend.idle? = link_to t('admin.friend_servers.accept'), accept_admin_friend_server_path(@friend), class: 'button', method: :post, data: { confirm: t('admin.accounts.are_you_sure') } if @friend.they_are_pending? = link_to t('admin.friend_servers.reject'), reject_admin_friend_server_path(@friend), class: 'button', method: :post, data: { confirm: t('admin.accounts.are_you_sure') } if @friend.they_are_pending? diff --git a/app/views/admin/friend_servers/index.html.haml b/app/views/admin/friend_servers/index.html.haml index 6dd16e397e1fa5..196407c4c49939 100644 --- a/app/views/admin/friend_servers/index.html.haml +++ b/app/views/admin/friend_servers/index.html.haml @@ -13,8 +13,7 @@ %thead %tr %th= t('admin.friend_servers.domain') - %th= t('admin.friend_servers.active_status') - %th= t('admin.friend_servers.passive_status') + %th= t('admin.friend_servers.status') %th %tbody - @friends.each do |friend| diff --git a/config/locales/en.yml b/config/locales/en.yml index 2185f933cb23ca..456433750426f9 100644 --- a/config/locales/en.yml +++ b/config/locales/en.yml @@ -501,7 +501,6 @@ en: unsuppress: Restore follow recommendation friend_servers: accept: Accept - active_status: My status add_new: Add and make a new application delete: Delete description_html: フレンドサーバーとは、お互いのローカル公開・ローカル検索許可の投稿をそのまま交換するシステムです。 @@ -511,6 +510,8 @@ en: allow_all_posts: Receive all posts allow_all_posts_hint: 通常は自分のサーバーの誰もフォローしていないアカウントの投稿は例外を除き受け入れがブロックされます。そのブロックを解除します。スパムが発生した場合など、いつでもブロックを再開できます。 available: Available + delivery_local: Deliver without changing public unlisted visibility and searchability + delivery_local_hint: Public unlisted posts will be added the friend's global timeline description: フレンドサーバーは、登録と同時に相手方のサーバーへ申請されます。 domain: Domain inbox_url: Friend server inbox URL @@ -521,7 +522,6 @@ en: edit_friend: Edit enabled: Enabled follow: Request - passive_status: Partner status pending: Pending reject: Reject save_and_enable: Save and enable diff --git a/config/locales/ja.yml b/config/locales/ja.yml index 61189de940c3a1..b9317934b2c34a 100644 --- a/config/locales/ja.yml +++ b/config/locales/ja.yml @@ -496,7 +496,6 @@ ja: unsuppress: おすすめフォローを復元 friend_servers: accept: 相手の申請を承認する - active_status: 自分の状態 add_new: フレンドサーバーを追加・申請 delete: 削除 description_html: フレンドサーバーとは、お互いのローカル公開・ローカル検索許可の投稿をそのまま交換するシステムです。 @@ -506,6 +505,8 @@ ja: allow_all_posts: このサーバーからの投稿を無条件で受け入れる allow_all_posts_hint: 通常は自分のサーバーの誰もフォローしていないアカウントの投稿は例外を除き受け入れがブロックされます。そのブロックを解除します。スパムが発生した場合など、いつでもブロックを再開できます。 available: 有効にする + delivery_local: ローカル公開の公開範囲・検索許可を持った投稿をそのまま相手と共有する + delivery_local_hint: ローカル公開投稿は、通常は非収載に変換されて配送されます。その処理をせず、相手サーバーにもローカル公開と認識されるようにします。相手の連合タイムラインに掲載されます description: フレンドサーバーは、登録と同時に相手方のサーバーへ申請されます。 domain: ドメイン inbox_url: フレンドサーバーの inbox URL @@ -516,7 +517,6 @@ ja: edit_friend: 編集 enabled: 有効 follow: こちらから申請する - passive_status: 相手の状態 pending: 承認待ち reject: 相手からの申請を却下する save_and_enable: 保存して有効にする diff --git a/spec/lib/activitypub/activity/create_spec.rb b/spec/lib/activitypub/activity/create_spec.rb index 58aca0757327cc..f8bbfbecc7e1e7 100644 --- a/spec/lib/activitypub/activity/create_spec.rb +++ b/spec/lib/activitypub/activity/create_spec.rb @@ -1495,11 +1495,7 @@ context 'when sender is in friend server' do subject { described_class.new(json, sender, delivery: true) } - before do - Fabricate(:friend_domain, domain: sender.domain, active_state: :accepted, passive_state: :accepted) - subject.perform - end - + let!(:friend) { Fabricate(:friend_domain, domain: sender.domain, active_state: :accepted) } let(:object_json) do { id: [ActivityPub::TagManager.instance.uri_for(sender), '#bar'].join, @@ -1509,11 +1505,20 @@ end it 'creates status' do + subject.perform status = sender.statuses.first expect(status).to_not be_nil expect(status.text).to eq 'Lorem ipsum' end + + it 'whey no-relay not creates status' do + friend.update(allow_all_posts: false) + subject.perform + status = sender.statuses.first + + expect(status).to be_nil + end end context 'when the sender has no relevance to local activity' do diff --git a/spec/lib/activitypub/activity/follow_spec.rb b/spec/lib/activitypub/activity/follow_spec.rb index 5a1402e83e0587..74b024253174e1 100644 --- a/spec/lib/activitypub/activity/follow_spec.rb +++ b/spec/lib/activitypub/activity/follow_spec.rb @@ -349,12 +349,12 @@ it 'marks me as idle' do subject.perform - expect(friend.they_are_pending?).to be true + expect(friend.reload.they_are_pending?).to be true expect(friend.i_am_idle?).to be true end end - context 'when my server is accepted' do + context 'when my server is already accepted' do before do friend.update(active_state: :accepted) stub_request(:post, 'https://example.com/inbox') @@ -362,7 +362,7 @@ it 'marks me as idle and the friend as accepted' do subject.perform - expect(friend.they_are_accepted?).to be true + expect(friend.reload.they_are_accepted?).to be true expect(friend.i_am_idle?).to be true expect(a_request(:post, 'https://example.com/inbox').with(body: hash_including({ id: 'foo#accepts/friends', diff --git a/spec/lib/activitypub/activity/undo_spec.rb b/spec/lib/activitypub/activity/undo_spec.rb index 699aaf353b34f9..4634cb967e270a 100644 --- a/spec/lib/activitypub/activity/undo_spec.rb +++ b/spec/lib/activitypub/activity/undo_spec.rb @@ -149,7 +149,7 @@ friend = Fabricate(:friend_domain, domain: sender.domain, passive_state: :accepted) subject.perform expect(sender.following?(recipient)).to be false - expect(friend.they_are_accepted?).to be true + expect(friend.reload.they_are_accepted?).to be true end context 'with only object uri' do @@ -175,22 +175,19 @@ it 'deletes follow from this server to friend' do subject.perform - expect(friend.reload.they_are_idle?).to be true - expect(friend.passive_follow_activity_id).to be_nil + expect(FriendDomain.exists?(domain: 'abc.com')).to be false end it 'when my server is pending' do friend.update(active_state: :pending) subject.perform - expect(friend.reload.they_are_idle?).to be true - expect(friend.i_am_idle?).to be true + expect(FriendDomain.exists?(domain: 'abc.com')).to be false end it 'when my server is accepted' do friend.update(active_state: :accepted) subject.perform - expect(friend.reload.they_are_idle?).to be true - expect(friend.i_am_idle?).to be true + expect(FriendDomain.exists?(domain: 'abc.com')).to be false end end end