mirror of
https://github.com/glitch-soc/mastodon.git
synced 2025-12-18 10:37:45 +00:00
Merge commit 'd7d6407d4196ab6783485b20a3d9e2fbfc00ef01' into glitch-soc/merge-4.4
This commit is contained in:
@@ -9,10 +9,16 @@ module Admin
|
|||||||
|
|
||||||
@pending_appeals_count = Appeal.pending.async_count
|
@pending_appeals_count = Appeal.pending.async_count
|
||||||
@pending_reports_count = Report.unresolved.async_count
|
@pending_reports_count = Report.unresolved.async_count
|
||||||
@pending_tags_count = Tag.pending_review.async_count
|
@pending_tags_count = pending_tags.async_count
|
||||||
@pending_users_count = User.pending.async_count
|
@pending_users_count = User.pending.async_count
|
||||||
@system_checks = Admin::SystemCheck.perform(current_user)
|
@system_checks = Admin::SystemCheck.perform(current_user)
|
||||||
@time_period = (29.days.ago.to_date...Time.now.utc.to_date)
|
@time_period = (29.days.ago.to_date...Time.now.utc.to_date)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
private
|
||||||
|
|
||||||
|
def pending_tags
|
||||||
|
::Trends::TagFilter.new(status: :pending_review).results
|
||||||
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -217,11 +217,11 @@ class ActivityPub::Activity::Create < ActivityPub::Activity
|
|||||||
|
|
||||||
def process_quote
|
def process_quote
|
||||||
@quote_uri = @status_parser.quote_uri
|
@quote_uri = @status_parser.quote_uri
|
||||||
return if @quote_uri.blank?
|
return unless @status_parser.quote?
|
||||||
|
|
||||||
approval_uri = @status_parser.quote_approval_uri
|
approval_uri = @status_parser.quote_approval_uri
|
||||||
approval_uri = nil if unsupported_uri_scheme?(approval_uri)
|
approval_uri = nil if unsupported_uri_scheme?(approval_uri) || TagManager.instance.local_url?(approval_uri)
|
||||||
@quote = Quote.new(account: @account, approval_uri: approval_uri, legacy: @status_parser.legacy_quote?)
|
@quote = Quote.new(account: @account, approval_uri: approval_uri, legacy: @status_parser.legacy_quote?, state: @status_parser.deleted_quote? ? :deleted : :pending)
|
||||||
end
|
end
|
||||||
|
|
||||||
def process_hashtag(tag)
|
def process_hashtag(tag)
|
||||||
|
|||||||
@@ -119,6 +119,14 @@ class ActivityPub::Parser::StatusParser
|
|||||||
flags
|
flags
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def quote?
|
||||||
|
%w(quote _misskey_quote quoteUrl quoteUri).any? { |key| @object[key].present? }
|
||||||
|
end
|
||||||
|
|
||||||
|
def deleted_quote?
|
||||||
|
@object['quote'].is_a?(Hash) && @object['quote']['type'] == 'Tombstone'
|
||||||
|
end
|
||||||
|
|
||||||
def quote_uri
|
def quote_uri
|
||||||
%w(quote _misskey_quote quoteUrl quoteUri).filter_map do |key|
|
%w(quote _misskey_quote quoteUrl quoteUri).filter_map do |key|
|
||||||
value_or_id(as_array(@object[key]).first)
|
value_or_id(as_array(@object[key]).first)
|
||||||
|
|||||||
@@ -21,7 +21,7 @@ class Quote < ApplicationRecord
|
|||||||
REFRESH_DEADLINE = 6.hours
|
REFRESH_DEADLINE = 6.hours
|
||||||
|
|
||||||
enum :state,
|
enum :state,
|
||||||
{ pending: 0, accepted: 1, rejected: 2, revoked: 3 },
|
{ pending: 0, accepted: 1, rejected: 2, revoked: 3, deleted: 4 },
|
||||||
validate: true
|
validate: true
|
||||||
|
|
||||||
belongs_to :status
|
belongs_to :status
|
||||||
|
|||||||
@@ -74,6 +74,8 @@ class ActivityPub::ProcessStatusUpdateService < BaseService
|
|||||||
update_quote_approval!
|
update_quote_approval!
|
||||||
update_counts!
|
update_counts!
|
||||||
end
|
end
|
||||||
|
|
||||||
|
broadcast_updates! if @status.quote&.state_previously_changed?
|
||||||
end
|
end
|
||||||
|
|
||||||
def update_interaction_policies!
|
def update_interaction_policies!
|
||||||
@@ -298,15 +300,17 @@ class ActivityPub::ProcessStatusUpdateService < BaseService
|
|||||||
def update_quote!
|
def update_quote!
|
||||||
quote_uri = @status_parser.quote_uri
|
quote_uri = @status_parser.quote_uri
|
||||||
|
|
||||||
if quote_uri.present?
|
if @status_parser.quote?
|
||||||
approval_uri = @status_parser.quote_approval_uri
|
approval_uri = @status_parser.quote_approval_uri
|
||||||
approval_uri = nil if unsupported_uri_scheme?(approval_uri)
|
approval_uri = nil if unsupported_uri_scheme?(approval_uri)
|
||||||
|
|
||||||
if @status.quote.present?
|
if @status.quote.present?
|
||||||
|
state = @status_parser.deleted_quote? ? :deleted : :pending
|
||||||
|
|
||||||
# If the quoted post has changed, discard the old object and create a new one
|
# If the quoted post has changed, discard the old object and create a new one
|
||||||
if @status.quote.quoted_status.present? && ActivityPub::TagManager.instance.uri_for(@status.quote.quoted_status) != quote_uri
|
if @status.quote.quoted_status.present? && ActivityPub::TagManager.instance.uri_for(@status.quote.quoted_status) != quote_uri
|
||||||
@status.quote.destroy
|
@status.quote.destroy
|
||||||
quote = Quote.create(status: @status, approval_uri: approval_uri, legacy: @status_parser.legacy_quote?)
|
quote = Quote.create(status: @status, approval_uri: approval_uri, legacy: @status_parser.legacy_quote?, state: state)
|
||||||
@quote_changed = true
|
@quote_changed = true
|
||||||
else
|
else
|
||||||
quote = @status.quote
|
quote = @status.quote
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ class ActivityPub::RefetchAndVerifyQuoteWorker
|
|||||||
def perform(quote_id, quoted_uri, options = {})
|
def perform(quote_id, quoted_uri, options = {})
|
||||||
quote = Quote.find(quote_id)
|
quote = Quote.find(quote_id)
|
||||||
ActivityPub::VerifyQuoteService.new.call(quote, fetchable_quoted_uri: quoted_uri, request_id: options[:request_id])
|
ActivityPub::VerifyQuoteService.new.call(quote, fetchable_quoted_uri: quoted_uri, request_id: options[:request_id])
|
||||||
|
::DistributionWorker.perform_async(quote.status_id, { 'update' => true }) if quote.state_previously_changed?
|
||||||
rescue ActiveRecord::RecordNotFound
|
rescue ActiveRecord::RecordNotFound
|
||||||
# Do nothing
|
# Do nothing
|
||||||
true
|
true
|
||||||
|
|||||||
@@ -988,6 +988,30 @@ RSpec.describe ActivityPub::Activity::Create do
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
context 'with an unverifiable quote of a dead post' do
|
||||||
|
let(:quoted_status) { Fabricate(:status) }
|
||||||
|
|
||||||
|
let(:object_json) do
|
||||||
|
build_object(
|
||||||
|
type: 'Note',
|
||||||
|
content: 'woah what she said is amazing',
|
||||||
|
quote: { type: 'Tombstone' }
|
||||||
|
)
|
||||||
|
end
|
||||||
|
|
||||||
|
it 'creates a status with an unverified quote' do
|
||||||
|
expect { subject.perform }.to change(sender.statuses, :count).by(1)
|
||||||
|
|
||||||
|
status = sender.statuses.first
|
||||||
|
expect(status).to_not be_nil
|
||||||
|
expect(status.quote).to_not be_nil
|
||||||
|
expect(status.quote).to have_attributes(
|
||||||
|
state: 'deleted',
|
||||||
|
approval_uri: nil
|
||||||
|
)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
context 'with an unverifiable unknown post' do
|
context 'with an unverifiable unknown post' do
|
||||||
let(:unknown_post_uri) { 'https://unavailable.example.com/unavailable-post' }
|
let(:unknown_post_uri) { 'https://unavailable.example.com/unavailable-post' }
|
||||||
|
|
||||||
|
|||||||
@@ -976,6 +976,44 @@ RSpec.describe ActivityPub::ProcessStatusUpdateService do
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
context 'when the status swaps a verified quote with an ID-less Tombstone through an explicit update' do
|
||||||
|
let(:quoted_account) { Fabricate(:account, domain: 'quoted.example.com') }
|
||||||
|
let(:quoted_status) { Fabricate(:status, account: quoted_account) }
|
||||||
|
let(:second_quoted_status) { Fabricate(:status, account: quoted_account) }
|
||||||
|
let!(:quote) { Fabricate(:quote, status: status, quoted_status: quoted_status, approval_uri: approval_uri, state: :accepted) }
|
||||||
|
let(:approval_uri) { 'https://quoted.example.com/approvals/1' }
|
||||||
|
|
||||||
|
let(:payload) do
|
||||||
|
{
|
||||||
|
'@context': [
|
||||||
|
'https://www.w3.org/ns/activitystreams',
|
||||||
|
{
|
||||||
|
'@id': 'https://w3id.org/fep/044f#quote',
|
||||||
|
'@type': '@id',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
'@id': 'https://w3id.org/fep/044f#quoteAuthorization',
|
||||||
|
'@type': '@id',
|
||||||
|
},
|
||||||
|
],
|
||||||
|
id: 'foo',
|
||||||
|
type: 'Note',
|
||||||
|
summary: 'Show more',
|
||||||
|
content: 'Hello universe',
|
||||||
|
updated: '2021-09-08T22:39:25Z',
|
||||||
|
quote: { type: 'Tombstone' },
|
||||||
|
}
|
||||||
|
end
|
||||||
|
|
||||||
|
it 'updates the URI and unverifies the quote' do
|
||||||
|
expect { subject.call(status, json, json) }
|
||||||
|
.to change { status.quote.quoted_status }.from(quoted_status).to(nil)
|
||||||
|
.and change { status.quote.state }.from('accepted').to('deleted')
|
||||||
|
|
||||||
|
expect { quote.reload }.to raise_error(ActiveRecord::RecordNotFound)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
context 'when the status swaps a verified quote with another verifiable quote through an explicit update' do
|
context 'when the status swaps a verified quote with another verifiable quote through an explicit update' do
|
||||||
let(:quoted_account) { Fabricate(:account, domain: 'quoted.example.com') }
|
let(:quoted_account) { Fabricate(:account, domain: 'quoted.example.com') }
|
||||||
let(:second_quoted_account) { Fabricate(:account, domain: 'second-quoted.example.com') }
|
let(:second_quoted_account) { Fabricate(:account, domain: 'second-quoted.example.com') }
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ RSpec.describe 'Admin Dashboard' do
|
|||||||
before do
|
before do
|
||||||
stub_system_checks
|
stub_system_checks
|
||||||
Fabricate :software_update
|
Fabricate :software_update
|
||||||
|
Fabricate :tag, requested_review_at: 5.minutes.ago
|
||||||
sign_in(user)
|
sign_in(user)
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -18,6 +19,7 @@ RSpec.describe 'Admin Dashboard' do
|
|||||||
expect(page)
|
expect(page)
|
||||||
.to have_title(I18n.t('admin.dashboard.title'))
|
.to have_title(I18n.t('admin.dashboard.title'))
|
||||||
.and have_content(I18n.t('admin.system_checks.software_version_patch_check.message_html'))
|
.and have_content(I18n.t('admin.system_checks.software_version_patch_check.message_html'))
|
||||||
|
.and have_content('0 pending hashtags')
|
||||||
end
|
end
|
||||||
|
|
||||||
private
|
private
|
||||||
|
|||||||
Reference in New Issue
Block a user