Action Text Content

The ActionText::Content class wraps an HTML fragment to add support for parsing, rendering and serialization. It can be used to extract links and attachments, convert the fragment to plain text, or serialize the fragment to the database.

The ActionText::RichText record serializes the body attribute as ActionText::Content.

class Message < ActiveRecord::Base
  has_rich_text :content
end

message = Message.create!(content: "<h1>Funny times!</h1>")
body = message.content.body # => #<ActionText::Content "<div class=\"trix-conte...">
body.to_s # => "<h1>Funny times!</h1>"
body.to_plain_text # => "Funny times!"

Methods

Attributes

[R] fragment

Class Public methods

fragment_by_canonicalizing_content(content)

📝 Source code
# File actiontext/lib/action_text/content.rb, line 33
      def fragment_by_canonicalizing_content(content)
        fragment = ActionText::Attachment.fragment_by_canonicalizing_attachments(content)
        fragment = ActionText::AttachmentGallery.fragment_by_canonicalizing_attachment_galleries(fragment)
        fragment
      end
🔎 See on GitHub

new(content = nil, options = {})

📝 Source code
# File actiontext/lib/action_text/content.rb, line 40
    def initialize(content = nil, options = {})
      options.with_defaults! canonicalize: true

      if options[:canonicalize]
        @fragment = self.class.fragment_by_canonicalizing_content(content)
      else
        @fragment = ActionText::Fragment.wrap(content)
      end
    end
🔎 See on GitHub

Instance Public methods

==(other)

📝 Source code
# File actiontext/lib/action_text/content.rb, line 169
    def ==(other)
      if self.class == other.class
        to_html == other.to_html
      elsif other.is_a?(self.class)
        to_s == other.to_s
      end
    end
🔎 See on GitHub

append_attachables(attachables)

📝 Source code
# File actiontext/lib/action_text/content.rb, line 93
    def append_attachables(attachables)
      attachments = ActionText::Attachment.from_attachables(attachables)
      self.class.new([self.to_s.presence, *attachments].compact.join("\n"))
    end
🔎 See on GitHub

as_json(*)

📝 Source code
# File actiontext/lib/action_text/content.rb, line 161
    def as_json(*)
      to_html
    end
🔎 See on GitHub

attachables()

Extracts +ActionText::Attachable+s from the HTML fragment:

attachable = ActiveStorage::Blob.first
html = %Q(<action-text-attachment sgid="#{attachable.attachable_sgid}" caption="Captioned"></action-text-attachment>)
content = ActionText::Content.new(html)
content.attachables # => [attachable]
📝 Source code
# File actiontext/lib/action_text/content.rb, line 87
    def attachables
      @attachables ||= attachment_nodes.map do |node|
        ActionText::Attachable.from_node(node)
      end
    end
🔎 See on GitHub

attachment_galleries()

📝 Source code
# File actiontext/lib/action_text/content.rb, line 71
    def attachment_galleries
      @attachment_galleries ||= attachment_gallery_nodes.map do |node|
        attachment_gallery_for_node(node)
      end
    end
🔎 See on GitHub

attachments()

Extracts +ActionText::Attachment+s from the HTML fragment:

attachable = ActiveStorage::Blob.first
html = %Q(<action-text-attachment sgid="#{attachable.attachable_sgid}" caption="Captioned"></action-text-attachment>)
content = ActionText::Content.new(html)
content.attachments # => [#<ActionText::Attachment attachable=#<ActiveStorage::Blob...
📝 Source code
# File actiontext/lib/action_text/content.rb, line 65
    def attachments
      @attachments ||= attachment_nodes.map do |node|
        attachment_for_node(node)
      end
    end
🔎 See on GitHub
📝 Source code
# File actiontext/lib/action_text/content.rb, line 77
    def gallery_attachments
      @gallery_attachments ||= attachment_galleries.flat_map(&:attachments)
    end
🔎 See on GitHub

inspect()

📝 Source code
# File actiontext/lib/action_text/content.rb, line 165
    def inspect
      "#<#{self.class.name} #{to_html.truncate(25).inspect}>"
    end
🔎 See on GitHub

Extracts links from the HTML fragment:

html = '<a href="http://example.com/">Example</a>'
content = ActionText::Content.new(html)
content.links # => ["http://example.com/"]
📝 Source code
# File actiontext/lib/action_text/content.rb, line 55
    def links
      @links ||= fragment.find_all("a[href]").map { |a| a["href"] }.uniq
    end
🔎 See on GitHub

render_attachment_galleries(&block)

📝 Source code
# File actiontext/lib/action_text/content.rb, line 109
    def render_attachment_galleries(&block)
      content = ActionText::AttachmentGallery.fragment_by_replacing_attachment_gallery_nodes(fragment) do |node|
        block.call(attachment_gallery_for_node(node))
      end
      self.class.new(content, canonicalize: false)
    end
🔎 See on GitHub

render_attachments(**options, &block)

📝 Source code
# File actiontext/lib/action_text/content.rb, line 98
    def render_attachments(**options, &block)
      content = fragment.replace(ActionText::Attachment.tag_name) do |node|
        if node.key?("content")
          sanitized_content = sanitize_content_attachment(node.remove_attribute("content").to_s)
          node["content"] = sanitized_content if sanitized_content.present?
        end
        block.call(attachment_for_node(node, **options))
      end
      self.class.new(content, canonicalize: false)
    end
🔎 See on GitHub

to_html()

📝 Source code
# File actiontext/lib/action_text/content.rb, line 138
    def to_html
      fragment.to_html
    end
🔎 See on GitHub

to_partial_path()

📝 Source code
# File actiontext/lib/action_text/content.rb, line 146
    def to_partial_path
      "action_text/contents/content"
    end
🔎 See on GitHub

to_plain_text()

Returns a plain-text version of the markup contained by the content, with tags removed but HTML entities encoded.

content = ActionText::Content.new("<h1>Funny times!</h1>")
content.to_plain_text # => "Funny times!"

content = ActionText::Content.new("<div onclick='action()'>safe<script>unsafe</script></div>")
content.to_plain_text # => "safeunsafe"

NOTE: that the returned string is not HTML safe and should not be rendered in browsers.

content = ActionText::Content.new("&lt;script&gt;alert()&lt;/script&gt;")
content.to_plain_text # => "<script>alert()</script>"
📝 Source code
# File actiontext/lib/action_text/content.rb, line 130
    def to_plain_text
      render_attachments(with_full_attributes: false, &:to_plain_text).fragment.to_plain_text
    end
🔎 See on GitHub

to_rendered_html_with_layout()

📝 Source code
# File actiontext/lib/action_text/content.rb, line 142
    def to_rendered_html_with_layout
      render layout: "action_text/contents/content", partial: to_partial_path, formats: :html, locals: { content: self }
    end
🔎 See on GitHub

to_s()

Safely transforms Content into an HTML String.

content = ActionText::Content.new(content: "<h1>Funny times!</h1>")
content.to_s # => "<h1>Funny times!</h1>"

content = ActionText::Content.new("<div onclick='action()'>safe<script>unsafe</script></div>")
content.to_s # => "<div>safeunsafe</div>"
📝 Source code
# File actiontext/lib/action_text/content.rb, line 157
    def to_s
      to_rendered_html_with_layout
    end
🔎 See on GitHub

to_trix_html()

📝 Source code
# File actiontext/lib/action_text/content.rb, line 134
    def to_trix_html
      render_attachments(&:to_trix_attachment).to_html
    end
🔎 See on GitHub