summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDouwe Maan <douwe@selenight.nl>2017-05-09 16:02:55 -0500
committerDouwe Maan <douwe@selenight.nl>2017-05-12 15:13:14 -0500
commit5bcdc435e6f1c749aaf03d6ecb33195c5fd62bae (patch)
tree67e19fa49fac31123ec8873a3010387436d0772a
parented6cbde202a290e3d64e3e86c22b059d8aaab2fe (diff)
downloadgitlab-ce-dm-autolink-in-blobs.tar.gz
Autolink the raw text and “transfer” the found links to the highlighted textdm-autolink-in-blobs
-rw-r--r--lib/gitlab/highlight.rb39
1 files changed, 36 insertions, 3 deletions
diff --git a/lib/gitlab/highlight.rb b/lib/gitlab/highlight.rb
index da9ac7cc51e..e25d0f06020 100644
--- a/lib/gitlab/highlight.rb
+++ b/lib/gitlab/highlight.rb
@@ -25,7 +25,7 @@ module Gitlab
def highlight(text, continue: true, plain: false)
highlighted_text = highlight_text(text, continue: continue, plain: plain)
highlighted_text = link_dependencies(text, highlighted_text) if blob_name
- autolink_strings(highlighted_text)
+ autolink_strings(text, highlighted_text)
end
def lexer
@@ -68,9 +68,42 @@ module Gitlab
Gitlab::DependencyLinker.link(blob_name, text, highlighted_text)
end
- def autolink_strings(highlighted_text)
+ def autolink_strings(text, highlighted_text)
+ raw_lines = text.lines
+
# TODO: Don't run pre-processing pipeline, because this may break the highlighting
- Banzai.render(highlighted_text, pipeline: :autolink, autolink_emails: true).html_safe
+ linked_text = Banzai.render(
+ ERB::Util.html_escape(text),
+ pipeline: :autolink,
+ autolink_emails: true
+ ).html_safe
+
+ linked_lines = linked_text.lines
+
+ highlighted_lines = highlighted_text.lines
+
+ highlighted_lines.map!.with_index do |rich_line, i|
+ matches = []
+ linked_lines[i].scan(/(?<start><a[^>]+>)(?<content>[^<]+)(?<end><\/a>)/) { matches << Regexp.last_match }
+ next rich_line if matches.empty?
+
+ raw_line = raw_lines[i]
+ marked_line = rich_line.html_safe
+
+ matches.each do |match|
+ marker = StringRegexMarker.new(raw_line, marked_line)
+
+ regex = /#{Regexp.escape(match[:content])}/
+
+ marked_line = marker.mark(regex) do |text, left:, right:|
+ "#{match[:start]}#{text}#{match[:end]}"
+ end
+ end
+
+ marked_line
+ end
+
+ highlighted_lines.join.html_safe
end
end
end