@zeniai/client-epic-state 4.19.37-betaVR13 → 4.19.37-betaVR15

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -4,7 +4,7 @@ import { convertToPeriod, toMonthYearPeriodId, } from '../../../../commonStateTy
4
4
  import { getCurrentTenant } from '../../../../entity/tenant/tenantSelector';
5
5
  import { updateTransactions } from '../../../../entity/transaction/transactionReducer';
6
6
  import { createZeniAPIStatus, isSuccessResponse, } from '../../../../responsePayload';
7
- import { fetchCompletedTransactions, fetchCompletedTransactionsFailure, fetchCompletedTransactionsSuccess, } from '../../reducers/missingReceiptsViewReducer';
7
+ import { fetchCompletedTransactions, fetchCompletedTransactionsFailure, fetchCompletedTransactionsSuccess, getCompletedTransactionsCacheKey, } from '../../reducers/missingReceiptsViewReducer';
8
8
  export const fetchCompletedTransactionsEpic = (actions$, state$, zeniAPI) => actions$.pipe(filter(fetchCompletedTransactions.match), switchMap((action) => {
9
9
  const state = state$.value;
10
10
  const { expenseAutomationViewState: { selectedPeriodByTenantId }, expenseAutomationMissingReceiptsViewState: { bulkUpload }, } = state;
@@ -12,8 +12,12 @@ export const fetchCompletedTransactionsEpic = (actions$, state$, zeniAPI) => act
12
12
  const selectedPeriod = selectedPeriodByTenantId[currentTenant.tenantId];
13
13
  const periodId = toMonthYearPeriodId(selectedPeriod);
14
14
  const isInitialLoad = action.payload.pageToken == null;
15
- const existingData = bulkUpload.completedTransactionsByPeriod[periodId];
16
- if (isInitialLoad && existingData != null && existingData.transactionIds.length > 0) {
15
+ const cacheKey = getCompletedTransactionsCacheKey(periodId, bulkUpload.sortKey, bulkUpload.sortOrder, bulkUpload.completedSubTab);
16
+ const existingData = bulkUpload.completedTransactionsByPeriod[cacheKey];
17
+ if (isInitialLoad &&
18
+ action.payload.cacheOverride !== true &&
19
+ existingData != null &&
20
+ existingData.transactionIds.length > 0) {
17
21
  return from([]);
18
22
  }
19
23
  const period = convertToPeriod(selectedPeriod);
@@ -1,5 +1,6 @@
1
1
  import { createSlice } from '@reduxjs/toolkit';
2
2
  import { toMonthYearPeriodId } from '../../../commonStateTypes/timePeriod';
3
+ export const getCompletedTransactionsCacheKey = (periodId, sortKey, sortOrder, subTab) => `completed-${subTab}-${sortKey}-${sortOrder === 'ascending' ? 'asc' : 'desc'}-${periodId}`;
3
4
  export const initialBulkUploadState = {
4
5
  batchDetailsById: {},
5
6
  batchDetailsPaginationState: { fetchState: 'Not-Started', error: undefined },
@@ -210,7 +211,6 @@ const expenseAutomationMissingReceiptsView = createSlice({
210
211
  error: undefined,
211
212
  };
212
213
  },
213
- // eslint-disable-next-line @typescript-eslint/no-unused-vars
214
214
  fetchMoreBatchDetails(_draft) {
215
215
  _draft.bulkUpload.batchDetailsPaginationState = {
216
216
  fetchState: 'In-Progress',
@@ -302,7 +302,6 @@ const expenseAutomationMissingReceiptsView = createSlice({
302
302
  },
303
303
  setBulkUploadCompletedSubTab(draft, action) {
304
304
  draft.bulkUpload.completedSubTab = action.payload;
305
- draft.bulkUpload.completedTransactionsByPeriod = {};
306
305
  },
307
306
  setBulkUploadSortConfig(draft, action) {
308
307
  draft.bulkUpload.sortKey = action.payload.sortKey;
@@ -357,15 +356,16 @@ const expenseAutomationMissingReceiptsView = createSlice({
357
356
  }
358
357
  }
359
358
  },
360
- prepare(pageToken) {
361
- return { payload: { pageToken } };
359
+ prepare(pageToken, cacheOverride) {
360
+ return { payload: { pageToken, cacheOverride } };
362
361
  },
363
362
  },
364
363
  fetchCompletedTransactionsSuccess(draft, action) {
365
364
  const { transactionIds, nextPageToken, totalCount, selectedPeriod, isInitialLoad } = action.payload;
366
365
  const periodId = toMonthYearPeriodId(selectedPeriod);
366
+ const cacheKey = getCompletedTransactionsCacheKey(periodId, draft.bulkUpload.sortKey, draft.bulkUpload.sortOrder, draft.bulkUpload.completedSubTab);
367
367
  if (isInitialLoad) {
368
- draft.bulkUpload.completedTransactionsByPeriod[periodId] = {
368
+ draft.bulkUpload.completedTransactionsByPeriod[cacheKey] = {
369
369
  transactionIds,
370
370
  nextPageToken,
371
371
  totalCount,
@@ -373,7 +373,7 @@ const expenseAutomationMissingReceiptsView = createSlice({
373
373
  };
374
374
  }
375
375
  else {
376
- const existing = draft.bulkUpload.completedTransactionsByPeriod[periodId];
376
+ const existing = draft.bulkUpload.completedTransactionsByPeriod[cacheKey];
377
377
  if (existing != null) {
378
378
  existing.transactionIds.push(...transactionIds);
379
379
  existing.nextPageToken = nextPageToken;
@@ -381,7 +381,7 @@ const expenseAutomationMissingReceiptsView = createSlice({
381
381
  existing.fetchState = { fetchState: 'Completed', error: undefined };
382
382
  }
383
383
  else {
384
- draft.bulkUpload.completedTransactionsByPeriod[periodId] = {
384
+ draft.bulkUpload.completedTransactionsByPeriod[cacheKey] = {
385
385
  transactionIds,
386
386
  nextPageToken,
387
387
  totalCount,
@@ -392,7 +392,8 @@ const expenseAutomationMissingReceiptsView = createSlice({
392
392
  },
393
393
  fetchCompletedTransactionsFailure(draft, action) {
394
394
  const periodId = toMonthYearPeriodId(action.payload.selectedPeriod);
395
- const existing = draft.bulkUpload.completedTransactionsByPeriod[periodId];
395
+ const cacheKey = getCompletedTransactionsCacheKey(periodId, draft.bulkUpload.sortKey, draft.bulkUpload.sortOrder, draft.bulkUpload.completedSubTab);
396
+ const existing = draft.bulkUpload.completedTransactionsByPeriod[cacheKey];
396
397
  if (existing != null) {
397
398
  existing.fetchState = {
398
399
  fetchState: 'Error',
@@ -400,7 +401,7 @@ const expenseAutomationMissingReceiptsView = createSlice({
400
401
  };
401
402
  }
402
403
  else {
403
- draft.bulkUpload.completedTransactionsByPeriod[periodId] = {
404
+ draft.bulkUpload.completedTransactionsByPeriod[cacheKey] = {
404
405
  fetchState: { fetchState: 'Error', error: action.payload.error },
405
406
  nextPageToken: null,
406
407
  totalCount: 0,
@@ -3,6 +3,7 @@ import { toMonthYearPeriodId } from '../../../commonStateTypes/timePeriod';
3
3
  import { getCurrentTenant } from '../../../entity/tenant/tenantSelector';
4
4
  import { getSupportedTransactionById, getSupportedTransactionsByIds, } from '../../../entity/transaction/transactionSelector';
5
5
  import { getAllSteps } from '../selectorTypes/expenseAutomationViewSelectorTypes';
6
+ import { getCompletedTransactionsCacheKey } from '../reducers/missingReceiptsViewReducer';
6
7
  export function getExpenseAutomationMissingReceiptsView(state) {
7
8
  const { expenseAutomationMissingReceiptsViewState, expenseAutomationViewState, transactionState, monthEndCloseChecksState, } = state;
8
9
  const currentTenant = getCurrentTenant(state);
@@ -54,14 +55,19 @@ export function getExpenseAutomationMissingReceiptsView(state) {
54
55
  const batchList = monthYearPeriodId != null
55
56
  ? bulkUpload.batchListByPeriod[monthYearPeriodId] ?? []
56
57
  : [];
57
- const completedBatchesSorted = orderBy(batchList.filter((b) => b.status === 'completed'), (b) => b.createdAt, 'desc');
58
- const effectiveCurrentBatchId = bulkUpload.currentBatchId ?? completedBatchesSorted[0]?.batchId;
59
- const currentBatchDetails = effectiveCurrentBatchId != null
60
- ? bulkUpload.batchDetailsById[effectiveCurrentBatchId]
58
+ /** Completed batches in the same order as the batches API (batchList). First = primary "Unmatched" batch. */
59
+ const completedBatchesInApiOrder = batchList.filter((b) => b.status === 'completed');
60
+ const firstCompletedBatchId = completedBatchesInApiOrder[0]?.batchId;
61
+ /** During upload/matching, the in-flight batch may not appear in batchList yet — prefer currentBatchId. */
62
+ const unmatchedSectionBatchId = bulkUpload.phase === 'matching' || bulkUpload.phase === 'uploading'
63
+ ? bulkUpload.currentBatchId ?? firstCompletedBatchId
64
+ : firstCompletedBatchId;
65
+ const currentBatchDetails = unmatchedSectionBatchId != null
66
+ ? bulkUpload.batchDetailsById[unmatchedSectionBatchId]
61
67
  : undefined;
62
68
  const resolvedFiles = currentBatchDetails?.files.map((file) => resolveBatchFile(file, currentBatchDetails.batchId, transactionState));
63
69
  const failedIds = new Set(bulkUpload.failedBatchDetailIds);
64
- const hasMoreBatchDetails = completedBatchesSorted.some((b) => bulkUpload.batchDetailsById[b.batchId] == null &&
70
+ const hasMoreBatchDetails = completedBatchesInApiOrder.some((b) => bulkUpload.batchDetailsById[b.batchId] == null &&
65
71
  !failedIds.has(b.batchId));
66
72
  const getSortValue = (file) => {
67
73
  const t = file.matchedTransaction;
@@ -101,7 +107,7 @@ export function getExpenseAutomationMissingReceiptsView(state) {
101
107
  }
102
108
  : { total: 0, processed: 0, percentage: 0 };
103
109
  const batchListFetchState = bulkUpload.batchListFetchState;
104
- const pastBatches = batchList.filter((b) => b.batchId !== effectiveCurrentBatchId);
110
+ const pastBatches = completedBatchesInApiOrder.filter((b) => b.batchId !== unmatchedSectionBatchId);
105
111
  const pastUnmatchedFiles = pastBatches.flatMap((b) => {
106
112
  const details = bulkUpload.batchDetailsById[b.batchId];
107
113
  if (details == null) {
@@ -111,8 +117,11 @@ export function getExpenseAutomationMissingReceiptsView(state) {
111
117
  .filter((f) => f.status === 'un_matched' || f.status === 'no_match')
112
118
  .map((f) => resolveBatchFile(f, b.batchId, transactionState));
113
119
  });
114
- const completedTransactionsForPeriod = monthYearPeriodId != null
115
- ? bulkUpload.completedTransactionsByPeriod[monthYearPeriodId]
120
+ const completedTransactionsCacheKey = monthYearPeriodId != null
121
+ ? getCompletedTransactionsCacheKey(monthYearPeriodId, bulkUpload.sortKey, bulkUpload.sortOrder, bulkUpload.completedSubTab)
122
+ : undefined;
123
+ const completedTransactionsForPeriod = completedTransactionsCacheKey != null
124
+ ? bulkUpload.completedTransactionsByPeriod[completedTransactionsCacheKey]
116
125
  : undefined;
117
126
  const completedTransactionIds = completedTransactionsForPeriod?.transactionIds ?? [];
118
127
  const resolvedCompletedTransactions = getSupportedTransactionsByIds(transactionState, completedTransactionIds);
@@ -15,8 +15,12 @@ const fetchCompletedTransactionsEpic = (actions$, state$, zeniAPI) => actions$.p
15
15
  const selectedPeriod = selectedPeriodByTenantId[currentTenant.tenantId];
16
16
  const periodId = (0, timePeriod_1.toMonthYearPeriodId)(selectedPeriod);
17
17
  const isInitialLoad = action.payload.pageToken == null;
18
- const existingData = bulkUpload.completedTransactionsByPeriod[periodId];
19
- if (isInitialLoad && existingData != null && existingData.transactionIds.length > 0) {
18
+ const cacheKey = (0, missingReceiptsViewReducer_1.getCompletedTransactionsCacheKey)(periodId, bulkUpload.sortKey, bulkUpload.sortOrder, bulkUpload.completedSubTab);
19
+ const existingData = bulkUpload.completedTransactionsByPeriod[cacheKey];
20
+ if (isInitialLoad &&
21
+ action.payload.cacheOverride !== true &&
22
+ existingData != null &&
23
+ existingData.transactionIds.length > 0) {
20
24
  return (0, rxjs_1.from)([]);
21
25
  }
22
26
  const period = (0, timePeriod_1.convertToPeriod)(selectedPeriod);
@@ -6,6 +6,8 @@ import { TransactionPayload } from '../../../entity/transaction/payloadTypes/tra
6
6
  import { SupportedTransactionPayload } from '../../../entity/transaction/transactionState';
7
7
  import { ZeniAPIStatus } from '../../../responsePayload';
8
8
  import type { BatchDetails, BatchListItem, BatchStatus, BulkUploadResultsTab, BulkUploadSortKey, BulkUploadState, CompletedSubTab, ManualSearchResult, MissingReceiptsViewState, MissingReceiptsViewUIState } from '../types/missingReceiptsViewState';
9
+ import type { MonthYearPeriodId } from '../../../commonStateTypes/timePeriod';
10
+ export declare const getCompletedTransactionsCacheKey: (periodId: MonthYearPeriodId, sortKey: BulkUploadSortKey, sortOrder: SortOrder, subTab: CompletedSubTab) => string;
9
11
  export declare const initialBulkUploadState: BulkUploadState;
10
12
  export declare const initialState: MissingReceiptsViewState;
11
13
  export declare const fetchMissingReceipts: import("@reduxjs/toolkit").ActionCreatorWithPreparedPayload<[period: TimePeriod, minimumTransactionAmount: Amount, cacheOverride?: any, refreshViewInBackground?: any], {
@@ -67,8 +69,9 @@ export declare const fetchMissingReceipts: import("@reduxjs/toolkit").ActionCrea
67
69
  query: string;
68
70
  }, "expenseAutomationMissingReceiptsView/searchTransactionsForManualMatch", never, never>, searchTransactionsForManualMatchSuccess: import("@reduxjs/toolkit").ActionCreatorWithPayload<ManualSearchResult[], "expenseAutomationMissingReceiptsView/searchTransactionsForManualMatchSuccess">, searchTransactionsForManualMatchFailure: import("@reduxjs/toolkit").ActionCreatorWithPayload<{
69
71
  error: ZeniAPIStatus;
70
- }, "expenseAutomationMissingReceiptsView/searchTransactionsForManualMatchFailure">, clearManualSearchResults: import("@reduxjs/toolkit").ActionCreatorWithoutPayload<"expenseAutomationMissingReceiptsView/clearManualSearchResults">, fetchCompletedTransactions: import("@reduxjs/toolkit").ActionCreatorWithPreparedPayload<[pageToken?: string | undefined], {
72
+ }, "expenseAutomationMissingReceiptsView/searchTransactionsForManualMatchFailure">, clearManualSearchResults: import("@reduxjs/toolkit").ActionCreatorWithoutPayload<"expenseAutomationMissingReceiptsView/clearManualSearchResults">, fetchCompletedTransactions: import("@reduxjs/toolkit").ActionCreatorWithPreparedPayload<[pageToken?: string | undefined, cacheOverride?: boolean | undefined], {
71
73
  pageToken: string | undefined;
74
+ cacheOverride: boolean | undefined;
72
75
  }, "expenseAutomationMissingReceiptsView/fetchCompletedTransactions", never, never>, fetchCompletedTransactionsSuccess: import("@reduxjs/toolkit").ActionCreatorWithPayload<{
73
76
  isInitialLoad: boolean;
74
77
  nextPageToken: string | null;
@@ -1,9 +1,11 @@
1
1
  "use strict";
2
2
  var _a;
3
3
  Object.defineProperty(exports, "__esModule", { value: true });
4
- exports.fetchCompletedTransactionsFailure = exports.fetchCompletedTransactionsSuccess = exports.fetchCompletedTransactions = exports.clearManualSearchResults = exports.searchTransactionsForManualMatchFailure = exports.searchTransactionsForManualMatchSuccess = exports.searchTransactionsForManualMatch = exports.clearBulkUpload = exports.setBulkUploadSortConfig = exports.setBulkUploadCompletedSubTab = exports.setBulkUploadResultsTab = exports.confirmBulkUploadMatchFailure = exports.confirmBulkUploadMatchSuccess = exports.confirmBulkUploadMatch = exports.fetchBulkUploadBatchesFailure = exports.fetchBulkUploadBatchesSuccess = exports.fetchBulkUploadBatches = exports.fetchMoreBatchDetailsFailure = exports.fetchMoreBatchDetailsComplete = exports.fetchMoreBatchDetails = exports.setInitialBatchDetailsLoading = exports.batchDetailFetchFailed = exports.storeBatchDetails = exports.fetchBulkUploadBatchDetailsFailure = exports.fetchBulkUploadBatchDetailsSuccess = exports.fetchBulkUploadBatchDetails = exports.pusherBatchStatusUpdate = exports.bulkUploadReceiptsFailure = exports.bulkUploadReceiptsSuccess = exports.updateBulkUploadProgress = exports.bulkUploadReceipts = exports.clearExpenseAutomationMissingReceiptsView = exports.markMissingReceiptAsDone = exports.updateMissingReceiptsUIState = exports.updateMissingReceiptUploadState = exports.uploadMissingReceiptSuccess = exports.fetchMissingReceiptsFailure = exports.fetchMissingReceiptsSuccess = exports.fetchMissingReceipts = exports.initialState = exports.initialBulkUploadState = void 0;
4
+ exports.fetchCompletedTransactionsFailure = exports.fetchCompletedTransactionsSuccess = exports.fetchCompletedTransactions = exports.clearManualSearchResults = exports.searchTransactionsForManualMatchFailure = exports.searchTransactionsForManualMatchSuccess = exports.searchTransactionsForManualMatch = exports.clearBulkUpload = exports.setBulkUploadSortConfig = exports.setBulkUploadCompletedSubTab = exports.setBulkUploadResultsTab = exports.confirmBulkUploadMatchFailure = exports.confirmBulkUploadMatchSuccess = exports.confirmBulkUploadMatch = exports.fetchBulkUploadBatchesFailure = exports.fetchBulkUploadBatchesSuccess = exports.fetchBulkUploadBatches = exports.fetchMoreBatchDetailsFailure = exports.fetchMoreBatchDetailsComplete = exports.fetchMoreBatchDetails = exports.setInitialBatchDetailsLoading = exports.batchDetailFetchFailed = exports.storeBatchDetails = exports.fetchBulkUploadBatchDetailsFailure = exports.fetchBulkUploadBatchDetailsSuccess = exports.fetchBulkUploadBatchDetails = exports.pusherBatchStatusUpdate = exports.bulkUploadReceiptsFailure = exports.bulkUploadReceiptsSuccess = exports.updateBulkUploadProgress = exports.bulkUploadReceipts = exports.clearExpenseAutomationMissingReceiptsView = exports.markMissingReceiptAsDone = exports.updateMissingReceiptsUIState = exports.updateMissingReceiptUploadState = exports.uploadMissingReceiptSuccess = exports.fetchMissingReceiptsFailure = exports.fetchMissingReceiptsSuccess = exports.fetchMissingReceipts = exports.initialState = exports.initialBulkUploadState = exports.getCompletedTransactionsCacheKey = void 0;
5
5
  const toolkit_1 = require("@reduxjs/toolkit");
6
6
  const timePeriod_1 = require("../../../commonStateTypes/timePeriod");
7
+ const getCompletedTransactionsCacheKey = (periodId, sortKey, sortOrder, subTab) => `completed-${subTab}-${sortKey}-${sortOrder === 'ascending' ? 'asc' : 'desc'}-${periodId}`;
8
+ exports.getCompletedTransactionsCacheKey = getCompletedTransactionsCacheKey;
7
9
  exports.initialBulkUploadState = {
8
10
  batchDetailsById: {},
9
11
  batchDetailsPaginationState: { fetchState: 'Not-Started', error: undefined },
@@ -214,7 +216,6 @@ const expenseAutomationMissingReceiptsView = (0, toolkit_1.createSlice)({
214
216
  error: undefined,
215
217
  };
216
218
  },
217
- // eslint-disable-next-line @typescript-eslint/no-unused-vars
218
219
  fetchMoreBatchDetails(_draft) {
219
220
  _draft.bulkUpload.batchDetailsPaginationState = {
220
221
  fetchState: 'In-Progress',
@@ -306,7 +307,6 @@ const expenseAutomationMissingReceiptsView = (0, toolkit_1.createSlice)({
306
307
  },
307
308
  setBulkUploadCompletedSubTab(draft, action) {
308
309
  draft.bulkUpload.completedSubTab = action.payload;
309
- draft.bulkUpload.completedTransactionsByPeriod = {};
310
310
  },
311
311
  setBulkUploadSortConfig(draft, action) {
312
312
  draft.bulkUpload.sortKey = action.payload.sortKey;
@@ -361,15 +361,16 @@ const expenseAutomationMissingReceiptsView = (0, toolkit_1.createSlice)({
361
361
  }
362
362
  }
363
363
  },
364
- prepare(pageToken) {
365
- return { payload: { pageToken } };
364
+ prepare(pageToken, cacheOverride) {
365
+ return { payload: { pageToken, cacheOverride } };
366
366
  },
367
367
  },
368
368
  fetchCompletedTransactionsSuccess(draft, action) {
369
369
  const { transactionIds, nextPageToken, totalCount, selectedPeriod, isInitialLoad } = action.payload;
370
370
  const periodId = (0, timePeriod_1.toMonthYearPeriodId)(selectedPeriod);
371
+ const cacheKey = (0, exports.getCompletedTransactionsCacheKey)(periodId, draft.bulkUpload.sortKey, draft.bulkUpload.sortOrder, draft.bulkUpload.completedSubTab);
371
372
  if (isInitialLoad) {
372
- draft.bulkUpload.completedTransactionsByPeriod[periodId] = {
373
+ draft.bulkUpload.completedTransactionsByPeriod[cacheKey] = {
373
374
  transactionIds,
374
375
  nextPageToken,
375
376
  totalCount,
@@ -377,7 +378,7 @@ const expenseAutomationMissingReceiptsView = (0, toolkit_1.createSlice)({
377
378
  };
378
379
  }
379
380
  else {
380
- const existing = draft.bulkUpload.completedTransactionsByPeriod[periodId];
381
+ const existing = draft.bulkUpload.completedTransactionsByPeriod[cacheKey];
381
382
  if (existing != null) {
382
383
  existing.transactionIds.push(...transactionIds);
383
384
  existing.nextPageToken = nextPageToken;
@@ -385,7 +386,7 @@ const expenseAutomationMissingReceiptsView = (0, toolkit_1.createSlice)({
385
386
  existing.fetchState = { fetchState: 'Completed', error: undefined };
386
387
  }
387
388
  else {
388
- draft.bulkUpload.completedTransactionsByPeriod[periodId] = {
389
+ draft.bulkUpload.completedTransactionsByPeriod[cacheKey] = {
389
390
  transactionIds,
390
391
  nextPageToken,
391
392
  totalCount,
@@ -396,7 +397,8 @@ const expenseAutomationMissingReceiptsView = (0, toolkit_1.createSlice)({
396
397
  },
397
398
  fetchCompletedTransactionsFailure(draft, action) {
398
399
  const periodId = (0, timePeriod_1.toMonthYearPeriodId)(action.payload.selectedPeriod);
399
- const existing = draft.bulkUpload.completedTransactionsByPeriod[periodId];
400
+ const cacheKey = (0, exports.getCompletedTransactionsCacheKey)(periodId, draft.bulkUpload.sortKey, draft.bulkUpload.sortOrder, draft.bulkUpload.completedSubTab);
401
+ const existing = draft.bulkUpload.completedTransactionsByPeriod[cacheKey];
400
402
  if (existing != null) {
401
403
  existing.fetchState = {
402
404
  fetchState: 'Error',
@@ -404,7 +406,7 @@ const expenseAutomationMissingReceiptsView = (0, toolkit_1.createSlice)({
404
406
  };
405
407
  }
406
408
  else {
407
- draft.bulkUpload.completedTransactionsByPeriod[periodId] = {
409
+ draft.bulkUpload.completedTransactionsByPeriod[cacheKey] = {
408
410
  fetchState: { fetchState: 'Error', error: action.payload.error },
409
411
  nextPageToken: null,
410
412
  totalCount: 0,
@@ -9,6 +9,7 @@ const timePeriod_1 = require("../../../commonStateTypes/timePeriod");
9
9
  const tenantSelector_1 = require("../../../entity/tenant/tenantSelector");
10
10
  const transactionSelector_1 = require("../../../entity/transaction/transactionSelector");
11
11
  const expenseAutomationViewSelectorTypes_1 = require("../selectorTypes/expenseAutomationViewSelectorTypes");
12
+ const missingReceiptsViewReducer_1 = require("../reducers/missingReceiptsViewReducer");
12
13
  function getExpenseAutomationMissingReceiptsView(state) {
13
14
  const { expenseAutomationMissingReceiptsViewState, expenseAutomationViewState, transactionState, monthEndCloseChecksState, } = state;
14
15
  const currentTenant = (0, tenantSelector_1.getCurrentTenant)(state);
@@ -60,14 +61,19 @@ function getExpenseAutomationMissingReceiptsView(state) {
60
61
  const batchList = monthYearPeriodId != null
61
62
  ? bulkUpload.batchListByPeriod[monthYearPeriodId] ?? []
62
63
  : [];
63
- const completedBatchesSorted = (0, orderBy_1.default)(batchList.filter((b) => b.status === 'completed'), (b) => b.createdAt, 'desc');
64
- const effectiveCurrentBatchId = bulkUpload.currentBatchId ?? completedBatchesSorted[0]?.batchId;
65
- const currentBatchDetails = effectiveCurrentBatchId != null
66
- ? bulkUpload.batchDetailsById[effectiveCurrentBatchId]
64
+ /** Completed batches in the same order as the batches API (batchList). First = primary "Unmatched" batch. */
65
+ const completedBatchesInApiOrder = batchList.filter((b) => b.status === 'completed');
66
+ const firstCompletedBatchId = completedBatchesInApiOrder[0]?.batchId;
67
+ /** During upload/matching, the in-flight batch may not appear in batchList yet — prefer currentBatchId. */
68
+ const unmatchedSectionBatchId = bulkUpload.phase === 'matching' || bulkUpload.phase === 'uploading'
69
+ ? bulkUpload.currentBatchId ?? firstCompletedBatchId
70
+ : firstCompletedBatchId;
71
+ const currentBatchDetails = unmatchedSectionBatchId != null
72
+ ? bulkUpload.batchDetailsById[unmatchedSectionBatchId]
67
73
  : undefined;
68
74
  const resolvedFiles = currentBatchDetails?.files.map((file) => resolveBatchFile(file, currentBatchDetails.batchId, transactionState));
69
75
  const failedIds = new Set(bulkUpload.failedBatchDetailIds);
70
- const hasMoreBatchDetails = completedBatchesSorted.some((b) => bulkUpload.batchDetailsById[b.batchId] == null &&
76
+ const hasMoreBatchDetails = completedBatchesInApiOrder.some((b) => bulkUpload.batchDetailsById[b.batchId] == null &&
71
77
  !failedIds.has(b.batchId));
72
78
  const getSortValue = (file) => {
73
79
  const t = file.matchedTransaction;
@@ -107,7 +113,7 @@ function getExpenseAutomationMissingReceiptsView(state) {
107
113
  }
108
114
  : { total: 0, processed: 0, percentage: 0 };
109
115
  const batchListFetchState = bulkUpload.batchListFetchState;
110
- const pastBatches = batchList.filter((b) => b.batchId !== effectiveCurrentBatchId);
116
+ const pastBatches = completedBatchesInApiOrder.filter((b) => b.batchId !== unmatchedSectionBatchId);
111
117
  const pastUnmatchedFiles = pastBatches.flatMap((b) => {
112
118
  const details = bulkUpload.batchDetailsById[b.batchId];
113
119
  if (details == null) {
@@ -117,8 +123,11 @@ function getExpenseAutomationMissingReceiptsView(state) {
117
123
  .filter((f) => f.status === 'un_matched' || f.status === 'no_match')
118
124
  .map((f) => resolveBatchFile(f, b.batchId, transactionState));
119
125
  });
120
- const completedTransactionsForPeriod = monthYearPeriodId != null
121
- ? bulkUpload.completedTransactionsByPeriod[monthYearPeriodId]
126
+ const completedTransactionsCacheKey = monthYearPeriodId != null
127
+ ? (0, missingReceiptsViewReducer_1.getCompletedTransactionsCacheKey)(monthYearPeriodId, bulkUpload.sortKey, bulkUpload.sortOrder, bulkUpload.completedSubTab)
128
+ : undefined;
129
+ const completedTransactionsForPeriod = completedTransactionsCacheKey != null
130
+ ? bulkUpload.completedTransactionsByPeriod[completedTransactionsCacheKey]
122
131
  : undefined;
123
132
  const completedTransactionIds = completedTransactionsForPeriod?.transactionIds ?? [];
124
133
  const resolvedCompletedTransactions = (0, transactionSelector_1.getSupportedTransactionsByIds)(transactionState, completedTransactionIds);
@@ -106,7 +106,7 @@ export interface BulkUploadState {
106
106
  batchListFetchState: FetchStateAndError;
107
107
  batchStatusById: Record<ID, BatchStatus>;
108
108
  completedSubTab: CompletedSubTab;
109
- completedTransactionsByPeriod: Record<MonthYearPeriodId, CompletedTransactionsState>;
109
+ completedTransactionsByPeriod: Record<string, CompletedTransactionsState>;
110
110
  confirmMatchStatus: FetchStateAndError;
111
111
  currentResultsTab: BulkUploadResultsTab;
112
112
  failedBatchDetailIds: ID[];
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@zeniai/client-epic-state",
3
- "version": "4.19.37-betaVR13",
3
+ "version": "4.19.37-betaVR15",
4
4
  "description": "Shared module between Web & Mobile containing required abstractions for state management, async network communication. ",
5
5
  "main": "lib/index.js",
6
6
  "module": "lib/esm/index.js",