Based on https://github.com/mastodon/mastodon/compare/v4.1.12...v4.1.13
Notes:
* spec/lib/linked_data_signature_spec.rb: missing code this patch
addresses; ignored
15 files changed:
stoplight_wrap_request { ResolveAccountService.new.call(key_id.gsub(/\Aacct:/, ''), suppress_errors: false) }
elsif !ActivityPub::TagManager.instance.local_uri?(key_id)
account = ActivityPub::TagManager.instance.uri_to_actor(key_id)
stoplight_wrap_request { ResolveAccountService.new.call(key_id.gsub(/\Aacct:/, ''), suppress_errors: false) }
elsif !ActivityPub::TagManager.instance.local_uri?(key_id)
account = ActivityPub::TagManager.instance.uri_to_actor(key_id)
- account ||= stoplight_wrap_request { ActivityPub::FetchRemoteKeyService.new.call(key_id, id: false, suppress_errors: false) }
+ account ||= stoplight_wrap_request { ActivityPub::FetchRemoteKeyService.new.call(key_id, suppress_errors: false) }
account
end
rescue Mastodon::PrivateNetworkAddressError => e
account
end
rescue Mastodon::PrivateNetworkAddressError => e
- def fetch_resource(uri, id, on_behalf_of = nil)
- unless id
+ def fetch_resource(uri, id_is_known, on_behalf_of = nil)
+ unless id_is_known
json = fetch_resource_without_id_validation(uri, on_behalf_of)
return if !json.is_a?(Hash) || unsupported_uri_scheme?(json['id'])
json = fetch_resource_without_id_validation(uri, on_behalf_of)
return if !json.is_a?(Hash) || unsupported_uri_scheme?(json['id'])
def fetch_remote_original_status
if object_uri.start_with?('http')
return if ActivityPub::TagManager.instance.local_uri?(object_uri)
def fetch_remote_original_status
if object_uri.start_with?('http')
return if ActivityPub::TagManager.instance.local_uri?(object_uri)
- ActivityPub::FetchRemoteStatusService.new.call(object_uri, id: true, on_behalf_of: @account.followers.local.first)
+
+ # in 4.1.12 there is an extra argument `request_id: @options[:request_id]` here
+ ActivityPub::FetchRemoteStatusService.new.call(object_uri, on_behalf_of: @account.followers.local.first)
elsif @object['url'].present?
::FetchRemoteStatusService.new.call(@object['url'])
end
elsif @object['url'].present?
::FetchRemoteStatusService.new.call(@object['url'])
end
return unless type == 'RsaSignature2017'
creator = ActivityPub::TagManager.instance.uri_to_actor(creator_uri)
return unless type == 'RsaSignature2017'
creator = ActivityPub::TagManager.instance.uri_to_actor(creator_uri)
- creator ||= ActivityPub::FetchRemoteKeyService.new.call(creator_uri, id: false)
+ # 4.1.12 uses a reassignment `if creator&.public_key.blank?`
+ creator ||= ActivityPub::FetchRemoteKeyService.new.call(creator_uri)
class ActivityPub::FetchRemoteAccountService < ActivityPub::FetchRemoteActorService
# Does a WebFinger roundtrip on each call, unless `only_key` is true
class ActivityPub::FetchRemoteAccountService < ActivityPub::FetchRemoteActorService
# Does a WebFinger roundtrip on each call, unless `only_key` is true
- def call(uri, id: true, prefetched_body: nil, break_on_redirect: false, only_key: false, suppress_errors: true)
+ def call(uri, prefetched_body: nil, break_on_redirect: false, only_key: false, suppress_errors: true)
actor = super
return actor if actor.nil? || actor.is_a?(Account)
actor = super
return actor if actor.nil? || actor.is_a?(Account)
SUPPORTED_TYPES = %w(Application Group Organization Person Service).freeze
# Does a WebFinger roundtrip on each call, unless `only_key` is true
SUPPORTED_TYPES = %w(Application Group Organization Person Service).freeze
# Does a WebFinger roundtrip on each call, unless `only_key` is true
- def call(uri, id: true, prefetched_body: nil, break_on_redirect: false, only_key: false, suppress_errors: true)
+ def call(uri, prefetched_body: nil, break_on_redirect: false, only_key: false, suppress_errors: true)
return if domain_not_allowed?(uri)
return ActivityPub::TagManager.instance.uri_to_actor(uri) if ActivityPub::TagManager.instance.local_uri?(uri)
@json = begin
if prefetched_body.nil?
return if domain_not_allowed?(uri)
return ActivityPub::TagManager.instance.uri_to_actor(uri) if ActivityPub::TagManager.instance.local_uri?(uri)
@json = begin
if prefetched_body.nil?
- fetch_resource(uri, id)
+ fetch_resource(uri, true)
- body_to_json(prefetched_body, compare_id: id ? uri : nil)
+ body_to_json(prefetched_body, compare_id: uri)
end
rescue Oj::ParseError
raise Error, "Error parsing JSON-LD document #{uri}"
end
rescue Oj::ParseError
raise Error, "Error parsing JSON-LD document #{uri}"
class Error < StandardError; end
# Returns actor that owns the key
class Error < StandardError; end
# Returns actor that owns the key
- def call(uri, id: true, prefetched_body: nil, suppress_errors: true)
+ def call(uri, suppress_errors: true)
raise Error, 'No key URI given' if uri.blank?
raise Error, 'No key URI given' if uri.blank?
- if prefetched_body.nil?
- if id
- @json = fetch_resource_without_id_validation(uri)
- if actor_type?
- @json = fetch_resource(@json['id'], true)
- elsif uri != @json['id']
- raise Error, "Fetched URI #{uri} has wrong id #{@json['id']}"
- end
- else
- @json = fetch_resource(uri, id)
- end
- else
- @json = body_to_json(prefetched_body, compare_id: id ? uri : nil)
- end
+ @json = fetch_resource(uri, false)
raise Error, "Unable to fetch key JSON at #{uri}" if @json.nil?
raise Error, "Unsupported JSON-LD context for document #{uri}" unless supported_context?(@json)
raise Error, "Unable to fetch key JSON at #{uri}" if @json.nil?
raise Error, "Unsupported JSON-LD context for document #{uri}" unless supported_context?(@json)
include JsonLdHelper
# Should be called when uri has already been checked for locality
include JsonLdHelper
# Should be called when uri has already been checked for locality
- def call(uri, id: true, prefetched_body: nil, on_behalf_of: nil)
+ def call(uri, prefetched_body: nil, on_behalf_of: nil)
@json = begin
if prefetched_body.nil?
@json = begin
if prefetched_body.nil?
- fetch_resource(uri, id, on_behalf_of)
+ fetch_resource(uri, true, on_behalf_of)
- body_to_json(prefetched_body, compare_id: id ? uri : nil)
+ body_to_json(prefetched_body, compare_id: uri)
def account_from_uri(uri)
actor = ActivityPub::TagManager.instance.uri_to_resource(uri, Account)
def account_from_uri(uri)
actor = ActivityPub::TagManager.instance.uri_to_resource(uri, Account)
- actor = ActivityPub::FetchRemoteAccountService.new.call(uri, id: true) if actor.nil? || actor.possibly_stale?
+ actor = ActivityPub::FetchRemoteAccountService.new.call(uri) if actor.nil? || actor.possibly_stale?
def moved_account
account = ActivityPub::TagManager.instance.uri_to_resource(@json['movedTo'], Account)
def moved_account
account = ActivityPub::TagManager.instance.uri_to_resource(@json['movedTo'], Account)
- account ||= ActivityPub::FetchRemoteAccountService.new.call(@json['movedTo'], id: true, break_on_redirect: true)
+ account ||= ActivityPub::FetchRemoteAccountService.new.call(@json['movedTo'], break_on_redirect: true)
body = response.body_with_limit
json = body_to_json(body)
body = response.body_with_limit
json = body_to_json(body)
- [json['id'], { prefetched_body: body, id: true }] if supported_context?(json) && (equals_or_includes_any?(json['type'], ActivityPub::FetchRemoteActorService::SUPPORTED_TYPES) || expected_type?(json))
+ return unless supported_context?(json) && (equals_or_includes_any?(json['type'], ActivityPub::FetchRemoteActorService::SUPPORTED_TYPES) || expected_type?(json))
+
+ if json['id'] != @url
+ return if terminal
+
+ return process(json['id'], terminal: true)
+ end
+
+ [@url, { prefetched_body: body }]
elsif !terminal
link_header = response['Link'] && parse_link_header(response)
elsif !terminal
link_header = response['Link'] && parse_link_header(response)
- let(:account) { subject.call('https://example.com/alice', id: true) }
+ let(:account) { subject.call('https://example.com/alice') }
shared_examples 'sets profile data' do
it 'returns an account' do
shared_examples 'sets profile data' do
it 'returns an account' do
- let(:account) { subject.call('https://example.com/alice', id: true) }
+ let(:account) { subject.call('https://example.com/alice') }
shared_examples 'sets profile data' do
it 'returns an account' do
shared_examples 'sets profile data' do
it 'returns an account' do
- let(:account) { subject.call(public_key_id, id: false) }
+ let(:account) { subject.call(public_key_id) }
context 'when the key is a sub-object from the actor' do
before do
context 'when the key is a sub-object from the actor' do
before do
+ id: 'http://example.com/foo',
'@context': ActivityPub::TagManager::CONTEXT,
type: 'Note',
}.to_json
'@context': ActivityPub::TagManager::CONTEXT,
type: 'Note',
}.to_json
let(:content_type) { 'application/activity+json; charset=utf-8' }
let(:body) { json }
let(:content_type) { 'application/activity+json; charset=utf-8' }
let(:body) { json }
- it { is_expected.to eq [1, { prefetched_body: body, id: true }] }
+ it { is_expected.to eq ['http://example.com/foo', { prefetched_body: body }] }
end
context 'when content type is ld+json with profile' do
let(:content_type) { 'application/ld+json; profile="https://www.w3.org/ns/activitystreams"' }
let(:body) { json }
end
context 'when content type is ld+json with profile' do
let(:content_type) { 'application/ld+json; profile="https://www.w3.org/ns/activitystreams"' }
let(:body) { json }
- it { is_expected.to eq [1, { prefetched_body: body, id: true }] }
+ it { is_expected.to eq ['http://example.com/foo', { prefetched_body: body }] }
let(:content_type) { 'text/html' }
let(:body) { '<html><head><link rel="alternate" href="http://example.com/foo" type="application/activity+json"/></head></html>' }
let(:content_type) { 'text/html' }
let(:body) { '<html><head><link rel="alternate" href="http://example.com/foo" type="application/activity+json"/></head></html>' }
- it { is_expected.to eq [1, { prefetched_body: json, id: true }] }
+ it { is_expected.to eq ['http://example.com/foo', { prefetched_body: json }] }
stub_request(:get, url).to_return(status: 302, headers: { 'Location' => status_url })
body = ActiveModelSerializers::SerializableResource.new(status, serializer: ActivityPub::NoteSerializer, adapter: ActivityPub::Adapter).to_json
stub_request(:get, status_url).to_return(body: body, headers: { 'Content-Type' => 'application/activity+json' })
stub_request(:get, url).to_return(status: 302, headers: { 'Location' => status_url })
body = ActiveModelSerializers::SerializableResource.new(status, serializer: ActivityPub::NoteSerializer, adapter: ActivityPub::Adapter).to_json
stub_request(:get, status_url).to_return(body: body, headers: { 'Content-Type' => 'application/activity+json' })
+ stub_request(:get, uri).to_return(body: body, headers: { 'Content-Type' => 'application/activity+json' })
end
it 'returns status by url' do
end
it 'returns status by url' do