about summary refs log tree commit diff
diff options
context:
space:
mode:
authorFire Demon <firedemon@creature.cafe>2020-11-23 23:10:05 -0600
committerFire Demon <firedemon@creature.cafe>2020-11-23 23:10:05 -0600
commit65a9abb315f18ac777f3d0e09b3f7399830ad243 (patch)
tree39712b50201749efad11dce09561d81f4bdcdb2f
parent7f5ba917563aa1c9a373d9dd3a6a29f73d81ee9a (diff)
Add user options to disable recipient verification, allow anonymous public access; rework private mode
-rw-r--r--app/controllers/accounts_controller.rb10
-rw-r--r--app/controllers/activitypub/outboxes_controller.rb4
-rw-r--r--app/controllers/api/v1/accounts/statuses_controller.rb5
-rw-r--r--app/controllers/application_controller.rb6
-rw-r--r--app/controllers/settings/preferences_controller.rb1
-rw-r--r--app/controllers/settings/profiles_controller.rb2
-rw-r--r--app/controllers/statuses_controller.rb5
-rw-r--r--app/lib/activitypub/activity/announce.rb4
-rw-r--r--app/lib/activitypub/activity/create.rb4
-rw-r--r--app/lib/activitypub/adapter.rb1
-rw-r--r--app/lib/user_settings_decorator.rb5
-rw-r--r--app/models/account.rb3
-rw-r--r--app/models/status.rb5
-rw-r--r--app/models/user.rb2
-rw-r--r--app/policies/status_policy.rb12
-rw-r--r--app/presenters/activitypub/activity_presenter.rb2
-rw-r--r--app/serializers/activitypub/actor_serializer.rb4
-rw-r--r--app/services/activitypub/process_account_service.rb1
-rw-r--r--app/services/concerns/payloadable.rb6
-rw-r--r--app/services/fan_out_on_write_service.rb9
-rw-r--r--app/services/process_hashtags_service.rb4
-rw-r--r--app/services/reblog_service.rb2
-rw-r--r--app/services/remove_hashtags_service.rb2
-rw-r--r--app/services/remove_status_service.rb6
-rw-r--r--app/services/revoke_status_service.rb6
-rw-r--r--app/views/settings/preferences/privacy/show.html.haml3
-rw-r--r--app/views/settings/profiles/show.html.haml9
-rw-r--r--app/workers/activitypub/distribute_poll_update_worker.rb2
-rw-r--r--app/workers/activitypub/distribution_worker.rb2
-rw-r--r--config/locales/en-MP.yml4
-rw-r--r--config/locales/simple_form.en-MP.yml8
-rw-r--r--db/migrate/20201123152231_add_no_verify_auth_to_accounts.rb7
-rw-r--r--db/migrate/20201123171722_add_allow_anonymous_to_accounts.rb5
-rw-r--r--db/migrate/20201124005733_remove_require_auth_from_accounts.rb7
-rw-r--r--db/schema.rb5
35 files changed, 87 insertions, 76 deletions
diff --git a/app/controllers/accounts_controller.rb b/app/controllers/accounts_controller.rb
index f97eeb80b..3d328e920 100644
--- a/app/controllers/accounts_controller.rb
+++ b/app/controllers/accounts_controller.rb
@@ -8,11 +8,11 @@ class AccountsController < ApplicationController
   include SignatureAuthentication
 
   before_action :require_signature!, if: -> { request.format == :json && authorized_fetch_mode? }
+  before_action :require_authenticated!, if: -> { @account.private? }
+  before_action :require_following!, if: -> { request.format != :rss && @account.private? }
   before_action :set_cache_headers
   before_action :set_body_classes
 
-  before_action :require_authenticated!, if: -> { @account.require_auth? || @account.private? }
-
   skip_around_action :set_locale, if: -> { [:json, :rss].include?(request.format&.to_sym) }
   skip_before_action :require_functional! # , unless: :whitelist_mode?
 
@@ -44,7 +44,7 @@ class AccountsController < ApplicationController
       end
 
       format.rss do
-        return render xml: '', status: 404 if rss_disabled? || unauthorized?
+        return render xml: '', status: 404 if !@account.allow_anonymous? || unauthorized?
 
         expires_in 1.minute, public: !current_account?
 
@@ -182,10 +182,6 @@ class AccountsController < ApplicationController
     @unauthorized ||= blocked? || (@account.private? && !following?(@account))
   end
 
