Merge branch 'master' into ps-ember-update

Conflicts:
	assets/scripts/app/models/artifact.coffee
	assets/scripts/app/store.coffee
	assets/scripts/app/views/job.coffee
	assets/scripts/spec/spec_helper.coffee
This commit is contained in:
Piotr Sarnacki 2013-03-12 13:47:20 +01:00
commit e02ece9424
3 changed files with 185 additions and 1 deletions

View File

@ -0,0 +1,92 @@
get = Ember.get
Travis.ChunkBuffer = Em.ArrayProxy.extend
timeout: 5000
checkTimeoutFrequency: 1000
start: 1
next: 1
init: ->
@_super.apply this, arguments
@lastInsert = 0
@set('next', @get('start'))
@checkTimeout()
if @get('content.length')
@get('queue.content').pushObjects @get('content').toArray()
arrangedContent: (->
[]
).property('content')
addObject: (obj) ->
@get('content').pushObject(obj)
removeObject: (obj) ->
@get('content').removeObject(obj)
replaceContent: (idx, amt, objects) ->
@get('content').replace(idx, amt, objects)
queue: (->
Em.ArrayProxy.create(Em.SortableMixin,
content: []
sortProperties: ['number']
sortAscending: true
)
).property()
contentArrayDidChange: (array, index, removedCount, addedCount) ->
@_super.apply this, arguments
if addedCount
queue = @get('queue.content')
addedObjects = array.slice(index, index + addedCount)
console.log 'Added log parts with numbers:', addedObjects.map( (element) -> get(element, 'number') )+'', 'current', @get('next')
queue.pushObjects addedObjects
@check()
@inserted()
check: ->
queue = @get('queue')
next = @get('next')
arrangedContent = @get('arrangedContent')
toPush = []
while queue.get('firstObject.number') <= next
element = queue.shiftObject()
if get(element, 'number') == next
toPush.pushObject get(element, 'content')
next += 1
if toPush.length
arrangedContent.pushObjects toPush
@set('next', next)
inserted: ->
now = @now()
@lastInsert = now
checkTimeout: ->
now = @now()
if now - @lastInsert > @get('timeout')
@giveUpOnMissingParts()
@set 'runLaterId', Ember.run.later(this, @checkTimeout, @get('checkTimeoutFrequency'))
willDestroy: ->
Ember.run.cancel @get('runLaterId')
@_super.apply this, arguments
now: ->
(new Date()).getTime()
giveUpOnMissingParts: ->
if number = @get('queue.firstObject.number')
console.log 'Giving up on missing parts in the buffer, switching to:', number
@set('next', number)
@check()

View File

@ -6,7 +6,6 @@ minispade.require 'app'
waits(50)
runs ->
Travis.reset()
url = "/#{url}" unless url.match /^\//
Travis.__container__.lookup('router:main').handleURL(url)

View File

@ -0,0 +1,93 @@
createChunk = (number, content) ->
Em.Object.create(number: number, content: content)
describe 'Travis.ChunkBuffer', ->
it 'waits for parts to be in order before revealing them', ->
buffer = Travis.ChunkBuffer.create(content: [])
buffer.pushObject createChunk(3, "baz")
buffer.pushObject createChunk(2, "bar")
expect(buffer.get('length')).toEqual(0)
buffer.pushObject createChunk(1, "foo")
expect(buffer.get('length')).toEqual(3)
expect(buffer.toArray()).toEqual(['foo', 'bar', 'baz'])
it 'ignores a part if it fails to be delivered within timeout', ->
buffer = Travis.ChunkBuffer.create(content: [], timeout: 20, checkTimeoutFrequency: 5)
buffer.pushObject createChunk(3, "baz")
expect(buffer.get('length')).toEqual(0)
buffer.pushObject createChunk(1, "foo")
expect(buffer.get('length')).toEqual(1)
waits 40
runs ->
expect(buffer.get('length')).toEqual(2)
expect(buffer.toArray()).toEqual(['foo', 'baz'])
buffer.destroy()
it 'works correctly when parts are passed as content', ->
content = [createChunk(2, 'bar')]
buffer = Travis.ChunkBuffer.create(content: content)
expect(buffer.get('length')).toEqual(0)
buffer.pushObject createChunk(1, "foo")
expect(buffer.get('length')).toEqual(2)
expect(buffer.toArray()).toEqual(['foo', 'bar'])
it 'works correctly when parts duplicated', ->
buffer = Travis.ChunkBuffer.create(content: [])
buffer.pushObject createChunk(1, "foo")
buffer.pushObject createChunk(2, "bar")
buffer.pushObject createChunk(3, "baz")
buffer.pushObject createChunk(2, "bar")
buffer.pushObject createChunk(3, "baz")
buffer.pushObject createChunk(4, "qux")
expect(buffer.get('length')).toEqual(4)
expect(buffer.toArray()).toEqual(['foo', 'bar', 'baz', 'qux'])
it 'fires array observers properly', ->
changes = []
buffer = Travis.ChunkBuffer.create(content: [])
observer = Em.Object.extend(
init: ->
@_super.apply this, arguments
@get('content').addArrayObserver this,
willChange: 'arrayWillChange',
didChange: 'arrayDidChange'
arrayWillChange: (->)
arrayDidChange: (array, index, removedCount, addedCount) ->
changes.pushObject([index, addedCount])
).create(content: buffer)
buffer.pushObject createChunk(2, "baz")
expect(buffer.get('length')).toEqual(0)
expect(changes.length).toEqual(0)
buffer.pushObject createChunk(1, "foo")
expect(buffer.get('length')).toEqual(2)
expect(changes.length).toEqual(1)
expect(changes[0]).toEqual([0, 2])
it 'sets next to start if start is given at init', ->
buffer = Travis.ChunkBuffer.create(content: [], start: 5)
expect(buffer.get('next')).toEqual(5)