You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

247 lines
5.0 KiB

  1. # frozen_string_literal: true
  2. class ActivityPub::NoteSerializer < ActiveModel::Serializer
  3. attributes :id, :type, :summary,
  4. :in_reply_to, :published, :url,
  5. :attributed_to, :to, :cc, :sensitive,
  6. :atom_uri, :in_reply_to_atom_uri,
  7. :conversation
  8. attribute :content
  9. attribute :content_map, if: :language?
  10. has_many :media_attachments, key: :attachment
  11. has_many :virtual_tags, key: :tag
  12. has_one :replies, serializer: ActivityPub::CollectionSerializer, if: :local?
  13. has_many :poll_loaded_options, key: :one_of, if: :poll_and_not_multiple?
  14. has_many :poll_loaded_options, key: :any_of, if: :poll_and_multiple?
  15. attribute :end_time, if: :poll_and_expires?
  16. attribute :closed, if: :poll_and_expired?
  17. def id
  18. ActivityPub::TagManager.instance.uri_for(object)
  19. end
  20. def type
  21. object.poll ? 'Question' : 'Note'
  22. end
  23. def summary
  24. object.spoiler_text.presence
  25. end
  26. def content
  27. Formatter.instance.format(object)
  28. end
  29. def content_map
  30. { object.language => Formatter.instance.format(object) }
  31. end
  32. def replies
  33. replies = object.self_replies(5).pluck(:id, :uri)
  34. last_id = replies.last&.first
  35. ActivityPub::CollectionPresenter.new(
  36. type: :unordered,
  37. id: ActivityPub::TagManager.instance.replies_uri_for(object),
  38. first: ActivityPub::CollectionPresenter.new(
  39. type: :unordered,
  40. part_of: ActivityPub::TagManager.instance.replies_uri_for(object),
  41. items: replies.map(&:second),
  42. next: last_id ? ActivityPub::TagManager.instance.replies_uri_for(object, page: true, min_id: last_id) : nil
  43. )
  44. )
  45. end
  46. def language?
  47. object.language.present?
  48. end
  49. def in_reply_to
  50. return unless object.reply? && !object.thread.nil?
  51. if object.thread.uri.nil? || object.thread.uri.start_with?('http')
  52. ActivityPub::TagManager.instance.uri_for(object.thread)
  53. else
  54. object.thread.url
  55. end
  56. end
  57. def published
  58. object.created_at.iso8601
  59. end
  60. def url
  61. ActivityPub::TagManager.instance.url_for(object)
  62. end
  63. def attributed_to
  64. ActivityPub::TagManager.instance.uri_for(object.account)
  65. end
  66. def to
  67. ActivityPub::TagManager.instance.to(object)
  68. end
  69. def cc
  70. ActivityPub::TagManager.instance.cc(object)
  71. end
  72. def virtual_tags
  73. object.active_mentions.to_a.sort_by(&:id) + object.tags + object.emojis
  74. end
  75. def atom_uri
  76. return unless object.local?
  77. OStatus::TagManager.instance.uri_for(object)
  78. end
  79. def in_reply_to_atom_uri
  80. return unless object.reply? && !object.thread.nil?
  81. OStatus::TagManager.instance.uri_for(object.thread)
  82. end
  83. def conversation
  84. return if object.conversation.nil?
  85. if object.conversation.uri?
  86. object.conversation.uri
  87. else
  88. OStatus::TagManager.instance.unique_tag(object.conversation.created_at, object.conversation.id, 'Conversation')
  89. end
  90. end
  91. def local?
  92. object.account.local?
  93. end
  94. def poll_loaded_options
  95. object.poll.loaded_options
  96. end
  97. def poll_and_multiple?
  98. object.poll&.multiple?
  99. end
  100. def poll_and_not_multiple?
  101. object.poll && !object.poll.multiple?
  102. end
  103. def closed
  104. object.poll.expires_at.iso8601
  105. end
  106. alias end_time closed
  107. def poll_and_expires?
  108. object.poll&.expires_at&.present?
  109. end
  110. def poll_and_expired?
  111. object.poll&.expired?
  112. end
  113. class MediaAttachmentSerializer < ActiveModel::Serializer
  114. include RoutingHelper
  115. attributes :type, :media_type, :url, :name
  116. attribute :focal_point, if: :focal_point?
  117. def type
  118. 'Document'
  119. end
  120. def name
  121. object.description
  122. end
  123. def media_type
  124. object.file_content_type
  125. end
  126. def url
  127. object.local? ? full_asset_url(object.file.url(:original, false)) : object.remote_url
  128. end
  129. def focal_point?
  130. object.file.meta.is_a?(Hash) && object.file.meta['focus'].is_a?(Hash)
  131. end
  132. def focal_point
  133. [object.file.meta['focus']['x'], object.file.meta['focus']['y']]
  134. end
  135. end
  136. class MentionSerializer < ActiveModel::Serializer
  137. attributes :type, :href, :name
  138. def type
  139. 'Mention'
  140. end
  141. def href
  142. ActivityPub::TagManager.instance.uri_for(object.account)
  143. end
  144. def name
  145. "@#{object.account.acct}"
  146. end
  147. end
  148. class TagSerializer < ActiveModel::Serializer
  149. include RoutingHelper
  150. attributes :type, :href, :name
  151. def type
  152. 'Hashtag'
  153. end
  154. def href
  155. tag_url(object)
  156. end
  157. def name
  158. "##{object.name}"
  159. end
  160. end
  161. class CustomEmojiSerializer < ActivityPub::EmojiSerializer
  162. end
  163. class OptionSerializer < ActiveModel::Serializer
  164. class RepliesSerializer < ActiveModel::Serializer
  165. attributes :type, :total_items
  166. def type
  167. 'Collection'
  168. end
  169. def total_items
  170. object.votes_count
  171. end
  172. end
  173. attributes :type, :name
  174. has_one :replies, serializer: ActivityPub::NoteSerializer::OptionSerializer::RepliesSerializer
  175. def type
  176. 'Note'
  177. end
  178. def name
  179. object.title
  180. end
  181. def replies
  182. object
  183. end
  184. end
  185. end