From c30d5f984ac280f33b9b82e29a4324688c7da055 Mon Sep 17 00:00:00 2001 From: Henry Jameson Date: Thu, 27 Aug 2026 14:57:23 +0300 Subject: [PATCH 1/9] fix posts being discarded when posting after preview request --- changelog.d/preview_posting.fix | 1 + src/components/post_status_form/post_status_form.js | 4 ++++ 2 files changed, 5 insertions(+) create mode 100644 changelog.d/preview_posting.fix diff --git a/changelog.d/preview_posting.fix b/changelog.d/preview_posting.fix new file mode 100644 index 000000000..1a35dbeba --- /dev/null +++ b/changelog.d/preview_posting.fix @@ -0,0 +1 @@ +Fix posting not working when using preview diff --git a/src/components/post_status_form/post_status_form.js b/src/components/post_status_form/post_status_form.js index 1acd211c4..ef012c9cf 100644 --- a/src/components/post_status_form/post_status_form.js +++ b/src/components/post_status_form/post_status_form.js @@ -721,6 +721,10 @@ const PostStatusForm = { }) .finally(() => { this.previewLoading = false + // If we post right after doing a preview request + // backend treats non-preview request as preview one + // and "eats" the post + this.updateIdempotencyKey() }) }, debouncePreviewStatus: debounce(function () { From d8e530581d417ce13502d81f6289ba815ab8f3b2 Mon Sep 17 00:00:00 2001 From: Henry Jameson Date: Thu, 27 Aug 2026 17:25:35 +0300 Subject: [PATCH 2/9] better display of empty/initially-loading timeline --- src/components/timeline/timeline.js | 1 + src/components/timeline/timeline.scss | 8 ++++ src/components/timeline/timeline.vue | 46 ++++++++++++-------- src/components/user_profile/user_profile.vue | 1 + src/stores/fetchers/timeline_fetcher.js | 6 ++- 5 files changed, 44 insertions(+), 18 deletions(-) diff --git a/src/components/timeline/timeline.js b/src/components/timeline/timeline.js index 3c7e33060..9a6d75c8a 100644 --- a/src/components/timeline/timeline.js +++ b/src/components/timeline/timeline.js @@ -31,6 +31,7 @@ const Timeline = { embedded: Boolean, inProfile: Boolean, skipPinned: Boolean, + hideEmpty: Boolean, }, data() { return { diff --git a/src/components/timeline/timeline.scss b/src/components/timeline/timeline.scss index 2dd66328d..984129bf4 100644 --- a/src/components/timeline/timeline.scss +++ b/src/components/timeline/timeline.scss @@ -4,6 +4,14 @@ backdrop-filter: none; } + .timeline-placeholder { + background: var(--background); + display: flex; + place-items: center; + place-content: center; + padding: 5em; + } + .alert-badge { font-size: 0.75em; line-height: 1; diff --git a/src/components/timeline/timeline.vue b/src/components/timeline/timeline.vue index 1435bba48..d5397546d 100644 --- a/src/components/timeline/timeline.vue +++ b/src/components/timeline/timeline.vue @@ -94,6 +94,24 @@ collapsable /> +
- {{ $t('timeline.no_statuses') }} -
-
{{ $t('timeline.no_more_statuses') }}
-
+
diff --git a/src/components/user_profile/user_profile.vue b/src/components/user_profile/user_profile.vue index 9a987cd09..43d91b8e5 100644 --- a/src/components/user_profile/user_profile.vue +++ b/src/components/user_profile/user_profile.vue @@ -30,6 +30,7 @@ :timeline-ref="{ name: 'userPinned', argument: userId }" embedded in-profile + hide-empty /> { const numStatusesBeforeFetch = timeline.statusIds.size - if (bottomedOut.value) return + if (older && bottomedOut.value) return return fetchTimeline(args) .then(({ data: statuses, pagination, timestamp }) => { + // No statuses for timeline, ever. + if (timeline.order.length === 0 && statuses.length === 0) { + bottomedOut.value = true + } if (!older && statuses.length >= 20 && numStatusesBeforeFetch > 0) { useTimelinesStore().requireReload(timeline.name) } From 21467735b028d4d3eec96c96681ac6b3b4d75e11 Mon Sep 17 00:00:00 2001 From: Henry Jameson Date: Thu, 27 Aug 2026 18:53:25 +0300 Subject: [PATCH 3/9] typo --- src/components/status/status.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/components/status/status.js b/src/components/status/status.js index a53812da1..c2850eac0 100644 --- a/src/components/status/status.js +++ b/src/components/status/status.js @@ -153,7 +153,7 @@ const Status = { showReasonMutedThread() { return ( (this.mainStatus.thread_muted || - this.smainSatus.reblog?.thread_muted) && + this.mainSatus.reblog?.thread_muted) && !this.inConversation ) }, From 01a99f9e8b0f3b87ef6d50f01b43ef8582eabafa Mon Sep 17 00:00:00 2001 From: Henry Jameson Date: Thu, 27 Aug 2026 20:28:04 +0300 Subject: [PATCH 4/9] lint --- src/components/status/status.js | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/components/status/status.js b/src/components/status/status.js index c2850eac0..43b0f4806 100644 --- a/src/components/status/status.js +++ b/src/components/status/status.js @@ -152,8 +152,7 @@ const Status = { }, showReasonMutedThread() { return ( - (this.mainStatus.thread_muted || - this.mainSatus.reblog?.thread_muted) && + (this.mainStatus.thread_muted || this.mainSatus.reblog?.thread_muted) && !this.inConversation ) }, From 4733eb7872426c607dc291659445b9b11aa0eb84 Mon Sep 17 00:00:00 2001 From: Henry Jameson Date: Thu, 27 Aug 2026 20:28:07 +0300 Subject: [PATCH 5/9] =?UTF-8?q?repr=C3=B6=C3=B6t=20deduplication?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/stores/fetchers/timeline_fetcher.js | 27 +++- src/stores/timelines.js | 66 +++++++- test/unit/specs/stores/timelines.spec.js | 197 +++++++++++++++++++++++ 3 files changed, 275 insertions(+), 15 deletions(-) diff --git a/src/stores/fetchers/timeline_fetcher.js b/src/stores/fetchers/timeline_fetcher.js index 90a5f845a..494377b94 100644 --- a/src/stores/fetchers/timeline_fetcher.js +++ b/src/stores/fetchers/timeline_fetcher.js @@ -54,25 +54,36 @@ const timelineFetcher = (timeline, argument, credentials) => { if (older && bottomedOut.value) return return fetchTimeline(args) - .then(({ data: statuses, pagination, timestamp }) => { + .then(({ data, pagination, timestamp }) => { // No statuses for timeline, ever. - if (timeline.order.length === 0 && statuses.length === 0) { + if (timeline.order.length === 0 && data.length === 0) { bottomedOut.value = true } - if (!older && statuses.length >= 20 && numStatusesBeforeFetch > 0) { + if (!older && data.length >= 20 && numStatusesBeforeFetch > 0) { useTimelinesStore().requireReload(timeline.name) } - if (older && statuses.length === 0) { + if (older && data.length === 0) { bottomedOut.value = true } - const processed = useStatusesStore() - .addNewStatuses({ statuses, timestamp }) - .map(({ id }) => id) + const processed = useStatusesStore().addNewStatuses({ + statuses: data, + timestamp, + }) + + const statuses = processed.map(({ id }) => id) + + const repeats = processed + .filter(({ retweeted_status }) => Boolean(retweeted_status)) + .map(({ id, retweeted_status: { id: repeatedId } }) => [ + id, + repeatedId, + ]) useTimelinesStore().addStatusesToTimeline(timeline.name, argument, { - statuses: processed, + statuses, + repeats, showImmediately, older, pagination, diff --git a/src/stores/timelines.js b/src/stores/timelines.js index 26223e69d..000415b52 100644 --- a/src/stores/timelines.js +++ b/src/stores/timelines.js @@ -21,6 +21,11 @@ const emptyTl = (name, argument = null) => { // Statuses shown to user visibleStatusIds: new Set(), + // Tracked reprööts, used to avoid displaying same reprööt more than once + repeatedToRepeat: new Map(), + repeatToRepeated: new Map(), + ignoredIds: new Set(), + // Number of statuses not shown yet newStatusCount: 0, @@ -188,6 +193,7 @@ export const useTimelinesStore = defineStore('timelines', { timeline.order = [] timeline.statusIds = new Set() timeline.visibleStatusIds = new Set() + timeline.ignoredIds = new Set() timeline.newStatusCount = 0 timeline.maxId = '' timeline.minId = '' @@ -252,6 +258,7 @@ export const useTimelinesStore = defineStore('timelines', { argument, { statuses, + repeats, showImmediately = false, noIdUpdate = false, pagination = {}, @@ -261,6 +268,8 @@ export const useTimelinesStore = defineStore('timelines', { if (statuses.length === 0) return const timeline = this[timelineName] + this.populateRepeats(timeline, repeats) + // This makes sure that user timeline won't get data meant for other // user. I.e. opening different user profiles makes request which could // return data late after user already viewing different user profile @@ -287,13 +296,18 @@ export const useTimelinesStore = defineStore('timelines', { timeline.statusIds.add(statusId) if (isNew) { - if (showImmediately) { - // Add it directly to the visibleStatuses, don't change - // newStatusCount - timeline.visibleStatusIds.add(statusId) + const seenBefore = this.checkSeenBefore(timeline, statusId) + if (!seenBefore) { + if (showImmediately) { + // Add it directly to the visibleStatuses, don't change + // newStatusCount + timeline.visibleStatusIds.add(statusId) + } else { + // Just change newStatuscount + timeline.newStatusCount += 1 + } } else { - // Just change newStatuscount - timeline.newStatusCount += 1 + timeline.ignoredIds.add(statusId) } } }) @@ -301,9 +315,43 @@ export const useTimelinesStore = defineStore('timelines', { onStreamMessage(timeline, argument, event) { this.addStatusesToTimeline(timeline, argument, { statuses: event.data.map(({ id }) => id), + repeats: event.data + .filter(({ retweeted_status }) => Boolean(retweeted_status)) + .map(({ id, retweeted_status: { id: repeatedId } }) => [ + id, + repeatedId, + ]), }) }, + // Reprööt handling + populateRepeats(timeline, repeats) { + // Starting from oldest + ;[...repeats].reverse().forEach(([repeatId, repeatedId]) => { + timeline.repeatToRepeated.set(repeatId, repeatedId) + const knownRepeats = + timeline.repeatedToRepeat.get(repeatedId) ?? new Set() + knownRepeats.add(repeatId) + timeline.repeatedToRepeat.set(repeatedId, knownRepeats) + }) + }, + checkSeenBefore(timeline, statusId) { + // Check if this is a reprööt + const repeatedStatusId = timeline.repeatToRepeated.get(statusId) + // Non-reprööts are never seen before + if (!repeatedStatusId) return false + // We've seen this status already directly + if (timeline.statusIds.has(repeatedStatusId)) return true + + // Check for reprööts + const knownRepeats = timeline.repeatedToRepeat.get(repeatedStatusId) + + // If it's the only reprööt then we've never seen post before + if (knownRepeats.size === 1) return false + // If we're working on oldest known reprööt then we've never seen it before + return first(knownRepeats) !== statusId + }, + // Poll & Push onStreamConnect(timeline) { console.debug('[Timelines] Stream connected', timeline) @@ -391,7 +439,11 @@ export const useTimelinesStore = defineStore('timelines', { timeline.newStatusCount = 0 timeline.order = timeline.order.slice(0, 50) timeline.statusIds = new Set([...timeline.order]) - timeline.visibleStatusIds = new Set([...timeline.order]) + + // Reprööts CAN be present in order but some must be ignored + timeline.visibleStatusIds = new Set([ + ...timeline.order.filter((id) => !timeline.ignoredIds.has(id)), + ]) this.updateTimelineExtremes(timeline) }, syncOrder(timeline) { diff --git a/test/unit/specs/stores/timelines.spec.js b/test/unit/specs/stores/timelines.spec.js index cfc84ea3d..6b4010c71 100644 --- a/test/unit/specs/stores/timelines.spec.js +++ b/test/unit/specs/stores/timelines.spec.js @@ -122,6 +122,7 @@ describe('Timelines store', () => { store.activate('list', '1') store.addStatusesToTimeline('list', '1', { statuses, + repeats: [], pagination: { minId: '1', maxId: '3' }, }) @@ -140,10 +141,12 @@ describe('Timelines store', () => { store.activate('list', '1') store.addStatusesToTimeline('list', '1', { statuses, + repeats: [], pagination: { minId: '1', maxId: '3' }, }) store.addStatusesToTimeline('list', '1', { statuses, + repeats: [], pagination: { minId: '1', maxId: '3' }, }) @@ -162,6 +165,7 @@ describe('Timelines store', () => { store.activate('list', '1') store.addStatusesToTimeline('list', '1', { statuses, + repeats: [], showImmediately: true, pagination: { minId: '1', maxId: '3' }, }) @@ -181,6 +185,7 @@ describe('Timelines store', () => { store.activate('list', '1') store.addStatusesToTimeline('list', '1', { statuses, + repeats: [], noIdUpdate: true, pagination: { minId: '1', maxId: '3' }, }) @@ -200,6 +205,7 @@ describe('Timelines store', () => { store.activate('list', '1') store.addStatusesToTimeline('list', '2', { statuses, + repeats: [], noIdUpdate: true, pagination: { minId: '1', maxId: '3' }, }) @@ -220,10 +226,12 @@ describe('Timelines store', () => { store.activate('list', '1') store.addStatusesToTimeline('list', '1', { statuses: statuses1, + repeats: [], pagination: { minId: '3', maxId: '1' }, }) store.addStatusesToTimeline('list', '1', { statuses: statuses2, + repeats: [], pagination: { minId: '6', maxId: '4' }, }) @@ -244,10 +252,12 @@ describe('Timelines store', () => { store.activate('list', '1') store.addStatusesToTimeline('list', '1', { statuses: statuses1, + repeats: [], pagination: { minId: '6', maxId: '4' }, }) store.addStatusesToTimeline('list', '1', { statuses: statuses2, + repeats: [], pagination: { minId: '3', maxId: '1' }, older: true, }) @@ -260,6 +270,171 @@ describe('Timelines store', () => { expect(store.list).to.have.property('maxId', '6') expect(store.list).to.have.property('minId', '1') }) + + describe('repeat de-duplication', () => { + it('handles repeat de-duplication (older)', () => { + const store = useTimelinesStore() + const statuses1 = ['s7s3', 's6s3', 's5', 's4s0', 's3', 's2'] + const statuses2 = ['s1s0', 's0'] + + store.activate('list', '1') + store.addStatusesToTimeline('list', '1', { + statuses: statuses1, + repeats: [ + ['s7s3', 's2'], + ['s6s3', 's2'], + ['s4s0', 's0'], + ], + pagination: { minId: 's7s3', maxId: 's2' }, + showImmediately: true, + }) + expect(store.list.order).to.eql(statuses1) + expect(store.list.statusIds).to.eql(new Set(statuses1)) + expect(store.list.visibleStatusIds).to.eql(new Set([ + 's5', + 's4s0', + 's3', + 's2', + ])) + expect(store.list).to.have.property('maxId', 's7s3') + expect(store.list).to.have.property('minId', 's2') + + store.addStatusesToTimeline('list', '1', { + statuses: statuses2, + repeats: [ + ['s1s0', 's0'], + ], + pagination: { minId: 's1', maxId: 's0' }, + showImmediately: true, + older: true + }) + + const newOrder = [...statuses1, ...statuses2] + expect(store.list.order).to.eql(newOrder) + expect(store.list.statusIds).to.eql(new Set(newOrder)) + expect(store.list.visibleStatusIds).to.eql(new Set([ + 's5', + 's4s0', + 's3', + 's2', + 's0', + ])) + expect(store.list).to.have.property('maxId', 's7s3') + expect(store.list).to.have.property('minId', 's0') + }) + + it('handles repeat de-duplication(reverse)', () => { + const store = useTimelinesStore() + const statuses1 = ['s6s2', 's5s2', 's4', 's3s0', 's2', 's1'] + const statuses2 = ['sAs0', 's9s1', 's8', 's7s2'] + + store.activate('list', '1') + store.addStatusesToTimeline('list', '1', { + statuses: statuses1, + repeats: [ + ['s6s2', 's2'], + ['s5s2', 's2'], + ['s3s0', 's0'], + ], + pagination: { minId: 's6s2', maxId: 's1' }, + showImmediately: true, + }) + expect(store.list.order).to.eql(statuses1) + expect(store.list.statusIds).to.eql(new Set(statuses1)) + expect(store.list.visibleStatusIds).to.eql(new Set([ + 's4', + 's3s0', + 's2', + 's1', + ])) + expect(store.list).to.have.property('maxId', 's6s2') + expect(store.list).to.have.property('minId', 's1') + + store.addStatusesToTimeline('list', '1', { + statuses: statuses2, + repeats: [ + ['sAs0', 's0'], + ['s9s1', 's1'], + ['s7s2', 's2'], + ], + pagination: { minId: 'sAs0', maxId: 's7s2' }, + showImmediately: true, + }) + + const newOrder = [...statuses2, ...statuses1] + expect(store.list.order).to.eql(newOrder) + expect(store.list.statusIds).to.eql(new Set(newOrder)) + expect(store.list.visibleStatusIds).to.eql(new Set([ + 's4', + 's3s0', + 's2', + 's1', + // Newer + 's8', + ])) + expect(store.list).to.have.property('maxId', 'sAs0') + expect(store.list).to.have.property('minId', 's1') + }) + + it('showNewStatuses follows de-duplication rules', () => { + const store = useTimelinesStore() + const statuses1 = ['s6s2', 's5s2', 's4', 's3s0', 's2', 's1'] + const statuses2 = ['sAs0', 's9s1', 's8', 's7s2'] + + store.activate('list', '1') + store.addStatusesToTimeline('list', '1', { + statuses: statuses1, + repeats: [ + ['s6s2', 's2'], + ['s5s2', 's2'], + ['s3s0', 's0'], + ], + pagination: { minId: 's6s2', maxId: 's1' }, + showImmediately: true, + }) + expect(store.list.order).to.eql(statuses1) + expect(store.list.statusIds).to.eql(new Set(statuses1)) + expect(store.list.visibleStatusIds).to.eql(new Set([ + 's4', + 's3s0', + 's2', + 's1', + ])) + expect(store.list).to.have.property('maxId', 's6s2') + expect(store.list).to.have.property('minId', 's1') + + store.addStatusesToTimeline('list', '1', { + statuses: statuses2, + repeats: [ + ['sAs0', 's0'], + ['s9s1', 's1'], + ['s7s2', 's2'], + ], + pagination: { minId: 'sAs0', maxId: 's7s2' }, + }) + + const newOrder = [...statuses2, ...statuses1] + expect(store.list.order).to.eql(newOrder) + expect(store.list.statusIds).to.eql(new Set(newOrder)) + expect(store.list.newStatusCount).to.eql(1) + expect(store.list.visibleStatusIds).to.eql(new Set([ + 's4', + 's3s0', + 's2', + 's1', + ])) + + store.showNewStatuses('list') + expect(store.list.visibleStatusIds).to.eql(new Set([ + 's4', + 's3s0', + 's2', + 's1', + // Newer + 's8', + ])) + }) + }) }) describe('showNewStatuses', () => { @@ -270,6 +445,7 @@ describe('Timelines store', () => { store.activate('public') store.addStatusesToTimeline('public', undefined, { statuses, + repeats: [], pagination: { minId: '1', maxId: '3' }, }) @@ -280,6 +456,25 @@ describe('Timelines store', () => { expect(store.public.visibleStatusIds).to.eql(new Set(statuses)) expect(store.public.newStatusCount).to.equal(0) }) + + it('limits shown items to 50 for better performance', () => { + const store = useTimelinesStore() + const statuses = new Array(100).fill().map((_, index) => 's' + index) + + store.activate('public') + store.addStatusesToTimeline('public', undefined, { + statuses, + repeats: [], + pagination: { minId: '1', maxId: '3' }, + }) + + expect(store.public.statusIds).to.eql(new Set(statuses)) + expect(store.public.visibleStatusIds).to.eql(new Set()) + expect(store.public.newStatusCount).to.equal(100) + store.showNewStatuses('public') + expect(store.public.visibleStatusIds).to.eql(new Set(statuses.slice(0, 50))) + expect(store.public.newStatusCount).to.equal(0) + }) }) describe('wipeStatuses', () => { @@ -290,9 +485,11 @@ describe('Timelines store', () => { store.activate('public') store.addStatusesToTimeline('public', undefined, { statuses: ['1', '2', '3', '0'], + repeats: [], }) store.addStatusesToTimeline('friends', undefined, { statuses: ['5', '0', '9', '1'], + repeats: [], }) store.wipeStatuses(['0']) expect(store.friends.statusIds).to.not.have.members('0') From 422c12c0266b8da898339a81ade1ef891b24de6b Mon Sep 17 00:00:00 2001 From: Henry Jameson Date: Thu, 27 Aug 2026 20:30:06 +0300 Subject: [PATCH 6/9] don't show "up to date" indicator together with loadingNewer indicator on mobile --- src/components/timeline/timeline.vue | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/components/timeline/timeline.vue b/src/components/timeline/timeline.vue index d5397546d..d3c3eced2 100644 --- a/src/components/timeline/timeline.vue +++ b/src/components/timeline/timeline.vue @@ -40,7 +40,7 @@
Date: Thu, 27 Aug 2026 20:43:20 +0300 Subject: [PATCH 7/9] fix --- src/stores/timelines.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/stores/timelines.js b/src/stores/timelines.js index 000415b52..ed4ecfaec 100644 --- a/src/stores/timelines.js +++ b/src/stores/timelines.js @@ -258,7 +258,7 @@ export const useTimelinesStore = defineStore('timelines', { argument, { statuses, - repeats, + repeats = [], showImmediately = false, noIdUpdate = false, pagination = {}, From a8166dff960ef23b716045e2693f2858a49ff4b1 Mon Sep 17 00:00:00 2001 From: Henry Jameson Date: Thu, 27 Aug 2026 20:56:46 +0300 Subject: [PATCH 8/9] fix virtual scrolling --- src/components/timeline/timeline.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/components/timeline/timeline.js b/src/components/timeline/timeline.js index 9a6d75c8a..872f61216 100644 --- a/src/components/timeline/timeline.js +++ b/src/components/timeline/timeline.js @@ -107,7 +107,7 @@ const Timeline = { const statusesPerSide = Math.ceil(Math.max(3, window.innerHeight / 80)) const min = Math.max(0, this.virtualScrollIndex - statusesPerSide) const max = Math.min(amount, this.virtualScrollIndex + statusesPerSide) - return new Set(this.timeline.order.slice(min, max)) + return new Set(this.filteredVisibleStatuses.slice(min, max).map(({id}) => id)) }, virtualScrollingEnabled() { return useMergedConfigStore().mergedConfig.virtualScrolling From 2297cf8ab039d6dba3b7ee0f94cd5cbca3510747 Mon Sep 17 00:00:00 2001 From: Henry Jameson Date: Thu, 27 Aug 2026 21:01:00 +0300 Subject: [PATCH 9/9] lint --- src/components/timeline/timeline.js | 4 +- test/unit/specs/stores/timelines.spec.js | 92 +++++++++++------------- 2 files changed, 43 insertions(+), 53 deletions(-) diff --git a/src/components/timeline/timeline.js b/src/components/timeline/timeline.js index 872f61216..ed9519e06 100644 --- a/src/components/timeline/timeline.js +++ b/src/components/timeline/timeline.js @@ -107,7 +107,9 @@ const Timeline = { const statusesPerSide = Math.ceil(Math.max(3, window.innerHeight / 80)) const min = Math.max(0, this.virtualScrollIndex - statusesPerSide) const max = Math.min(amount, this.virtualScrollIndex + statusesPerSide) - return new Set(this.filteredVisibleStatuses.slice(min, max).map(({id}) => id)) + return new Set( + this.filteredVisibleStatuses.slice(min, max).map(({ id }) => id), + ) }, virtualScrollingEnabled() { return useMergedConfigStore().mergedConfig.virtualScrolling diff --git a/test/unit/specs/stores/timelines.spec.js b/test/unit/specs/stores/timelines.spec.js index 6b4010c71..2b4704052 100644 --- a/test/unit/specs/stores/timelines.spec.js +++ b/test/unit/specs/stores/timelines.spec.js @@ -290,35 +290,26 @@ describe('Timelines store', () => { }) expect(store.list.order).to.eql(statuses1) expect(store.list.statusIds).to.eql(new Set(statuses1)) - expect(store.list.visibleStatusIds).to.eql(new Set([ - 's5', - 's4s0', - 's3', - 's2', - ])) + expect(store.list.visibleStatusIds).to.eql( + new Set(['s5', 's4s0', 's3', 's2']), + ) expect(store.list).to.have.property('maxId', 's7s3') expect(store.list).to.have.property('minId', 's2') store.addStatusesToTimeline('list', '1', { statuses: statuses2, - repeats: [ - ['s1s0', 's0'], - ], + repeats: [['s1s0', 's0']], pagination: { minId: 's1', maxId: 's0' }, showImmediately: true, - older: true + older: true, }) const newOrder = [...statuses1, ...statuses2] expect(store.list.order).to.eql(newOrder) expect(store.list.statusIds).to.eql(new Set(newOrder)) - expect(store.list.visibleStatusIds).to.eql(new Set([ - 's5', - 's4s0', - 's3', - 's2', - 's0', - ])) + expect(store.list.visibleStatusIds).to.eql( + new Set(['s5', 's4s0', 's3', 's2', 's0']), + ) expect(store.list).to.have.property('maxId', 's7s3') expect(store.list).to.have.property('minId', 's0') }) @@ -341,12 +332,9 @@ describe('Timelines store', () => { }) expect(store.list.order).to.eql(statuses1) expect(store.list.statusIds).to.eql(new Set(statuses1)) - expect(store.list.visibleStatusIds).to.eql(new Set([ - 's4', - 's3s0', - 's2', - 's1', - ])) + expect(store.list.visibleStatusIds).to.eql( + new Set(['s4', 's3s0', 's2', 's1']), + ) expect(store.list).to.have.property('maxId', 's6s2') expect(store.list).to.have.property('minId', 's1') @@ -364,14 +352,16 @@ describe('Timelines store', () => { const newOrder = [...statuses2, ...statuses1] expect(store.list.order).to.eql(newOrder) expect(store.list.statusIds).to.eql(new Set(newOrder)) - expect(store.list.visibleStatusIds).to.eql(new Set([ - 's4', - 's3s0', - 's2', - 's1', - // Newer - 's8', - ])) + expect(store.list.visibleStatusIds).to.eql( + new Set([ + 's4', + 's3s0', + 's2', + 's1', + // Newer + 's8', + ]), + ) expect(store.list).to.have.property('maxId', 'sAs0') expect(store.list).to.have.property('minId', 's1') }) @@ -394,12 +384,9 @@ describe('Timelines store', () => { }) expect(store.list.order).to.eql(statuses1) expect(store.list.statusIds).to.eql(new Set(statuses1)) - expect(store.list.visibleStatusIds).to.eql(new Set([ - 's4', - 's3s0', - 's2', - 's1', - ])) + expect(store.list.visibleStatusIds).to.eql( + new Set(['s4', 's3s0', 's2', 's1']), + ) expect(store.list).to.have.property('maxId', 's6s2') expect(store.list).to.have.property('minId', 's1') @@ -417,22 +404,21 @@ describe('Timelines store', () => { expect(store.list.order).to.eql(newOrder) expect(store.list.statusIds).to.eql(new Set(newOrder)) expect(store.list.newStatusCount).to.eql(1) - expect(store.list.visibleStatusIds).to.eql(new Set([ - 's4', - 's3s0', - 's2', - 's1', - ])) + expect(store.list.visibleStatusIds).to.eql( + new Set(['s4', 's3s0', 's2', 's1']), + ) store.showNewStatuses('list') - expect(store.list.visibleStatusIds).to.eql(new Set([ - 's4', - 's3s0', - 's2', - 's1', - // Newer - 's8', - ])) + expect(store.list.visibleStatusIds).to.eql( + new Set([ + 's4', + 's3s0', + 's2', + 's1', + // Newer + 's8', + ]), + ) }) }) }) @@ -472,7 +458,9 @@ describe('Timelines store', () => { expect(store.public.visibleStatusIds).to.eql(new Set()) expect(store.public.newStatusCount).to.equal(100) store.showNewStatuses('public') - expect(store.public.visibleStatusIds).to.eql(new Set(statuses.slice(0, 50))) + expect(store.public.visibleStatusIds).to.eql( + new Set(statuses.slice(0, 50)), + ) expect(store.public.newStatusCount).to.equal(0) }) })