forked from cybrespace/pinafore
truly fix streaming gap issue, remove sleeps from tests
This commit is contained in:
parent
eaa19f79e4
commit
00fd911579
|
@ -21,7 +21,8 @@ function processMessage (instanceName, timelineName, message) {
|
||||||
stop('processMessage')
|
stop('processMessage')
|
||||||
}
|
}
|
||||||
|
|
||||||
export function createStream (streamingApi, instanceName, accessToken, timelineName) {
|
export function createStream (streamingApi, instanceName, accessToken,
|
||||||
|
timelineName, onOpenStream) {
|
||||||
return new TimelineStream(streamingApi, accessToken, timelineName, {
|
return new TimelineStream(streamingApi, accessToken, timelineName, {
|
||||||
onMessage (msg) {
|
onMessage (msg) {
|
||||||
if (msg.event !== 'update' && msg.event !== 'delete' && msg.event !== 'notification') {
|
if (msg.event !== 'update' && msg.event !== 'delete' && msg.event !== 'notification') {
|
||||||
|
@ -33,6 +34,9 @@ export function createStream (streamingApi, instanceName, accessToken, timelineN
|
||||||
})
|
})
|
||||||
},
|
},
|
||||||
onOpen () {
|
onOpen () {
|
||||||
|
if (onOpenStream) {
|
||||||
|
onOpenStream()
|
||||||
|
}
|
||||||
console.log('opened stream for timeline', timelineName)
|
console.log('opened stream for timeline', timelineName)
|
||||||
},
|
},
|
||||||
onClose () {
|
onClose () {
|
||||||
|
|
|
@ -43,12 +43,12 @@ export function timelineObservers (store) {
|
||||||
let accessToken = store.get('accessToken')
|
let accessToken = store.get('accessToken')
|
||||||
await updateInstanceInfo(currentInstance)
|
await updateInstanceInfo(currentInstance)
|
||||||
|
|
||||||
let checkInstanceAndTimelineAreUnchanged = () => (
|
let currentTimelineIsUnchanged = () => (
|
||||||
store.get('currentInstance') === currentInstance &&
|
store.get('currentInstance') === currentInstance &&
|
||||||
store.get('currentTimeline') === currentTimeline
|
store.get('currentTimeline') === currentTimeline
|
||||||
)
|
)
|
||||||
|
|
||||||
if (!checkInstanceAndTimelineAreUnchanged()) {
|
if (!currentTimelineIsUnchanged()) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -56,23 +56,23 @@ export function timelineObservers (store) {
|
||||||
currentTimeline, 'timelineItemIds')
|
currentTimeline, 'timelineItemIds')
|
||||||
let firstTimelineItemId = timelineItemIds && timelineItemIds[0]
|
let firstTimelineItemId = timelineItemIds && timelineItemIds[0]
|
||||||
|
|
||||||
if (firstTimelineItemId) {
|
let onOpenStream = async () => {
|
||||||
|
if (!firstTimelineItemId || !currentTimelineIsUnchanged()) {
|
||||||
|
return
|
||||||
|
}
|
||||||
// fill in the "streaming gap" – i.e. fetch the most recent 20 items so that there isn't
|
// fill in the "streaming gap" – i.e. fetch the most recent 20 items so that there isn't
|
||||||
// a big gap in the timeline if you haven't looked at it in awhile
|
// a big gap in the timeline if you haven't looked at it in awhile
|
||||||
// TODO: race condition here, should start streaming while this request is ongoing
|
let newTimelineItems = await getTimeline(currentInstance, accessToken,
|
||||||
let newTimelineItems = await getTimeline(currentInstance, accessToken, currentTimeline,
|
currentTimeline, null, firstTimelineItemId)
|
||||||
null, firstTimelineItemId)
|
|
||||||
if (newTimelineItems.length) {
|
if (newTimelineItems.length) {
|
||||||
addStatusesOrNotifications(currentInstance, currentTimeline, newTimelineItems)
|
addStatusesOrNotifications(currentInstance, currentTimeline, newTimelineItems)
|
||||||
}
|
}
|
||||||
if (!checkInstanceAndTimelineAreUnchanged()) {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
let instanceInfo = store.get('currentInstanceInfo')
|
let instanceInfo = store.get('currentInstanceInfo')
|
||||||
currentTimelineStream = createStream(instanceInfo.urls.streaming_api,
|
let streamingApi = instanceInfo.urls.streaming_api
|
||||||
currentInstance, accessToken, currentTimeline)
|
currentTimelineStream = createStream(streamingApi, currentInstance, accessToken,
|
||||||
|
currentTimeline, onOpenStream)
|
||||||
|
|
||||||
if (process.env.NODE_ENV !== 'production') {
|
if (process.env.NODE_ENV !== 'production') {
|
||||||
window.currentTimelineStream = currentTimelineStream
|
window.currentTimelineStream = currentTimelineStream
|
||||||
|
|
|
@ -10,59 +10,56 @@ fixture`105-deletes.js`
|
||||||
.page`http://localhost:4002`
|
.page`http://localhost:4002`
|
||||||
|
|
||||||
test('deleted statuses are removed from the timeline', async t => {
|
test('deleted statuses are removed from the timeline', async t => {
|
||||||
|
let timeout = 20000
|
||||||
await t.useRole(foobarRole)
|
await t.useRole(foobarRole)
|
||||||
.hover(getNthStatus(0))
|
.hover(getNthStatus(0))
|
||||||
let status = await postAs('admin', "I'm gonna delete this")
|
let status = await postAs('admin', "I'm gonna delete this")
|
||||||
await sleep(1000)
|
await t.expect(getNthStatus(0).innerText).contains("I'm gonna delete this", {timeout})
|
||||||
await t.expect(getNthStatus(0).innerText).contains("I'm gonna delete this")
|
|
||||||
await deleteAs('admin', status.id)
|
await deleteAs('admin', status.id)
|
||||||
await sleep(1000)
|
await t.expect(getNthStatus(0).innerText).notContains("I'm gonna delete this", {timeout})
|
||||||
await t.expect(getNthStatus(0).innerText).notContains("I'm gonna delete this")
|
|
||||||
await clickToNotificationsAndBackHome(t)
|
await clickToNotificationsAndBackHome(t)
|
||||||
await t.expect(getNthStatus(0).innerText).notContains("I'm gonna delete this")
|
await t.expect(getNthStatus(0).innerText).notContains("I'm gonna delete this", {timeout})
|
||||||
await t.navigateTo('/notifications')
|
await t.navigateTo('/notifications')
|
||||||
await forceOffline()
|
await forceOffline()
|
||||||
await t.click(homeNavButton)
|
await t.click(homeNavButton)
|
||||||
await t.expect(getNthStatus(0).innerText).notContains("I'm gonna delete this")
|
await t.expect(getNthStatus(0).innerText).notContains("I'm gonna delete this", {timeout})
|
||||||
await forceOnline()
|
await forceOnline()
|
||||||
await t
|
await t
|
||||||
.navigateTo('/')
|
.navigateTo('/')
|
||||||
.expect(getNthStatus(0).innerText).notContains("I'm gonna delete this")
|
.expect(getNthStatus(0).innerText).notContains("I'm gonna delete this", {timeout})
|
||||||
})
|
})
|
||||||
|
|
||||||
test('deleted statuses are removed from threads', async t => {
|
test('deleted statuses are removed from threads', async t => {
|
||||||
|
let timeout = 20000
|
||||||
await t.useRole(foobarRole)
|
await t.useRole(foobarRole)
|
||||||
.hover(getNthStatus(0))
|
.hover(getNthStatus(0))
|
||||||
let status = await postAs('admin', "I won't delete this")
|
let status = await postAs('admin', "I won't delete this")
|
||||||
let reply = await postReplyAs('admin', 'But I will delete this', status.id)
|
let reply = await postReplyAs('admin', 'But I will delete this', status.id)
|
||||||
await sleep(5000)
|
await t.expect(getNthStatus(0).innerText).contains('But I will delete this', {timeout})
|
||||||
await t.expect(getNthStatus(0).innerText).contains('But I will delete this')
|
.expect(getNthStatus(1).innerText).contains("I won't delete this", {timeout})
|
||||||
.expect(getNthStatus(1).innerText).contains("I won't delete this")
|
|
||||||
.click(getNthStatus(1))
|
.click(getNthStatus(1))
|
||||||
.expect(getUrl()).contains('/statuses')
|
.expect(getUrl()).contains('/statuses')
|
||||||
.expect(getNthStatus(0).innerText).contains("I won't delete this")
|
.expect(getNthStatus(0).innerText).contains("I won't delete this", {timeout})
|
||||||
.expect(getNthStatus(1).innerText).contains('But I will delete this')
|
.expect(getNthStatus(1).innerText).contains('But I will delete this', {timeout})
|
||||||
await deleteAs('admin', reply.id)
|
await deleteAs('admin', reply.id)
|
||||||
await sleep(1000)
|
|
||||||
await t.expect(getNthStatus(1).exists).notOk()
|
await t.expect(getNthStatus(1).exists).notOk()
|
||||||
.expect(getNthStatus(0).innerText).contains("I won't delete this")
|
.expect(getNthStatus(0).innerText).contains("I won't delete this", {timeout})
|
||||||
await t.navigateTo('/')
|
await t.navigateTo('/')
|
||||||
await forceOffline()
|
await forceOffline()
|
||||||
await t.click(getNthStatus(0))
|
await t.click(getNthStatus(0))
|
||||||
.expect(getUrl()).contains('/statuses')
|
.expect(getUrl()).contains('/statuses')
|
||||||
.expect(getNthStatus(1).exists).notOk()
|
.expect(getNthStatus(1).exists).notOk()
|
||||||
.expect(getNthStatus(0).innerText).contains("I won't delete this")
|
.expect(getNthStatus(0).innerText).contains("I won't delete this", {timeout})
|
||||||
await forceOnline()
|
await forceOnline()
|
||||||
})
|
})
|
||||||
|
|
||||||
test('deleted statuses result in deleted notifications', async t => {
|
test('deleted statuses result in deleted notifications', async t => {
|
||||||
|
let timeout = 20000
|
||||||
await t.useRole(foobarRole)
|
await t.useRole(foobarRole)
|
||||||
.hover(getNthStatus(0))
|
.hover(getNthStatus(0))
|
||||||
.expect(notificationsNavButton.getAttribute('aria-label')).eql('Notifications')
|
.expect(notificationsNavButton.getAttribute('aria-label')).eql('Notifications')
|
||||||
let status = await postAs('admin', "@foobar yo yo foobar what's up")
|
let status = await postAs('admin', "@foobar yo yo foobar what's up")
|
||||||
await sleep(2000)
|
await t.expect(notificationsNavButton.getAttribute('aria-label')).eql('Notifications (1)', {timeout})
|
||||||
await t.expect(notificationsNavButton.getAttribute('aria-label')).eql('Notifications (1)')
|
|
||||||
await deleteAs('admin', status.id)
|
await deleteAs('admin', status.id)
|
||||||
await sleep(5000)
|
await t.expect(notificationsNavButton.getAttribute('aria-label')).eql('Notifications', {timeout})
|
||||||
await t.expect(notificationsNavButton.getAttribute('aria-label')).eql('Notifications')
|
|
||||||
})
|
})
|
||||||
|
|
|
@ -10,7 +10,7 @@ fixture`107-streaming-gap.js`
|
||||||
.page`http://localhost:4002`
|
.page`http://localhost:4002`
|
||||||
|
|
||||||
test('fills in a status posted while away from timeline', async t => {
|
test('fills in a status posted while away from timeline', async t => {
|
||||||
let timeout = 20000
|
let timeout = 30000
|
||||||
|
|
||||||
await t.useRole(foobarRole)
|
await t.useRole(foobarRole)
|
||||||
.click(localTimelineNavButton)
|
.click(localTimelineNavButton)
|
||||||
|
@ -23,7 +23,7 @@ test('fills in a status posted while away from timeline', async t => {
|
||||||
await t.expect(getNthStatus(0).innerText).contains('posted this while you were away!', {timeout})
|
await t.expect(getNthStatus(0).innerText).contains('posted this while you were away!', {timeout})
|
||||||
.click(localTimelineNavButton)
|
.click(localTimelineNavButton)
|
||||||
.expect(getNthStatus(0).innerText).contains('posted this while you were away!', {timeout})
|
.expect(getNthStatus(0).innerText).contains('posted this while you were away!', {timeout})
|
||||||
await sleep(2000)
|
.expect(getNthStatus(1).innerText).contains('heyo', {timeout})
|
||||||
await postAs('admin', 'posted this while you were watching')
|
await postAs('admin', 'posted this while you were watching')
|
||||||
await t.expect(getNthStatus(0).innerText).contains('posted this while you were watching', {timeout})
|
await t.expect(getNthStatus(0).innerText).contains('posted this while you were watching', {timeout})
|
||||||
})
|
})
|
||||||
|
|
Loading…
Reference in New Issue