diff options
author | Valery Sizov <valery@gitlab.com> | 2016-01-22 11:24:38 +0200 |
---|---|---|
committer | Valery Sizov <valery@gitlab.com> | 2016-01-22 11:24:44 +0200 |
commit | be7bc9d9b096a3d45bd8f58d1946bc80fea1c7f0 (patch) | |
tree | 2ace38e7225d109f606e7c85b09036ac2669f409 /app/helpers/snippets_helper.rb | |
parent | 5f0d7e2e3b1260c29b4a71e48b797f69355bf491 (diff) | |
download | gitlab-ce-be7bc9d9b096a3d45bd8f58d1946bc80fea1c7f0.tar.gz |
Backport some changes from EEes_backport
Diffstat (limited to 'app/helpers/snippets_helper.rb')
-rw-r--r-- | app/helpers/snippets_helper.rb | 75 |
1 files changed, 75 insertions, 0 deletions
diff --git a/app/helpers/snippets_helper.rb b/app/helpers/snippets_helper.rb index 906cb12cd48..bc36434f549 100644 --- a/app/helpers/snippets_helper.rb +++ b/app/helpers/snippets_helper.rb @@ -17,4 +17,79 @@ module SnippetsHelper snippet_path(snippet) end end + + # Get an array of line numbers surrounding a matching + # line, bounded by min/max. + # + # @returns Array of line numbers + def bounded_line_numbers(line, min, max, surrounding_lines) + lower = line - surrounding_lines > min ? line - surrounding_lines : min + upper = line + surrounding_lines < max ? line + surrounding_lines : max + (lower..upper).to_a + end + + # Returns a sorted set of lines to be included in a snippet preview. + # This ensures matching adjacent lines do not display duplicated + # surrounding code. + # + # @returns Array, unique and sorted. + def matching_lines(lined_content, surrounding_lines) + used_lines = [] + lined_content.each_with_index do |line, line_number| + used_lines.concat bounded_line_numbers( + line_number, + 0, + lined_content.size, + surrounding_lines + ) if line.include?(query) + end + + used_lines.uniq.sort + end + + # 'Chunkify' entire snippet. Splits the snippet data into matching lines + + # surrounding_lines() worth of unmatching lines. + # + # @returns a hash with {snippet_object, snippet_chunks:{data,start_line}} + def chunk_snippet(snippet, surrounding_lines = 3) + lined_content = snippet.content.split("\n") + used_lines = matching_lines(lined_content, surrounding_lines) + + snippet_chunk = [] + snippet_chunks = [] + snippet_start_line = 0 + last_line = -1 + + # Go through each used line, and add consecutive lines as a single chunk + # to the snippet chunk array. + used_lines.each do |line_number| + if last_line < 0 + # Start a new chunk. + snippet_start_line = line_number + snippet_chunk << lined_content[line_number] + elsif last_line == line_number - 1 + # Consecutive line, continue chunk. + snippet_chunk << lined_content[line_number] + else + # Non-consecutive line, add chunk to chunk array. + snippet_chunks << { + data: snippet_chunk.join("\n"), + start_line: snippet_start_line + 1 + } + + # Start a new chunk. + snippet_chunk = [lined_content[line_number]] + snippet_start_line = line_number + end + last_line = line_number + end + # Add final chunk to chunk array + snippet_chunks << { + data: snippet_chunk.join("\n"), + start_line: snippet_start_line + 1 + } + + # Return snippet with chunk array + { snippet_object: snippet, snippet_chunks: snippet_chunks } + end end |