Merge remote-tracking branch 'parent/main' into upstream-20240117

This commit is contained in:
KMY 2025-01-17 16:29:11 +09:00
commit 5d79bd078c
150 changed files with 2982 additions and 1485 deletions

View file

@ -5,6 +5,7 @@ class ActivityPub::Activity::Announce < ActivityPub::Activity
def perform
return reject_payload! if delete_arrived_first?(@json['id']) || !related_to_local_activity?
return reject_payload! if @object.nil?
with_redis_lock("announce:#{value_or_id(@object)}") do
original_status = status_from_object

View file

@ -98,8 +98,34 @@ class ActivityPub::TagManager
account_status_shares_url(target.account, target)
end
def followers_uri_for(target)
target.local? ? account_followers_url(target) : target.followers_url.presence
def following_uri_for(target, ...)
raise ArgumentError, 'target must be a local account' unless target.local?
account_following_index_url(target, ...)
end
def followers_uri_for(target, ...)
return target.followers_url.presence unless target.local?
account_followers_url(target, ...)
end
def collection_uri_for(target, ...)
raise NotImplementedError unless target.local?
account_collection_url(target, ...)
end
def inbox_uri_for(target)
raise NotImplementedError unless target.local?
target.instance_actor? ? instance_actor_inbox_url : account_inbox_url(target)
end
def outbox_uri_for(target, ...)
raise NotImplementedError unless target.local?
target.instance_actor? ? instance_actor_outbox_url(...) : account_outbox_url(target, ...)
end
# Primary audience of a status
@ -111,9 +137,9 @@ class ActivityPub::TagManager
when 'public'
[COLLECTIONS[:public]]
when 'unlisted', 'public_unlisted', 'private'
[account_followers_url(status.account)]
[followers_uri_for(status.account)]
when 'login'
[account_followers_url(status.account), 'as:LoginOnly', 'kmyblue:LoginOnly', 'LoginUser']
[followers_uri_for(status.account), 'as:LoginOnly', 'kmyblue:LoginOnly', 'LoginUser']
when 'direct'
if status.account.silenced?
# Only notify followers if the account is locally silenced
@ -156,7 +182,7 @@ class ActivityPub::TagManager
case status.visibility
when 'public'
cc << account_followers_url(status.account)
cc << followers_uri_for(status.account)
when 'unlisted', 'public_unlisted'
cc << COLLECTIONS[:public]
end

View file

@ -46,6 +46,8 @@ class DeliveryFailureTracker
urls.reject do |url|
host = Addressable::URI.parse(url).normalized_host
unavailable_domains_map[host]
rescue Addressable::URI::InvalidURIError, IDN::Idna::IdnaError
true
end
end

View file

@ -111,16 +111,10 @@ class Request
end
begin
# If we are using a persistent connection, we have to
# read every response to be able to move forward at all.
# However, simply calling #to_s or #flush may not be safe,
# as the response body, if malicious, could be too big
# for our memory. So we use the #body_with_limit method
response.body_with_limit if http_client.persistent?
yield response if block_given?
ensure
http_client.close unless http_client.persistent?
response.truncated_body if http_client.persistent? && !response.connection.finished_request?
http_client.close unless http_client.persistent? && response.connection.finished_request?
end
end

View file

@ -2,7 +2,8 @@
class WebPushRequest
SIGNATURE_ALGORITHM = 'p256ecdsa'
AUTH_HEADER = 'WebPush'
LEGACY_AUTH_HEADER = 'WebPush'
STANDARD_AUTH_HEADER = 'vapid'
PAYLOAD_EXPIRATION = 24.hours
JWT_ALGORITHM = 'ES256'
JWT_TYPE = 'JWT'
@ -10,6 +11,7 @@ class WebPushRequest
attr_reader :web_push_subscription
delegate(
:standard,
:endpoint,
:key_auth,
:key_p256dh,
@ -24,20 +26,36 @@ class WebPushRequest
@audience ||= Addressable::URI.parse(endpoint).normalized_site
end
def authorization_header
[AUTH_HEADER, encoded_json_web_token].join(' ')
def legacy_authorization_header
[LEGACY_AUTH_HEADER, encoded_json_web_token].join(' ')
end
def crypto_key_header
[SIGNATURE_ALGORITHM, vapid_key.public_key_for_push_header].join('=')
end
def encrypt(payload)
def legacy_encrypt(payload)
Webpush::Legacy::Encryption.encrypt(payload, key_p256dh, key_auth)
end
def standard_authorization_header
[STANDARD_AUTH_HEADER, standard_vapid_value].join(' ')
end
def standard_encrypt(payload)
Webpush::Encryption.encrypt(payload, key_p256dh, key_auth)
end
def legacy
!standard
end
private
def standard_vapid_value
"t=#{encoded_json_web_token},k=#{vapid_key.public_key_for_push_header}"
end
def encoded_json_web_token
JWT.encode(
web_token_payload,