Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gitlab.com/gitlab-org/gitlab-foss.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSarah Yasonik <syasonik@gitlab.com>2019-07-10 14:27:25 +0300
committerDmitriy Zaporozhets <dmitriy.zaporozhets@gmail.com>2019-07-10 14:27:25 +0300
commit7d393bd85233bd6c8f003aec638e93c01deb9f8a (patch)
tree0dcad0bc26766b82f0d8d55762b768e65a41f186 /lib/banzai/filter/inline_embeds_filter.rb
parent476c9f0bb6bb629d36efc7b62fcb12eda6ceee2d (diff)
Expose metrics element for FE consumption
Adds GFM Pipline filters to insert a placeholder in the generated HTML from GFM based on the presence of a metrics dashboard link. The front end should look for the class 'js-render-metrics' to determine if it should replace the element with metrics charts. The data element 'data-dashboard-url' should be the endpoint the front end should hit in order to obtain a dashboard layout in order to appropriately render the charts.
Diffstat (limited to 'lib/banzai/filter/inline_embeds_filter.rb')
-rw-r--r--lib/banzai/filter/inline_embeds_filter.rb67
1 files changed, 67 insertions, 0 deletions
diff --git a/lib/banzai/filter/inline_embeds_filter.rb b/lib/banzai/filter/inline_embeds_filter.rb
new file mode 100644
index 00000000000..97394fd8f82
--- /dev/null
+++ b/lib/banzai/filter/inline_embeds_filter.rb
@@ -0,0 +1,67 @@
+# frozen_string_literal: true
+
+module Banzai
+ module Filter
+ # HTML filter that inserts a node for each occurence of
+ # a given link format. To transform references to DB
+ # resources in place, prefer to inherit from AbstractReferenceFilter.
+ class InlineEmbedsFilter < HTML::Pipeline::Filter
+ # Find every relevant link, create a new node based on
+ # the link, and insert this node after any html content
+ # surrounding the link.
+ def call
+ return doc unless Feature.enabled?(:gfm_embedded_metrics, context[:project])
+
+ doc.xpath(xpath_search).each do |node|
+ next unless element = element_to_embed(node)
+
+ # We want this to follow any surrounding content. For example,
+ # if a link is inline in a paragraph.
+ node.parent.children.last.add_next_sibling(element)
+ end
+
+ doc
+ end
+
+ # Implement in child class.
+ #
+ # Return a Nokogiri::XML::Element to embed in the
+ # markdown.
+ def create_element(params)
+ end
+
+ # Implement in child class unless overriding #embed_params
+ #
+ # Returns the regex pattern used to filter
+ # to only matching urls.
+ def link_pattern
+ end
+
+ # Returns the xpath query string used to select nodes
+ # from the html document on which the embed is based.
+ #
+ # Override to select nodes other than links.
+ def xpath_search
+ 'descendant-or-self::a[@href]'
+ end
+
+ # Creates a new element based on the parameters
+ # obtained from the target link
+ def element_to_embed(node)
+ return unless params = embed_params(node)
+
+ create_element(params)
+ end
+
+ # Returns a hash of named parameters based on the
+ # provided regex with string keys.
+ #
+ # Override to select nodes other than links.
+ def embed_params(node)
+ url = node['href']
+
+ link_pattern.match(url) { |m| m.named_captures }
+ end
+ end
+ end
+end