diff --git a/assets/scripts/app/views/log.coffee b/assets/scripts/app/views/log.coffee index 87bf913b..927fa88a 100644 --- a/assets/scripts/app/views/log.coffee +++ b/assets/scripts/app/views/log.coffee @@ -1,5 +1,6 @@ require 'log' require 'travis/lines_selector' +require 'travis/log_folder' Log.DEBUG = false Log.LIMIT = 10000 @@ -47,7 +48,8 @@ Travis.reopen console.log 'log view: create engine' if Log.DEBUG @scroll = new Log.Scroll @engine = Log.create(limit: Log.LIMIT, listeners: [@scroll]) - @lineSelector = new Travis.LinesSelector(@$().find('#log'), @scroll) + @logFolder = new Travis.LogFolder(@$().find('#log')) + @lineSelector = new Travis.LinesSelector(@$().find('#log'), @scroll, @logFolder) @observeParts() observeParts: -> @@ -76,11 +78,6 @@ Travis.reopen Travis.tailing.toggle() event.preventDefault() - click: (event) -> - target = $(event.target) - if target.prop('tagName') == 'P' - target.closest('.fold').toggleClass('open') - actions: toTop: () -> $(window).scrollTop(0) diff --git a/assets/scripts/lib/travis/lines_selector.coffee b/assets/scripts/lib/travis/lines_selector.coffee index ba4242cb..1f81002c 100644 --- a/assets/scripts/lib/travis/lines_selector.coffee +++ b/assets/scripts/lib/travis/lines_selector.coffee @@ -10,10 +10,12 @@ class Travis.LinesSelector element: null scroll: null location: null + view: null last_selected_line: null - constructor: (@element, @scroll, location) -> + constructor: (@element, @scroll, @folder, location) -> @location = location || @Location + Ember.run.scheduleOnce 'afterRender', this, -> @last_selected_line = @getSelectedLines()?.first @highlightLines() @@ -38,6 +40,13 @@ class Travis.LinesSelector if lines = @getSelectedLines() @element.find('p:visible').slice(lines.first - 1, lines.last).addClass('highlight') @scroll.tryScroll() + @unfoldLines() + + unfoldLines: -> + if lines = @getSelectedLines() + for index, l of lines + line = @element.find('p:visible').slice(l - 1, l) + @folder.unfold line setHashValueWithLine: (line, multiple) -> line_number = @getLineNumberFromElement(line) diff --git a/assets/scripts/lib/travis/log_folder.coffee b/assets/scripts/lib/travis/log_folder.coffee new file mode 100644 index 00000000..1d1bb1be --- /dev/null +++ b/assets/scripts/lib/travis/log_folder.coffee @@ -0,0 +1,24 @@ +class Travis.LogFolder + constructor: (@element) -> + @element.on 'click', '.fold', (event) => + folder = @getFolderFromLine $(event.target) + @toggle folder + + event.preventDefault() + false + + fold: (line) -> + folder = @getFolderFromLine(line) + if folder.hasClass('open') + @toggle(folder) + + unfold: (line) -> + folder = @getFolderFromLine(line) + unless folder.hasClass('open') + @toggle(folder) + + toggle: (folder) -> + folder.toggleClass('open') + + getFolderFromLine: (line) -> + line.parent('.fold') diff --git a/assets/scripts/spec/integration/log_spec.coffee b/assets/scripts/spec/integration/log_spec.coffee new file mode 100644 index 00000000..45e52032 --- /dev/null +++ b/assets/scripts/spec/integration/log_spec.coffee @@ -0,0 +1,35 @@ +module "Logs", + setup: -> + Ember.run -> Travis.advanceReadiness() + @sandbox = sinon.sandbox.create(); + $.mockjax + url: '/jobs/1/log?cors_hax=true' + responseTime: 0 + responseText: "First line\ncontent:travis_fold:start:install\r$ Install something\nInstalling something\ncontent:travis_fold:end:install\r$ End" + + teardown: -> + Ember.run -> Travis.reset() + @sandbox.restore(); + +test 'displaying the logs initializes the line selector', -> + selector_stub = + willDestroy: @sandbox.spy() + lineSelector = @sandbox.stub(Travis, "LinesSelector").returns(selector_stub) + visit('/travis-ci/travis-core/jobs/1').then -> + ok lineSelector.calledWithNew(), 'the lines selector has been initialized' + +test 'displaying the log initializes the logger', -> + log = @sandbox.stub(Log, "create").returns + set: @sandbox.spy() + scroll_stub = + tryScroll: @sandbox.spy() + scroll = @sandbox.stub(Log, "Scroll").returns(scroll_stub) + + visit('/travis-ci/travis-core/jobs/1').then -> + ok log.calledWith({limit: Log.LIMIT, listeners: [scroll_stub]}), 'the logger has been initialized' + +test 'displaying the logs initializes the log folder', -> + folder_stub = {} + logFolder = @sandbox.stub(Travis, "LogFolder").returns(folder_stub) + visit('/travis-ci/travis-core/jobs/1').then -> + ok logFolder.calledWithNew(), 'the logs folder has been initialized' diff --git a/assets/scripts/spec/unit/line_selector_spec.coffee b/assets/scripts/spec/unit/line_selector_spec.coffee index 04e882cf..93a5a7c3 100644 --- a/assets/scripts/spec/unit/line_selector_spec.coffee +++ b/assets/scripts/spec/unit/line_selector_spec.coffee @@ -7,6 +7,7 @@ fakeLocation = { fakeScroll = tryScroll: sinon.spy() +fakeFolder = {} element = jQuery('

first line

@@ -16,6 +17,7 @@ element = jQuery('
module "Travis.LinesSelector", setup: -> + fakeFolder.unfold = sinon.spy() fakeLocation.hash = '' jQuery('body').append(element) @@ -24,7 +26,7 @@ module "Travis.LinesSelector", test "defaults to no line selected", -> Ember.run -> - new Travis.LinesSelector(element, fakeScroll, fakeLocation) + new Travis.LinesSelector(element, fakeScroll, fakeFolder, fakeLocation) wait().then -> equal($('#fakeLog p.highlight').length, 0) @@ -32,7 +34,7 @@ test "defaults to no line selected", -> test "defaults to a single line selected", -> fakeLocation.hash = '#L2' Ember.run -> - new Travis.LinesSelector(element, fakeScroll, fakeLocation) + new Travis.LinesSelector(element, fakeScroll, fakeFolder, fakeLocation) wait().then -> equal($('#fakeLog p.highlight').length, 1) @@ -41,7 +43,7 @@ test "defaults to a single line selected", -> test "defaults to multiple lines selected", -> fakeLocation.hash = '#L2-L3' Ember.run -> - new Travis.LinesSelector(element, fakeScroll, fakeLocation) + new Travis.LinesSelector(element, fakeScroll, fakeFolder, fakeLocation) wait().then -> equal($('#fakeLog p.highlight').length, 2) @@ -50,7 +52,7 @@ test "defaults to multiple lines selected", -> test "selects a single line", -> Ember.run -> - new Travis.LinesSelector(element, fakeScroll, fakeLocation) + new Travis.LinesSelector(element, fakeScroll, fakeFolder, fakeLocation) wait().then -> equal($('#fakeLog p.highlight').length, 0) @@ -62,7 +64,7 @@ test "selects a single line", -> test "selects multiple lines", -> fakeLocation.hash = '#L2' Ember.run -> - new Travis.LinesSelector(element, fakeScroll, fakeLocation) + new Travis.LinesSelector(element, fakeScroll, fakeFolder, fakeLocation) wait().then -> equal($('#fakeLog p.highlight').length, 1) @@ -79,7 +81,7 @@ test "selects multiple lines", -> test "uses the last selected line as second selection line", -> selector = null Ember.run -> - selector = new Travis.LinesSelector(element, fakeScroll, fakeLocation) + selector = new Travis.LinesSelector(element, fakeScroll, fakeFolder, fakeLocation) wait().then -> $('#fakeLog p:last a').click() @@ -96,3 +98,11 @@ test "uses the last selected line as second selection line", -> equal($('#fakeLog p:nth-child(3)').hasClass('highlight'), true) equal('#L1-L3', fakeLocation.hash) equal(1, selector.last_selected_line) + +test "unfolds the first and last selected lines", -> + fakeLocation.hash = '#L1-L3' + Ember.run -> + new Travis.LinesSelector(element, fakeScroll, fakeFolder, fakeLocation) + + wait().then -> + ok(fakeFolder.unfold.calledTwice, 'the first and last lines have been unfolded') diff --git a/assets/scripts/spec/unit/log_folder_spec.coffee b/assets/scripts/spec/unit/log_folder_spec.coffee new file mode 100644 index 00000000..d683c45b --- /dev/null +++ b/assets/scripts/spec/unit/log_folder_spec.coffee @@ -0,0 +1,54 @@ +element = jQuery('
+

first line

+
+

second line

+

third line

+
+

fourth line

+
') +logFolder = null + +module "Travis.LogFolder", + setup: -> + jQuery('body').append(element) + logFolder = new Travis.LogFolder jQuery('#fakeLog') + + teardown: -> + element.remove() + +test "displays the fold", -> + equal($('#fakeLog .fold.open').length, 0) + $('#fakeLog .fold p:first').click() + equal($('#fakeLog .fold.open').length, 1) + +test "hides the fold", -> + $('#fakeLog .fold').addClass('open') + $('#fakeLog .fold p:first').click() + equal($('#fakeLog .fold.open').length, 0) + +test "binds new elements", -> + new_element = jQuery('
+

fifth line

+
') + jQuery('#fakeLog').append new_element + + equal($('#fakeLog .fold.open').length, 0) + $('#fakeLog .fold p:first-child').click() + equal($('#fakeLog .fold.open').length, 2) + +test "fold", -> + fold = jQuery('#fakeLog .fold') + line = fold.find('p:first') + fold.addClass('open') + + equal(fold.hasClass('open'), true) + logFolder.fold(line) + equal(fold.hasClass('open'), false) + +test "unfold", -> + fold = jQuery('#fakeLog .fold') + line = fold.find('p:first') + + equal(fold.hasClass('open'), false) + logFolder.unfold(line) + equal(fold.hasClass('open'), true)