-  def rss_disabled?
-    @account.user&.setting_rss_disabled
-  end
-
   def cached_filtered_status_page
     cache_collection_paginated_by_id(
       filtered_statuses,
diff --git a/app/controllers/activitypub/outboxes_controller.rb b/app/controllers/activitypub/outboxes_controller.rb
index 1a879c379..e06688994 100644
--- a/app/controllers/activitypub/outboxes_controller.rb
+++ b/app/controllers/activitypub/outboxes_controller.rb
@@ -7,12 +7,10 @@ class ActivityPub::OutboxesController < ActivityPub::BaseController
   include AccountOwnedConcern
 
   before_action :require_signature!, if: :authorized_fetch_mode?
+  before_action :require_following!, if: -> { @account.private? }
   before_action :set_statuses
   before_action :set_cache_headers
 
-  before_action :require_authenticated!, if: -> { @account.require_auth? }
-  before_action -> { require_following!(@account) }, if: -> { @account.private? }
-
   def show
     expires_in(page_requested? ? 0 : 3.minutes, public: public_fetch_mode? && !(current_account.present? && page_requested?))
     render json: outbox_presenter, serializer: ActivityPub::OutboxSerializer, adapter: ActivityPub::Adapter, content_type: 'application/activity+json', domain: current_account&.domain
diff --git a/app/controllers/api/v1/accounts/statuses_controller.rb b/app/controllers/api/v1/accounts/statuses_controller.rb
index a0ce810ad..91b8629e3 100644
--- a/app/controllers/api/v1/accounts/statuses_controller.rb
+++ b/app/controllers/api/v1/accounts/statuses_controller.rb
@@ -22,7 +22,7 @@ class Api::V1::Accounts::StatusesController < Api::BaseController
   end
 
   def load_statuses
-    @account.suspended? ? [] : cached_account_statuses
+    unauthorized? ? [] : cached_account_statuses
   end
 
   def cached_account_statuses
@@ -39,7 +39,6 @@ class Api::V1::Accounts::StatusesController < Api::BaseController
 
   def permitted_account_statuses
     return mentions_scope if truthy_param?(:mentions)
-    return Status.none if unauthorized?
 
     @account.statuses.permitted_for(
       @account,
@@ -58,7 +57,7 @@ class Api::V1::Accounts::StatusesController < Api::BaseController
   end
 
   def unauthorized?
-    (@account.private && !following?(@account)) || (@account.require_auth && !current_account?)
+    @account.suspended? || (@account.private? && !following?(@account))
   end
 
   def include_reblogs?
diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb
index 5e12e89c8..9074e6450 100644
--- a/app/controllers/application_controller.rb
+++ b/app/controllers/application_controller.rb
@@ -49,7 +49,7 @@ class ApplicationController < ActionController::Base
   end
 
   def authorized_fetch_mode?
-    !(Rails.env.development? || Rails.env.test?)
+    !(current_account&.allow_anonymous? || (@account&.id && current_user&.account_id == @account.id) || Rails.env.development? || Rails.env.test?)
   end
 
   def public_fetch_mode?
@@ -90,8 +90,8 @@ class ApplicationController < ActionController::Base
     end
   end
 
-  def require_following!(account)
-    forbidden unless following?(account)
+  def require_following!
+    forbidden unless @account.present? && following?(@account)
   end
 
   def after_sign_out_path_for(_resource_or_scope)
diff --git a/app/controllers/settings/preferences_controller.rb b/app/controllers/settings/preferences_controller.rb
index 7e42d4e40..e8d45ff2a 100644
--- a/app/controllers/settings/preferences_controller.rb
+++ b/app/controllers/settings/preferences_controller.rb
@@ -76,7 +76,6 @@ class Settings::PreferencesController < Settings::BaseController
       :setting_boost_random,
       :setting_filter_unknown,
       :setting_unpublish_on_delete,
-      :setting_rss_disabled,
       :setting_home_reblogs,
       :setting_max_history_public,
       :setting_max_history_private,
diff --git a/app/controllers/settings/profiles_controller.rb b/app/controllers/settings/profiles_controller.rb
index e71ebbb10..93d08ee4b 100644
--- a/app/controllers/settings/profiles_controller.rb
+++ b/app/controllers/settings/profiles_controller.rb
@@ -21,7 +21,7 @@ class Settings::ProfilesController < Settings::BaseController
 
   def account_params
     params.require(:account).permit(:display_name, :note, :avatar, :header, :locked, :bot, :discoverable,
-                                    :show_replies, :show_unlisted, :private, :require_auth,
+                                    :show_replies, :show_unlisted, :private, :allow_anonymous, :no_verify_auth,
                                     fields_attributes: [:name, :value])
   end
 
diff --git a/app/controllers/statuses_controller.rb b/app/controllers/statuses_controller.rb
index ad065a6fa..27575e414 100644
--- a/app/controllers/statuses_controller.rb
+++ b/app/controllers/statuses_controller.rb
@@ -8,10 +8,9 @@ class StatusesController < ApplicationController
 
   layout 'public'
 
-  before_action :require_signature!, only: :show, if: -> { request.format == :json && authorized_fetch_mode? && current_user&.account_id != @account.id }
-  before_action :require_authenticated!, if: -> { @account.require_auth? }
-  before_action -> { require_following!(@account) }, if: -> { request.format != :json && @account.private? }
+  before_action :require_signature!, only: :show, if: -> { request.format == :json && authorized_fetch_mode? }
   before_action :set_status
+  before_action :require_following!, if: -> { @account.private? && !(@status.public_visibility? || @status.unlisted_visibility?) }
   before_action :set_instance_presenter
   before_action :set_link_headers
   before_action :redirect_to_original, only: :show
diff --git a/app/lib/activitypub/activity/announce.rb b/app/lib/activitypub/activity/announce.rb
index 327def623..21fe556af 100644
--- a/app/lib/activitypub/activity/announce.rb
+++ b/app/lib/activitypub/activity/announce.rb
@@ -44,9 +44,9 @@ class ActivityPub::Activity::Announce < ActivityPub::Activity
 
   def visibility_from_audience
     if audience_to.include?(ActivityPub::TagManager::COLLECTIONS[:public])
-      :public
+      @account.private? ? :private : :public
     elsif audience_cc.include?(ActivityPub::TagManager::COLLECTIONS[:public])
-      :unlisted
+      @account.private? ? :private : :unlisted
     elsif audience_to.include?(@account.followers_url)
       :private
     else
diff --git a/app/lib/activitypub/activity/create.rb b/app/lib/activitypub/activity/create.rb
index 98bcada7a..3053b1bb3 100644
--- a/app/lib/activitypub/activity/create.rb
+++ b/app/lib/activitypub/activity/create.rb
@@ -462,9 +462,9 @@ class ActivityPub::Activity::Create < ActivityPub::Activity
 
   def visibility_from_audience
     if audience_to.include?(ActivityPub::TagManager::COLLECTIONS[:public])
-      :public
+      @account.private? ? :private : :public
     elsif audience_cc.include?(ActivityPub::TagManager::COLLECTIONS[:public])
-      :unlisted
+      @account.private? ? :private : :unlisted
     elsif audience_to.include?(@account.followers_url)
       :private
     elsif direct_message == false
diff --git a/app/lib/activitypub/adapter.rb b/app/lib/activitypub/adapter.rb
index 3063f7a4b..6fcf219be 100644
--- a/app/lib/activitypub/adapter.rb
+++ b/app/lib/activitypub/adapter.rb
@@ -12,7 +12,6 @@ class ActivityPub::Adapter < ActiveModelSerializers::Adapter::Base
     show_replies: { 'mp' => 'https://the.monsterpit.net/ns#', 'showReplies' => 'mp:showReplies' },
     show_unlisted: { 'mp' => 'https://the.monsterpit.net/ns#', 'showUnlisted' => 'mp:showUnlisted' },
     private: { 'mp' => 'https://the.monsterpit.net/ns#', 'private' => 'mp:private' },
-    require_auth: { 'mp' => 'https://the.monsterpit.net/ns#', 'requireAuth' => 'mp:requireAuth' },
     metadata: { 'mp' => 'https://the.monsterpit.net/ns#', 'metadata' => { '@id' => 'mp:metadata', '@type' => '@id' } },
     server_metadata: { 'mp' => 'https://the.monsterpit.net/ns#', 'serverMetadata' => { '@id' => 'mp:serverMetadata', '@type' => '@id' } },
     root: { 'mp' => 'https://the.monsterpit.net/ns#', 'root' => { '@id' => 'mp:root', '@type' => '@id' } },
diff --git a/app/lib/user_settings_decorator.rb b/app/lib/user_settings_decorator.rb
index 0f927d5d0..ca6c09a3a 100644
--- a/app/lib/user_settings_decorator.rb
+++ b/app/lib/user_settings_decorator.rb
@@ -63,7 +63,6 @@ class UserSettingsDecorator
     user.settings['boost_random']        = boost_random_preference if change?('setting_boost_random')
     user.settings['filter_unknown']      = filter_unknown_preference if change?('setting_filter_unknown')
     user.settings['unpublish_on_delete'] = unpublish_on_delete_preference if change?('setting_unpublish_on_delete')
-    user.settings['rss_disabled']        = rss_disabled_preference if change?('setting_rss_disabled')
     user.settings['home_reblogs']        = home_reblogs_preference if change?('setting_home_reblogs')
     user.settings['max_history_public']  = max_history_public_preference if change?('setting_max_history_public')
     user.settings['max_history_private'] = max_history_private_preference if change?('setting_max_history_private')
@@ -246,10 +245,6 @@ class UserSettingsDecorator
     boolean_cast_setting 'setting_unpublish_on_delete'
   end
 
-  def rss_disabled_preference
-    boolean_cast_setting 'setting_rss_disabled'
-  end
-
   def home_reblogs_preference
     boolean_cast_setting 'setting_home_reblogs'
   end
diff --git a/app/models/account.rb b/app/models/account.rb
index 90145ceb2..bf286d111 100644
--- a/app/models/account.rb
+++ b/app/models/account.rb
@@ -53,10 +53,11 @@
 #  show_replies                  :boolean          default(TRUE), not null
 #  show_unlisted                 :boolean          default(TRUE), not null
 #  private                       :boolean          default(FALSE), not null
-#  require_auth                  :boolean          default(FALSE), not null
 #  last_synced_at                :datetime
 #  sensitized_at                 :datetime
 #  suspension_origin             :integer
+#  no_verify_auth                :boolean          default(FALSE), not null
+#  allow_anonymous               :boolean          default(FALSE), not null
 #
 
 class Account < ApplicationRecord
diff --git a/app/models/status.rb b/app/models/status.rb
index 73eda2c4c..f20e7710d 100644
--- a/app/models/status.rb
+++ b/app/models/status.rb
@@ -254,7 +254,7 @@ class Status < ApplicationRecord
   end
 
   def distributable?
-    public_visibility? || unlisted_visibility?
+    !account.private? && (public_visibility? || unlisted_visibility?)
   end
 
   alias sign? distributable?
@@ -344,6 +344,7 @@ class Status < ApplicationRecord
 
   def visibility_for_domain(domain)
     return visibility.to_s if domain.blank?
+    return 'private' if account.private?
 
     v = domain_permissions.find_by(domain: [domain, '*'])&.visibility || visibility.to_s
 
@@ -659,7 +660,7 @@ class Status < ApplicationRecord
     if reply? && !thread.nil?
       self.in_reply_to_account_id = carried_over_reply_to_account_id
       self.conversation_id        = thread.conversation_id if conversation_id.nil?
-      self.visibility             = :limited if visibility.to_s == 'private' && in_reply_to_account_id != account_id
+      self.visibility             = :limited if in_reply_to_account_id != account_id && (visibility.to_s == 'private' || account.private?)
     end
   end
 
diff --git a/app/models/user.rb b/app/models/user.rb
index 8d91593ae..d3ac464d7 100644
--- a/app/models/user.rb
+++ b/app/models/user.rb
@@ -124,7 +124,7 @@ class User < ApplicationRecord
            :style_css_profile_errors, :style_css_webapp, :style_css_webapp_errors,
            :style_wide_media, :style_lowercase,
            :publish_in, :unpublish_in, :unpublish_delete, :boost_every, :boost_jitter,
-           :boost_random, :unpublish_on_delete, :rss_disabled, :home_reblogs,
+           :boost_random, :unpublish_on_delete, :home_reblogs,
            :filter_unknown, :max_history_public, :max_history_private, :web_push,
            to: :settings, prefix: :setting, allow_nil: false
 
diff --git a/app/policies/status_policy.rb b/app/policies/status_policy.rb
index 56c217cec..c16ec29ed 100644
--- a/app/policies/status_policy.rb
+++ b/app/policies/status_policy.rb
@@ -18,10 +18,12 @@ class StatusPolicy < ApplicationPolicy
 
     if requires_mention?
       owned? || mention_exists?
+    elsif author.private? && public?
+      !(author_blocking? || author_blocking_domain?)
     elsif private?
       owned? || following_author? || mention_exists?
     else
-      current_account.nil? || (!author_blocking? && !author_blocking_domain?)
+      current_account.nil? || !(author_blocking? || author_blocking_domain?)
     end
   end
 
@@ -80,7 +82,7 @@ class StatusPolicy < ApplicationPolicy
   end
 
   def author_blocking?
-    return author.require_auth? if current_account.nil?
+    return false if current_account.nil?
 
     @preloaded_relations[:blocked_by] ? @preloaded_relations[:blocked_by][author.id] : author.blocking?(current_account)
   end
@@ -94,7 +96,7 @@ class StatusPolicy < ApplicationPolicy
   def author
     record.account
   end
-  
+
   def local_only?
     record.local_only?
   end
@@ -103,6 +105,10 @@ class StatusPolicy < ApplicationPolicy
     record.published?
   end
 
+  def public?
+    record.public_visibility? || record.unlisted_visibility?
+  end
+
   def visibility_for_remote_domain
     @visibility_for_domain ||= record.visibility_for_domain(current_account&.domain)
   end
diff --git a/app/presenters/activitypub/activity_presenter.rb b/app/presenters/activitypub/activity_presenter.rb
index e17f8bb98..dbeeb5316 100644
--- a/app/presenters/activitypub/activity_presenter.rb
+++ b/app/presenters/activitypub/activity_presenter.rb
@@ -14,7 +14,7 @@ class ActivityPub::ActivityPresenter < ActiveModelSerializers::Model
         presenter.to        = ActivityPub::TagManager.instance.to(status, domain)
         presenter.cc        = ActivityPub::TagManager.instance.cc(status, domain)
 
-        unless embed
+        unless embed || status.account.no_verify_auth?
           presenter.virtual_object = ActivityPub::TagManager.instance.uri_for(status.proper)
           next
         end
diff --git a/app/serializers/activitypub/actor_serializer.rb b/app/serializers/activitypub/actor_serializer.rb
index 38c566937..ebaf2d093 100644
--- a/app/serializers/activitypub/actor_serializer.rb
+++ b/app/serializers/activitypub/actor_serializer.rb
@@ -25,8 +25,8 @@ class ActivityPub::ActorSerializer < ActivityPub::Serializer
   attribute :also_known_as, if: :also_known_as?
   attribute :suspended, if: :suspended?
 
-  context_extensions :show_replies, :private, :require_auth, :metadata, :server_metadata
-  attributes :show_replies, :show_unlisted, :private, :require_auth
+  context_extensions :show_replies, :private, :metadata, :server_metadata
+  attributes :show_replies, :show_unlisted, :private
   attributes :metadata, :server_metadata
 
   class EndpointsSerializer < ActivityPub::Serializer
diff --git a/app/services/activitypub/process_account_service.rb b/app/services/activitypub/process_account_service.rb
index ec1041b3d..049ceae83 100644
--- a/app/services/activitypub/process_account_service.rb
+++ b/app/services/activitypub/process_account_service.rb
@@ -95,7 +95,6 @@ class ActivityPub::ProcessAccountService < BaseService
     @account.show_replies            = @json['showReplies'] || true
     @account.show_unlisted           = @json['showUnlisted'] || true
     @account.private                 = @json['private'] || false
-    @account.require_auth            = @json['require_auth'] || false
   end
 
   def set_fetchable_attributes!
diff --git a/app/services/concerns/payloadable.rb b/app/services/concerns/payloadable.rb
index ba94539c8..1492f8076 100644
--- a/app/services/concerns/payloadable.rb
+++ b/app/services/concerns/payloadable.rb
@@ -7,14 +7,10 @@ module Payloadable
     payload   = ActiveModelSerializers::SerializableResource.new(record, options.merge(serializer: serializer, adapter: ActivityPub::Adapter)).as_json
     object    = record.respond_to?(:virtual_object) ? record.virtual_object : record
 
-    if (object.respond_to?(:sign?) && object.sign?) && signer && signing_enabled?
+    if (object.respond_to?(:sign?) && object.sign?) && signer && !signer.allow_anonymous?
       ActivityPub::LinkedDataSignature.new(payload).sign!(signer, sign_with: sign_with)
     else
       payload
     end
   end
-
-  def signing_enabled?
-    true
-  end
 end
diff --git a/app/services/fan_out_on_write_service.rb b/app/services/fan_out_on_write_service.rb
index 1fa8b2520..679ba8501 100644
--- a/app/services/fan_out_on_write_service.rb
+++ b/app/services/fan_out_on_write_service.rb
@@ -21,15 +21,12 @@ class FanOutOnWriteService < BaseService
       deliver_to_lists(status)
     end
 
-    return if status.account.silenced?
+    return if !status.public_visibility? || status.account.silenced?
     return if status.reblog? && !Setting.show_reblogs_in_public_timelines
 
-    if status.distributable?
-      render_anonymous_payload(status)
-      deliver_to_hashtags(status)
-    end
+    render_anonymous_payload(status)
+    deliver_to_hashtags(status)
 
-    return unless status.public_visibility?
     return if status.reply? && status.in_reply_to_account_id != status.account_id && !Setting.show_replies_in_public_timelines
 
     deliver_to_public(status)
diff --git a/app/services/process_hashtags_service.rb b/app/services/process_hashtags_service.rb
index 5ec5ea0c2..51c152164 100644
--- a/app/services/process_hashtags_service.rb
+++ b/app/services/process_hashtags_service.rb
@@ -13,10 +13,10 @@ class ProcessHashtagsService < BaseService
       status.tags << tag
       records << tag
 
-      TrendingTags.record_use!(tag, status.account, status.created_at) if status.distributable?
+      TrendingTags.record_use!(tag, status.account, status.created_at) if status.public_visibility?
     end
 
-    return unless status.distributable?
+    return unless status.public_visibility?
 
     status.account.featured_tags.where(tag_id: records.map(&:id)).each do |featured_tag|
       featured_tag.increment(status.created_at)
diff --git a/app/services/reblog_service.rb b/app/services/reblog_service.rb
index ef7468194..b694bc500 100644
--- a/app/services/reblog_service.rb
+++ b/app/services/reblog_service.rb
@@ -32,7 +32,7 @@ class ReblogService < BaseService
     curate!(reblogged_status) unless reblogged_status.curated? || !reblogged_status.published?
 
     DistributionWorker.perform_async(reblog.id)
-    ActivityPub::DistributionWorker.perform_async(reblog.id) unless reblogged_status.local_only?
+    ActivityPub::DistributionWorker.perform_async(reblog.id) unless reblogged_status.local_only? || reblogged_status.account.private?
 
     create_notification(reblog)
     bump_potential_friendship(account, reblog)
diff --git a/app/services/remove_hashtags_service.rb b/app/services/remove_hashtags_service.rb
index 6bf77a068..af2ba6f8c 100644
--- a/app/services/remove_hashtags_service.rb
+++ b/app/services/remove_hashtags_service.rb
@@ -8,7 +8,7 @@ class RemoveHashtagsService < BaseService
       featured_tag.decrement(status.id)
     end
 
-    if status.distributable?
+    if status.public_visibility?
       delete_payload = Oj.dump(event: :delete, payload: status.id.to_s)
       tags.pluck(:name).each do |hashtag|
         redis.publish("timeline:hashtag:#{hashtag.mb_chars.downcase}", delete_payload)
diff --git a/app/services/remove_status_service.rb b/app/services/remove_status_service.rb
index beb415f94..e6ecfbc56 100644
--- a/app/services/remove_status_service.rb
+++ b/app/services/remove_status_service.rb
@@ -144,7 +144,7 @@ class RemoveStatusService < BaseService
       featured_tag.decrement(@status.id)
     end
 
-    return unless @status.distributable?
+    return unless @status.public_visibility?
 
     @tags.each do |hashtag|
       redis.publish("timeline:hashtag:#{hashtag.mb_chars.downcase}", @payload)
@@ -153,7 +153,7 @@ class RemoveStatusService < BaseService
   end
 
   def remove_from_public
-    return unless @status.distributable?
+    return unless @status.public_visibility?
 
     redis.publish('timeline:public', @payload)
     redis.publish('timeline:public:local', @payload) if @status.local?
@@ -161,7 +161,7 @@ class RemoveStatusService < BaseService
   end
 
   def remove_from_media
-    return unless @status.distributable?
+    return unless @status.public_visibility?
 
     redis.publish('timeline:public:media', @payload)
     redis.publish('timeline:public:local:media', @payload) if @status.local?
diff --git a/app/services/revoke_status_service.rb b/app/services/revoke_status_service.rb
index f4762631c..d860ab278 100644
--- a/app/services/revoke_status_service.rb
+++ b/app/services/revoke_status_service.rb
@@ -62,7 +62,7 @@ class RevokeStatusService < BaseService
       featured_tag.decrement(@status.id)
     end
 
-    return unless @status.distributable?
+    return unless @status.public_visibility?
 
     @tags.each do |hashtag|
       redis.publish("timeline:hashtag:#{hashtag.mb_chars.downcase}", @payload)
@@ -71,7 +71,7 @@ class RevokeStatusService < BaseService
   end
 
   def remove_from_public
-    return if @status.distributable?
+    return if @status.public_visibility?
 
     redis.publish('timeline:public', @payload)
     redis.publish('timeline:public:local', @payload) if @status.local?
@@ -79,7 +79,7 @@ class RevokeStatusService < BaseService
   end
 
   def remove_from_media
-    return if @status.distributable?
+    return if @status.public_visibility?
 
     redis.publish('timeline:public:media', @payload)
     redis.publish('timeline:public:local:media', @payload) if @status.local?
diff --git a/app/views/settings/preferences/privacy/show.html.haml b/app/views/settings/preferences/privacy/show.html.haml
index 8f7199665..55d27844a 100644
--- a/app/views/settings/preferences/privacy/show.html.haml
+++ b/app/views/settings/preferences/privacy/show.html.haml
@@ -29,9 +29,6 @@
   .fields-group
     = f.input :setting_hide_network, as: :boolean, wrapper: :with_label
 
-  .fields-group
-    = f.input :setting_rss_disabled, as: :boolean, wrapper: :with_label
-
   - unless Setting.hide_followers_count
     .fields-group
       = f.input :setting_hide_followers_count, as: :boolean, wrapper: :with_label
diff --git a/app/views/settings/profiles/show.html.haml b/app/views/settings/profiles/show.html.haml
index ef2600169..8c6c4c933 100644
--- a/app/views/settings/profiles/show.html.haml
+++ b/app/views/settings/profiles/show.html.haml
@@ -46,8 +46,15 @@
   .fields-group
     = f.input :private, as: :boolean, wrapper: :with_label, hint: t('simple_form.hints.defaults.private')
 
+  %h4= t 'settings.profiles.compatibility'
+
+  %p.hint= t 'settings.profiles.compatibility_html'
+
+  .fields-group
+    = f.input :no_verify_auth, as: :boolean, wrapper: :with_label, hint: t('simple_form.hints.defaults.no_verify_auth_html')
+
   .fields-group
-    = f.input :require_auth, as: :boolean, wrapper: :with_label, hint: t('simple_form.hints.defaults.require_auth')
+    = f.input :allow_anonymous, as: :boolean, wrapper: :with_label, hint: t('simple_form.hints.defaults.allow_anonymous_html')
 
   %hr.spacer/
 
diff --git a/app/workers/activitypub/distribute_poll_update_worker.rb b/app/workers/activitypub/distribute_poll_update_worker.rb
index 601075ea6..ed5447341 100644
--- a/app/workers/activitypub/distribute_poll_update_worker.rb
+++ b/app/workers/activitypub/distribute_poll_update_worker.rb
@@ -24,7 +24,7 @@ class ActivityPub::DistributePollUpdateWorker
   private
 
   def relayable?
-    @status.public_visibility?
+    @status.public_visibility? && !@account.private?
   end
 
   def inboxes
diff --git a/app/workers/activitypub/distribution_worker.rb b/app/workers/activitypub/distribution_worker.rb
index a8365ce8d..4d7527b46 100644
--- a/app/workers/activitypub/distribution_worker.rb
+++ b/app/workers/activitypub/distribution_worker.rb
@@ -30,7 +30,7 @@ class ActivityPub::DistributionWorker
   end
 
   def relayable?
-    @status.public_visibility?
+    @status.public_visibility? && !@account.private?
   end
 
   def inboxes
diff --git a/config/locales/en-MP.yml b/config/locales/en-MP.yml
index 420ae59b0..0f6a5b484 100644
--- a/config/locales/en-MP.yml
+++ b/config/locales/en-MP.yml
@@ -154,8 +154,8 @@ en-MP:
     profiles:
       privacy: Privacy
       privacy_html: These options allow you to adjust how much information is visible on your public profile on Monsterpit.  <strong>Be aware that other servers you send your roars to have their own profile systems and may not honor these options.  You will need to use <em>followers-only</em> or <em>direct</em> privacy for roars you do not want displayed in other servers' public profiles.</strong>
-      advanced_privacy: Advanced privacy
-      advanced_privacy_html: These options can increase your privacy at the expense of compatability with other servers. <strong>They can potentially cause roars to not be delivered to some of your followers.  Only enable them if you're fully aware of their side effects.</strong>
+      compatibility: Compatability
+      compatibility_html: These options will increase the compatability of your account and roars with older Fediverse servers at the expense of your privacy. <strong>Only use them if you're fully aware of their possible side effects, which are beyond the scope of support from Monsterpit's developers!</strong>
   timer:
     '0': Never
     1: 1 minute
diff --git a/config/locales/simple_form.en-MP.yml b/config/locales/simple_form.en-MP.yml
index 0430b02e2..75ae679c7 100644
--- a/config/locales/simple_form.en-MP.yml
+++ b/config/locales/simple_form.en-MP.yml
@@ -11,10 +11,11 @@ en-MP:
       announcement:
         text: You can use roar syntax. Please be mindful of the space the announcement will take up on the user's screen
       defaults:
+        allow_anonymous_html: "If enabled, public and unlisted roars can be read by anyone and any software without authentication. <strong>Be aware that this will allow accounts and servers you've blocked to continue accessing and redistributing your public roars!</strong>"
         irreversible: Filtered roars will disappear irreversibly, even if filter is later removed
+        no_verify_auth_html: "Deliver roars to participants on other servers without requiring their software to prove the authenticity of their accounts to Monsterpit.  Enabling this option makes it possible to interact with folks on servers using old versions of Mastodon (&lt; 3.2.0), but <strong>doing so can allow an attacker to trick Monsterpit into sending them your private roars</strong>."
         phrase: Will be matched regardless of casing in text or content warning of a roar
-        private: Only allow authenticated followers to view your local profile.
-        require_auth: Require viewers to log in to access your profile, roars, and threads from Monsterpit.
+        private: Limit the visibility of your profile to followers and force other Fediverse servers to make your roars private, reguardless of their local visibility.
         setting_aggregate_reblogs: Do not show new boosts for roars that have been recently boosted (only affects newly-received boosts)
         setting_default_content_type_html: When composing roars, assume they are written in raw HTML, unless specified otherwise
         setting_default_content_type_markdown: When composing roars, assume they are using Markdown for rich text formatting, unless specified otherwise
@@ -45,9 +46,10 @@ en-MP:
       admin_account_action:
         include_statuses: Include reported roars in the e-mail
       defaults:
+        allow_anonymous: Allow anonymous access to public roars
         bot: This is an automated account
+        no_verify_auth: Do not verify message recipients
         private: Private mode
-        require_auth: Disallow anonymous access
         setting_crop_images: Crop images in non-expanded roars to 16x9
         setting_default_content_type: Default format for roars
         setting_default_language: Roar language
diff --git a/db/migrate/20201123152231_add_no_verify_auth_to_accounts.rb b/db/migrate/20201123152231_add_no_verify_auth_to_accounts.rb
new file mode 100644
index 000000000..38f5bc046
--- /dev/null
+++ b/db/migrate/20201123152231_add_no_verify_auth_to_accounts.rb
@@ -0,0 +1,7 @@
+class AddNoVerifyAuthToAccounts < ActiveRecord::Migration[5.2]
+  def change
+    safety_assured do
+      add_column :accounts, :no_verify_auth, :boolean, null: false, default: false
+    end
+  end
+end
diff --git a/db/migrate/20201123171722_add_allow_anonymous_to_accounts.rb b/db/migrate/20201123171722_add_allow_anonymous_to_accounts.rb
new file mode 100644
index 000000000..c7fdfba14
--- /dev/null
+++ b/db/migrate/20201123171722_add_allow_anonymous_to_accounts.rb
@@ -0,0 +1,5 @@
+class AddAllowAnonymousToAccounts < ActiveRecord::Migration[5.2]
+  def change
+    add_column :accounts, :allow_anonymous, :boolean, null: false, default: false
+  end
+end
diff --git a/db/migrate/20201124005733_remove_require_auth_from_accounts.rb b/db/migrate/20201124005733_remove_require_auth_from_accounts.rb
new file mode 100644
index 000000000..3f64b539a
--- /dev/null
+++ b/db/migrate/20201124005733_remove_require_auth_from_accounts.rb
@@ -0,0 +1,7 @@
+class RemoveRequireAuthFromAccounts < ActiveRecord::Migration[5.2]
+  def change
+    safety_assured do
+      remove_column :accounts, :require_auth, :boolean, null: false, default: false
+    end
+  end
+end
diff --git a/db/schema.rb b/db/schema.rb
index 273e942f5..346177241 100644
--- a/db/schema.rb
+++ b/db/schema.rb
@@ -10,7 +10,7 @@
 #
 # It's strongly recommended that you check this file into your version control system.
 
-ActiveRecord::Schema.define(version: 2020_11_19_035441) do
+ActiveRecord::Schema.define(version: 2020_11_24_005733) do
 
   # These are extensions that must be enabled in order to support this database
   enable_extension "plpgsql"
@@ -209,10 +209,11 @@ ActiveRecord::Schema.define(version: 2020_11_19_035441) do
     t.boolean "show_replies", default: true, null: false
     t.boolean "show_unlisted", default: true, null: false
     t.boolean "private", default: false, null: false
-    t.boolean "require_auth", default: false, null: false
     t.datetime "last_synced_at"
     t.datetime "sensitized_at"
     t.integer "suspension_origin"
+    t.boolean "no_verify_auth", default: false, null: false
+    t.boolean "allow_anonymous", default: false, null: false
     t.index "(((setweight(to_tsvector('simple'::regconfig, (display_name)::text), 'A'::\"char\") || setweight(to_tsvector('simple'::regconfig, (username)::text), 'B'::\"char\")) || setweight(to_tsvector('simple'::regconfig, (COALESCE(domain, ''::character varying))::text), 'C'::\"char\")))", name: "search_index", using: :gin
     t.index "lower((username)::text), COALESCE(lower((domain)::text), ''::text)", name: "index_accounts_on_username_and_domain_lower", unique: true
     t.index ["moved_to_account_id"], name: "index_accounts_on_moved_to_account_id"