diff options
author | Sean McGivern <sean@gitlab.com> | 2019-06-17 17:03:41 +0000 |
---|---|---|
committer | Sean McGivern <sean@gitlab.com> | 2019-06-17 17:03:41 +0000 |
commit | 2634cad695e41f4882a67a8cfa0e2579b870f1a3 (patch) | |
tree | 18dfebd24d0b63d0ad98cfb15cb105365ec01e03 /lib | |
parent | 89a89b3230717920410de6fb6d6b7152ef41a03e (diff) | |
parent | d75a4ddab2cac69b7190c4a88adb8363c2950bdb (diff) | |
download | gitlab-ce-2634cad695e41f4882a67a8cfa0e2579b870f1a3.tar.gz |
Merge branch 'generate-spans-for-sections' into 'master'
Add collapsible sections to job log
See merge request gitlab-org/gitlab-ce!28642
Diffstat (limited to 'lib')
-rw-r--r-- | lib/gitlab/ci/ansi2html.rb | 87 |
1 files changed, 75 insertions, 12 deletions
diff --git a/lib/gitlab/ci/ansi2html.rb b/lib/gitlab/ci/ansi2html.rb index fba0de20ced..6109b45ffd2 100644 --- a/lib/gitlab/ci/ansi2html.rb +++ b/lib/gitlab/ci/ansi2html.rb @@ -131,9 +131,9 @@ module Gitlab def on_109(_) set_bg_color(9, 'l') end - attr_accessor :offset, :n_open_tags, :fg_color, :bg_color, :style_mask + attr_accessor :offset, :n_open_tags, :fg_color, :bg_color, :style_mask, :sections, :lineno_in_section - STATE_PARAMS = [:offset, :n_open_tags, :fg_color, :bg_color, :style_mask].freeze + STATE_PARAMS = [:offset, :n_open_tags, :fg_color, :bg_color, :style_mask, :sections, :lineno_in_section].freeze def convert(stream, new_state) reset_state @@ -153,10 +153,9 @@ module Gitlab start_offset = @offset - open_new_tag - stream.each_line do |line| s = StringScanner.new(line) + until s.eos? if s.scan(Gitlab::Regex.build_trace_section_regex) @@ -166,11 +165,11 @@ module Gitlab elsif s.scan(/\e(([@-_])(.*?)?)?$/) break elsif s.scan(/</) - @out << '<' + write_in_tag '<' elsif s.scan(/\r?\n/) - @out << '<br>' + handle_new_line else - @out << s.scan(/./m) + write_in_tag s.scan(/./m) end @offset += s.matched_size @@ -190,13 +189,59 @@ module Gitlab ) end + def section_to_class_name(section) + section.to_s.downcase.gsub(/[^a-z0-9]/, '-') + end + + def handle_new_line + css_classes = [] + + if @sections.any? + css_classes = %w[section line] + sections.map { |section| "s_#{section}" } + end + + write_in_tag %{<br/>} + write_raw %{<span class="#{css_classes.join(' ')}"></span>} if css_classes.any? + @lineno_in_section += 1 + open_new_tag + end + def handle_section(scanner) action = scanner[1] timestamp = scanner[2] section = scanner[3] - line = scanner.matched[0...-5] # strips \r\033[0K - @out << %{<div class="hidden" data-action="#{action}" data-timestamp="#{timestamp}" data-section="#{section}">#{line}</div>} + normalized_section = section_to_class_name(section) + + if action == "start" + handle_section_start(normalized_section, timestamp) + elsif action == "end" + handle_section_end(normalized_section, timestamp) + end + end + + def handle_section_start(section, timestamp) + return if @sections.include?(section) + + @sections << section + write_raw %{<div class="js-section-start fa fa-caret-down append-right-8 cursor-pointer" data-timestamp="#{timestamp}" data-section="#{data_section_names}" role="button"></div>} + @lineno_in_section = 0 + end + + def handle_section_end(section, timestamp) + return unless @sections.include?(section) + + # close all sections up to section + until @sections.empty? + write_raw %{<div class="section-end" data-section="#{data_section_names}"></div>} + + last_section = @sections.pop + break if section == last_section + end + end + + def data_section_names + @sections.join(" ") end def handle_sequence(scanner) @@ -217,8 +262,6 @@ module Gitlab end evaluate_command_stack(commands) - - open_new_tag end def evaluate_command_stack(stack) @@ -231,6 +274,20 @@ module Gitlab evaluate_command_stack(stack) end + def write_in_tag(data) + ensure_open_new_tag + @out << data + end + + def write_raw(data) + close_open_tags + @out << data + end + + def ensure_open_new_tag + open_new_tag if @n_open_tags == 0 + end + def open_new_tag css_classes = [] @@ -251,7 +308,11 @@ module Gitlab css_classes << "term-#{css_class}" if @style_mask & flag != 0 end - return if css_classes.empty? + if @sections.any? + css_classes << "section" + css_classes << "js-section-header" if @lineno_in_section == 0 + css_classes += sections.map { |section| "js-s-#{section}" } + end @out << %{<span class="#{css_classes.join(' ')}">} @n_open_tags += 1 @@ -268,6 +329,8 @@ module Gitlab @offset = 0 @n_open_tags = 0 @out = +'' + @sections = [] + @lineno_in_section = 0 reset end |