From 325c1c5f15e965b449a0cc8b553da832e9c8e684 Mon Sep 17 00:00:00 2001 From: Andrey Epifancev Date: Wed, 28 Oct 2026 22:22:43 +0400 Subject: [PATCH] =?UTF-8?q?perf(web):=20=D1=81=D0=B2=D0=BE=D0=B4=202=20?= =?UTF-8?q?=E2=80=94=20begin(load)=20=D0=BD=D0=B5=20=D0=BE=D1=87=D0=B8?= =?UTF-8?q?=D1=89=D0=B0=D0=B5=D1=82=20=D0=B4=D0=B0=D0=BD=D0=BD=D1=8B=D0=B5?= =?UTF-8?q?=20=D0=B4=D0=BE=20=D0=BF=D0=B5=D1=80=D0=B2=D0=BE=D0=B3=D0=BE=20?= =?UTF-8?q?=D0=BE=D1=82=D0=B2=D0=B5=D1=82=D0=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-Authored-By: Claude Opus 5.5 --- web/src/pages/Svod2Page/svod2Paging.js | 3 ++- web/src/pages/Svod2Page/svod2Paging.test.js | 23 +++++++++++++++++++++ 2 files changed, 25 insertions(+), 1 deletion(-) diff --git a/web/src/pages/Svod2Page/svod2Paging.js b/web/src/pages/Svod2Page/svod2Paging.js index da917f3..0ca4367 100644 --- a/web/src/pages/Svod2Page/svod2Paging.js +++ b/web/src/pages/Svod2Page/svod2Paging.js @@ -125,6 +125,8 @@ export function createSheetPagingState() { }; } +// Инвариант для хука: settled надо слать для КАЖДОГО поколения; settled старого поколения игнорируется, +// поэтому loading, выставленный begin(load), снимает только settled текущего поколения. export function svod2PagingReducer(state, action) { if (action.generation !== state.generation && action.type !== 'begin') return state; switch (action.type) { @@ -135,7 +137,6 @@ export function svod2PagingReducer(state, action) { pendingQueryKey: action.queryKey, error: '', loading: action.mode === 'load' ? true : state.loading, - ...(action.mode === 'load' ? { pages: new Map(), total: 0, facets: null } : {}), }; case 'page': { const first = state.dataGeneration !== action.generation; diff --git a/web/src/pages/Svod2Page/svod2Paging.test.js b/web/src/pages/Svod2Page/svod2Paging.test.js index 02b585e..07e9c16 100644 --- a/web/src/pages/Svod2Page/svod2Paging.test.js +++ b/web/src/pages/Svod2Page/svod2Paging.test.js @@ -256,3 +256,26 @@ test('facets и settled текущего поколения', () => { s = svod2PagingReducer(s, { type: 'settled', generation: 1 }); assert.equal(s.loading, false); }); + +test('begin(load) оставляет прежние pages/total/facets до первого ответа нового поколения', () => { + let s = begin(createSheetPagingState(), 1, 'load'); + s = page(s, 1, 0, ['a'], 5); + s = svod2PagingReducer(s, { type: 'facets', generation: 1, facets: { total: 5 } }); + s = begin(s, 2, 'load', 'k2'); + assert.equal(s.loading, true); + assert.deepEqual(s.pages.get(0), ['a']); + assert.equal(s.total, 5); + assert.deepEqual(s.facets, { total: 5 }); + s = page(s, 2, 0, ['z'], 1); + assert.deepEqual([...s.pages.keys()], [0]); + assert.deepEqual(s.pages.get(0), ['z']); +}); + +test('refine поверх load: loading снимает settled нового поколения, старого - игнорируется', () => { + let s = begin(createSheetPagingState(), 1, 'load'); + s = begin(s, 2, 'refine'); + assert.equal(s.loading, true); + assert.equal(svod2PagingReducer(s, { type: 'settled', generation: 1 }), s); + s = svod2PagingReducer(s, { type: 'settled', generation: 2 }); + assert.equal(s.loading, false); +});