Commit 2a755762 authored by Heinrich Lee Yu's avatar Heinrich Lee Yu

Post-process GFM after truncating the HTML

This is so that we only post-process the truncated
HTML and save some unnecessary Gitaly calls
parent 9a2dafa4
...@@ -76,13 +76,14 @@ module MarkupHelper ...@@ -76,13 +76,14 @@ module MarkupHelper
# +max_chars+ limit. If the length limit falls within a tag's contents, then # +max_chars+ limit. If the length limit falls within a tag's contents, then
# the tag contents are truncated without removing the closing tag. # the tag contents are truncated without removing the closing tag.
def first_line_in_markdown(object, attribute, max_chars = nil, options = {}) def first_line_in_markdown(object, attribute, max_chars = nil, options = {})
md = markdown_field(object, attribute, options) md = markdown_field(object, attribute, options.merge(post_process: false))
return unless md.present? return unless md.present?
tags = %w(a gl-emoji b pre code p span) tags = %w(a gl-emoji b pre code p span)
tags << 'img' if options[:allow_images] tags << 'img' if options[:allow_images]
text = truncate_visible(md, max_chars || md.length) text = truncate_visible(md, max_chars || md.length)
text = prepare_for_rendering(text, markdown_field_render_context(object, attribute, options))
text = sanitize( text = sanitize(
text, text,
tags: tags, tags: tags,
...@@ -107,15 +108,12 @@ module MarkupHelper ...@@ -107,15 +108,12 @@ module MarkupHelper
def markdown_field(object, field, context = {}) def markdown_field(object, field, context = {})
object = object.for_display if object.respond_to?(:for_display) object = object.for_display if object.respond_to?(:for_display)
redacted_field_html = object.try(:"redacted_#{field}_html")
return '' unless object.present? return '' unless object.present?
return redacted_field_html if redacted_field_html
html = Banzai.render_field(object, field, context) redacted_field_html = object.try(:"redacted_#{field}_html")
context.reverse_merge!(object.banzai_render_context(field)) if object.respond_to?(:banzai_render_context) return redacted_field_html if redacted_field_html
prepare_for_rendering(html, context) render_markdown_field(object, field, context)
end end
def markup(file_name, text, context = {}) def markup(file_name, text, context = {})
...@@ -277,6 +275,23 @@ module MarkupHelper ...@@ -277,6 +275,23 @@ module MarkupHelper
Gitlab::OtherMarkup.render(file_name, text, context) Gitlab::OtherMarkup.render(file_name, text, context)
end end
def render_markdown_field(object, field, context = {})
post_process = context.delete(:post_process)
post_process = true if post_process.nil?
html = Banzai.render_field(object, field, context)
return html unless post_process
prepare_for_rendering(html, markdown_field_render_context(object, field, context))
end
def markdown_field_render_context(object, field, base_context = {})
return base_context unless object.respond_to?(:banzai_render_context)
base_context.reverse_merge(object.banzai_render_context(field))
end
def prepare_for_rendering(html, context = {}) def prepare_for_rendering(html, context = {})
return '' unless html.present? return '' unless html.present?
......
---
title: Prevent unnecessary Gitaly calls when rendering comment excerpts in todos and
activity feed
merge_request: 23100
author:
type: performance
...@@ -138,10 +138,20 @@ describe MarkupHelper do ...@@ -138,10 +138,20 @@ describe MarkupHelper do
describe 'without redacted attribute' do describe 'without redacted attribute' do
it 'renders the markdown value' do it 'renders the markdown value' do
expect(Banzai).to receive(:render_field).with(commit, attribute, {}).and_call_original expect(Banzai).to receive(:render_field).with(commit, attribute, {}).and_call_original
expect(Banzai).to receive(:post_process)
helper.markdown_field(commit, attribute) helper.markdown_field(commit, attribute)
end end
end end
context 'when post_process is false' do
it 'does not run Markdown post processing' do
expect(Banzai).to receive(:render_field).with(commit, attribute, {}).and_call_original
expect(Banzai).not_to receive(:post_process)
helper.markdown_field(commit, attribute, post_process: false)
end
end
end end
describe '#link_to_markdown_field' do describe '#link_to_markdown_field' do
...@@ -565,6 +575,14 @@ describe MarkupHelper do ...@@ -565,6 +575,14 @@ describe MarkupHelper do
expect(doc.content).to eq "foo 😉\nbar 😀" expect(doc.content).to eq "foo 😉\nbar 😀"
end end
it 'does not post-process truncated text', :request_store do
object = create_object("hello \n\n [Test](README.md)")
expect do
first_line_in_markdown(object, attribute, nil, project: project)
end.not_to change { Gitlab::GitalyClient.get_request_count }
end
end end
context 'when the asked attribute can be redacted' do context 'when the asked attribute can be redacted' do
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment