fedibird-fe/app/controllers/activitypub/references_controller.rb
2023-01-16 12:58:29 +09:00

88 lines
2.3 KiB
Ruby

# frozen_string_literal: true
class ActivityPub::ReferencesController < ActivityPub::BaseController
include SignatureVerification
include Authorization
include AccountOwnedConcern
include StatusControllerConcern
before_action :require_signature!, if: :authorized_fetch_mode?
before_action :set_status
before_action :set_cache_headers
before_action :set_references
def index
expires_in 0, public: public_fetch_mode?
render json: references_collection_presenter, serializer: ActivityPub::CollectionSerializer, adapter: ActivityPub::Adapter, content_type: 'application/activity+json', skip_activities: true
end
private
def pundit_user
signed_request_account
end
def set_status
@status = @account.statuses.find(params[:status_id])
authorize @status, :show?
rescue Mastodon::NotPermittedError
not_found
end
def load_statuses
cached_references
end
def cached_references
cache_collection(Status.where(id: results).reorder(:id), Status)
end
def results
@_results ||= begin
references = @status.reference_relationships.order(target_status_id: :asc)
references = references.where('target_status_id > ?', page_params[:min_id]) if page_params[:min_id].present?
references = references.limit(limit_param(REFERENCES_LIMIT))
references.pluck(:target_status_id)
end
end
def pagination_min_id
results.last
end
def records_continue?
results.size == limit_param(REFERENCES_LIMIT)
end
def references_collection_presenter
page = ActivityPub::CollectionPresenter.new(
id: ActivityPub::TagManager.instance.references_uri_for(@status, page_params),
type: :unordered,
part_of: ActivityPub::TagManager.instance.references_uri_for(@status),
items: load_statuses.map(&:uri),
next: next_page,
)
return page if page_requested?
ActivityPub::CollectionPresenter.new(
type: :unordered,
id: ActivityPub::TagManager.instance.references_uri_for(@status),
first: page,
)
end
def page_requested?
truthy_param?(:page)
end
def next_page
if records_continue?
ActivityPub::TagManager.instance.references_uri_for(@status, page_params.merge(min_id: pagination_min_id))
end
end
def page_params
params_slice(:min_id, :limit).merge(page: true)
end
end