mirror of
https://github.com/bilawalsidhu/gods-eye-view.git
synced 2026-11-15 15:52:21 +00:00
fix(cockpit): a failed refresh after a move never shows the last location's brief
Co-Authored-By: Claude Fable 5.2 <[email protected]>
This commit is contained in:
1 parent
369b8e924a
commit
9c0ad0a730
2 files changed
+80
-3
No files matched your search
@@ -187,6 +187,13 @@ export function maybeRefreshRegionalBrief(info) {
|
|||||||
)
|
)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
// The brief held stands in after a failed refresh only near where its news
|
||||||
|
// was read; past the refresh distance it is another place's.
|
||||||
|
const previous =
|
||||||
|
this.services.regionalDistanceM(this.regionalBriefPoint, point) <
|
||||||
|
COCKPIT_REGIONAL_REFRESH_DISTANCE_M
|
||||||
|
? this.regionalBrief
|
||||||
|
: null;
|
||||||
this.regionalBriefAnchor = point;
|
this.regionalBriefAnchor = point;
|
||||||
this.regionalBriefFetchedAt = Date.now();
|
this.regionalBriefFetchedAt = Date.now();
|
||||||
const controller = new AbortController();
|
const controller = new AbortController();
|
||||||
@@ -204,7 +211,8 @@ export function maybeRefreshRegionalBrief(info) {
|
|||||||
subjectId !== this.regionalBriefSubjectId
|
subjectId !== this.regionalBriefSubjectId
|
||||||
)
|
)
|
||||||
return;
|
return;
|
||||||
this.regionalBrief = withCachedNews(payload, this.regionalBrief);
|
this.regionalBrief = withCachedNews(payload, previous);
|
||||||
|
if (this.regionalBrief === payload) this.regionalBriefPoint = point;
|
||||||
this.renderRegionalBrief(this.regionalBrief, info);
|
this.renderRegionalBrief(this.regionalBrief, info);
|
||||||
})
|
})
|
||||||
.catch((error) => {
|
.catch((error) => {
|
||||||
@@ -214,8 +222,7 @@ export function maybeRefreshRegionalBrief(info) {
|
|||||||
requestToken === this.regionalBriefRequestToken &&
|
requestToken === this.regionalBriefRequestToken &&
|
||||||
subjectId === this.regionalBriefSubjectId
|
subjectId === this.regionalBriefSubjectId
|
||||||
) {
|
) {
|
||||||
if (this.regionalBrief) {
|
if (previous) {
|
||||||
const previous = this.regionalBrief;
|
|
||||||
this.regionalBrief = cachedNews(previous, previous);
|
this.regionalBrief = cachedNews(previous, previous);
|
||||||
this.renderRegionalBrief(this.regionalBrief, info);
|
this.renderRegionalBrief(this.regionalBrief, info);
|
||||||
} else this.renderRegionalBriefStatus('unavailable', info);
|
} else this.renderRegionalBriefStatus('unavailable', info);
|
||||||
|
|||||||
@@ -508,3 +508,73 @@ test('the card and its toggle render the collapse the controller presents', asyn
|
|||||||
assert.equal(card.dataset.collapsed, 'false');
|
assert.equal(card.dataset.collapsed, 'false');
|
||||||
assert.equal(toggle.textContent.trim(), 'right_panel_close');
|
assert.equal(toggle.textContent.trim(), 'right_panel_close');
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test("a refresh that fails after a move never shows the last location's brief as current", async (t) => {
|
||||||
|
const { $, text, owner } = fixture(t);
|
||||||
|
const answers = [];
|
||||||
|
Object.assign(owner, {
|
||||||
|
active: true,
|
||||||
|
regionalBriefSubjectId: null,
|
||||||
|
regionalBriefAbort: null,
|
||||||
|
regionalBriefRequestToken: 0,
|
||||||
|
regionalBriefFetchedAt: 0,
|
||||||
|
regionalBrief: null,
|
||||||
|
renderRegionalBrief,
|
||||||
|
renderRegionalBriefStatus,
|
||||||
|
});
|
||||||
|
owner.services = {
|
||||||
|
...owner.services,
|
||||||
|
// One degree of latitude stands for a move past the refresh distance.
|
||||||
|
regionalDistanceM: (from, to) =>
|
||||||
|
from ? Math.abs(from.latitude - to.latitude) * 111_000 : Infinity,
|
||||||
|
fetchRegionalBrief: () => answers.shift()(),
|
||||||
|
};
|
||||||
|
const refresh = async (answer, latitude) => {
|
||||||
|
answers.push(answer);
|
||||||
|
owner.regionalBriefFetchedAt = 0;
|
||||||
|
maybeRefreshRegionalBrief.call(owner, {
|
||||||
|
...INFO,
|
||||||
|
icao24: 'abc123',
|
||||||
|
latitude,
|
||||||
|
});
|
||||||
|
await new Promise((resolve) => setTimeout(resolve, 0));
|
||||||
|
await nextTick();
|
||||||
|
};
|
||||||
|
const rows = () => document.querySelectorAll('#cockpit-news-list li').length;
|
||||||
|
const here = () =>
|
||||||
|
Promise.resolve({
|
||||||
|
status: 'ready',
|
||||||
|
newsStatus: 'ready',
|
||||||
|
newsSource: 'Google News RSS',
|
||||||
|
newsWindowHours: 24,
|
||||||
|
newsFetchedAt: hoursAgo(1),
|
||||||
|
articles: [story('a'), story('b')],
|
||||||
|
});
|
||||||
|
showBriefPage.call(owner, 1);
|
||||||
|
|
||||||
|
await refresh(here, 40);
|
||||||
|
assert.equal(rows(), 2);
|
||||||
|
// The same place: a failed refresh keeps the rows as cached.
|
||||||
|
await refresh(() => Promise.reject(new TypeError('Failed to fetch')), 40);
|
||||||
|
assert.equal(text('#cockpit-news-status'), 'CACHED · REFRESH FAILED');
|
||||||
|
assert.equal(rows(), 2);
|
||||||
|
// Elsewhere: the brief is unavailable, as it was before there was a cache.
|
||||||
|
await refresh(() => Promise.reject(new TypeError('Failed to fetch')), 45);
|
||||||
|
assert.equal($('#cockpit-news-status').dataset.state, 'unavailable');
|
||||||
|
assert.equal(rows(), 0);
|
||||||
|
|
||||||
|
// Nor does a brief there whose news read failed borrow the last place's rows.
|
||||||
|
await refresh(here, 40);
|
||||||
|
assert.equal(rows(), 2);
|
||||||
|
await refresh(
|
||||||
|
() =>
|
||||||
|
Promise.resolve({
|
||||||
|
status: 'partial',
|
||||||
|
newsStatus: 'unavailable',
|
||||||
|
articles: [],
|
||||||
|
}),
|
||||||
|
45,
|
||||||
|
);
|
||||||
|
assert.equal($('#cockpit-news-status').dataset.state, 'unavailable');
|
||||||
|
assert.equal(rows(), 0);
|
||||||
|
});
|
||||||
Reference in new issue
Block a user