@zeniai/client-epic-state 5.0.71-betaVR3 → 5.0.72
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.
- package/lib/coreEpics.js +1 -1
- package/lib/entity/account/accountSelector.d.ts +1 -1
- package/lib/entity/account/accountState.d.ts +1 -1
- package/lib/entity/account/subAccountSelector.d.ts +1 -1
- package/lib/entity/aiAccountantCustomer/aiAccountantCustomerPayload.js +3 -1
- package/lib/entity/aiAccountantCustomer/aiAccountantCustomerReducer.js +2 -1
- package/lib/entity/aiAccountantCustomer/aiAccountantCustomerSelector.d.ts +1 -1
- package/lib/entity/chargeCard/chargeCardReducer.d.ts +2 -19
- package/lib/entity/chargeCard/chargeCardReducer.js +2 -35
- package/lib/entity/chargeCardTransaction/chargeCardTransactionReducer.d.ts +1 -14
- package/lib/entity/chargeCardTransaction/chargeCardTransactionReducer.js +2 -36
- package/lib/entity/sectionProjectView/sectionProjectViewReducer.d.ts +1 -1
- package/lib/entity/sectionProjectView/sectionProjectViewSelector.js +1 -1
- package/lib/entity/tenant/SessionManager.js +3 -6
- package/lib/entity/tenant/clearAllEpic.d.ts +2 -2
- package/lib/entity/tenant/clearAllEpic.js +2 -2
- package/lib/entity/tenant/epic/saveAPIKeyConnectionEpic.js +2 -6
- package/lib/entity/tenant/epic/saveOAuthConnectionEpic.js +2 -6
- package/lib/entity/tenant/tenantReducer.js +1 -6
- package/lib/entity/transaction/payloadTypes/transactionLinePayload.js +1 -3
- package/lib/epic.d.ts +10 -12
- package/lib/epic.js +11 -13
- package/lib/esm/coreEpics.js +1 -1
- package/lib/esm/entity/aiAccountantCustomer/aiAccountantCustomerPayload.js +3 -1
- package/lib/esm/entity/aiAccountantCustomer/aiAccountantCustomerReducer.js +2 -1
- package/lib/esm/entity/chargeCard/chargeCardReducer.js +1 -34
- package/lib/esm/entity/chargeCardTransaction/chargeCardTransactionReducer.js +1 -35
- package/lib/esm/entity/sectionProjectView/sectionProjectViewSelector.js +1 -1
- package/lib/esm/entity/tenant/SessionManager.js +1 -4
- package/lib/esm/entity/tenant/clearAllEpic.js +2 -2
- package/lib/esm/entity/tenant/epic/saveAPIKeyConnectionEpic.js +2 -6
- package/lib/esm/entity/tenant/epic/saveOAuthConnectionEpic.js +2 -6
- package/lib/esm/entity/tenant/tenantReducer.js +1 -6
- package/lib/esm/entity/transaction/payloadTypes/transactionLinePayload.js +1 -3
- package/lib/esm/epic.js +11 -13
- package/lib/esm/index.js +15 -19
- package/lib/esm/reducer.js +2 -2
- package/lib/esm/view/aiAccountantView/epics/fetchAiAccountantCustomersEpic.js +5 -2
- package/lib/esm/view/aiAccountantView/epics/fetchAiAccountantJobsEpic.js +5 -2
- package/lib/esm/view/aiAccountantView/epics/triggerAiAccountantJobEpic.js +1 -4
- package/lib/esm/view/companyTaskManagerView/companyTaskManagerViewSelector.js +1 -1
- package/lib/esm/view/companyTaskManagerView/epics/fetchTaskManagerMetricsEpic.js +1 -1
- package/lib/esm/view/expenseAutomationView/epics/missingReceipts/fetchBulkUploadBatchesEpic.js +2 -2
- package/lib/esm/view/expenseAutomationView/epics/missingReceipts/fetchCompletedTransactionsEpic.js +1 -2
- package/lib/esm/view/expenseAutomationView/epics/missingReceipts/fetchMultipleBatchDetailsEpic.js +5 -21
- package/lib/esm/view/expenseAutomationView/epics/missingReceipts/restoreBulkUploadAutomatchingOnMountEpic.js +6 -8
- package/lib/esm/view/expenseAutomationView/epics/missingReceipts/searchTransactionsForManualMatchEpic.js +1 -7
- package/lib/esm/view/expenseAutomationView/epics/missingReceipts/watchBulkUploadBatchStatusEpic.js +9 -13
- package/lib/esm/view/expenseAutomationView/epics/transactionCategorization/fetchTransactionCategorizationEpic.js +1 -11
- package/lib/esm/view/expenseAutomationView/reducers/missingReceiptsViewReducer.js +2 -81
- package/lib/esm/view/expenseAutomationView/reducers/transactionsViewReducer.js +1 -127
- package/lib/esm/view/expenseAutomationView/selectors/missingReceiptsSelector.js +0 -2
- package/lib/esm/view/expenseAutomationView/selectors/transactionCategorizationSelector.js +1 -20
- package/lib/esm/view/expenseAutomationView/types/missingReceiptsViewState.js +2 -0
- package/lib/esm/view/financeStatement/financeStatementSelector.js +1 -1
- package/lib/esm/view/spendManagement/chargeCards/cashbackDetail/cashbackDetailReducer.js +2 -3
- package/lib/esm/view/spendManagement/chargeCards/chargeCardConfig/chargeCardConfigReducer.js +2 -3
- package/lib/esm/view/spendManagement/chargeCards/chargeCardDetail/chargeCardDetailReducer.js +18 -55
- package/lib/esm/view/spendManagement/chargeCards/chargeCardDetail/fetchChargeCardDetailEpic.js +2 -16
- package/lib/esm/view/spendManagement/chargeCards/chargeCardDetail/fetchChargeCardDetailPageEpic.js +4 -5
- package/lib/esm/view/spendManagement/chargeCards/chargeCardList/chargeCardListReducer.js +9 -26
- package/lib/esm/view/spendManagement/chargeCards/chargeCardList/fetchChargeCardListPageEpic.js +6 -9
- package/lib/esm/view/spendManagement/chargeCards/chargeCardPaymentHistory/chargeCardPaymentHistoryReducer.js +2 -3
- package/lib/esm/view/spendManagement/chargeCards/chargeCardPaymentHistory/fetchChargeCardPaymentPageEpic.js +1 -1
- package/lib/esm/view/spendManagement/chargeCards/chargeCardRepaymentDetail/chargeCardRepaymentDetailReducer.js +3 -7
- package/lib/esm/view/taskManager/cannedResponsesView/epics/fetchCannedResponsesEpic.js +1 -1
- package/lib/esm/view/taskManager/cannedResponsesView/epics/saveCannedResponseEpic.js +1 -1
- package/lib/esm/view/taskManager/taskDetailView/epics/unsnoozeTaskEpic.js +1 -1
- package/lib/esm/view/transactionDetail/transactionDetailSelector.js +1 -7
- package/lib/index.d.ts +16 -20
- package/lib/index.js +58 -75
- package/lib/reducer.d.ts +2 -2
- package/lib/reducer.js +2 -2
- package/lib/tsconfig.typecheck.tsbuildinfo +1 -0
- package/lib/view/aiAccountantView/aiAccountantViewPayload.d.ts +2 -2
- package/lib/view/aiAccountantView/aiAccountantViewReducer.d.ts +1 -1
- package/lib/view/aiAccountantView/epics/fetchAiAccountantCustomersEpic.js +5 -2
- package/lib/view/aiAccountantView/epics/fetchAiAccountantJobsEpic.js +5 -2
- package/lib/view/aiAccountantView/epics/triggerAiAccountantJobEpic.js +1 -4
- package/lib/view/companyTaskManagerView/companyTaskManagerViewSelector.d.ts +1 -1
- package/lib/view/companyTaskManagerView/companyTaskManagerViewSelector.js +1 -1
- package/lib/view/expenseAutomationView/epics/missingReceipts/fetchBulkUploadBatchesEpic.js +2 -2
- package/lib/view/expenseAutomationView/epics/missingReceipts/fetchCompletedTransactionsEpic.js +1 -2
- package/lib/view/expenseAutomationView/epics/missingReceipts/fetchMultipleBatchDetailsEpic.js +5 -21
- package/lib/view/expenseAutomationView/epics/missingReceipts/restoreBulkUploadAutomatchingOnMountEpic.js +6 -8
- package/lib/view/expenseAutomationView/epics/missingReceipts/searchTransactionsForManualMatchEpic.js +1 -7
- package/lib/view/expenseAutomationView/epics/missingReceipts/watchBulkUploadBatchStatusEpic.d.ts +5 -11
- package/lib/view/expenseAutomationView/epics/missingReceipts/watchBulkUploadBatchStatusEpic.js +8 -12
- package/lib/view/expenseAutomationView/epics/transactionCategorization/fetchTransactionCategorizationEpic.d.ts +2 -2
- package/lib/view/expenseAutomationView/epics/transactionCategorization/fetchTransactionCategorizationEpic.js +0 -10
- package/lib/view/expenseAutomationView/helpers/transactionCategorizationLocalDataHelper.d.ts +1 -1
- package/lib/view/expenseAutomationView/payload/transactionCategorizationPayload.d.ts +0 -21
- package/lib/view/expenseAutomationView/reducers/missingReceiptsViewReducer.d.ts +2 -15
- package/lib/view/expenseAutomationView/reducers/missingReceiptsViewReducer.js +3 -83
- package/lib/view/expenseAutomationView/reducers/transactionsViewReducer.d.ts +3 -9
- package/lib/view/expenseAutomationView/reducers/transactionsViewReducer.js +2 -128
- package/lib/view/expenseAutomationView/selectorTypes/missingReceiptsSelectorTypes.d.ts +1 -14
- package/lib/view/expenseAutomationView/selectorTypes/transactionsViewSelectorTypes.d.ts +0 -14
- package/lib/view/expenseAutomationView/selectors/missingReceiptsSelector.js +0 -2
- package/lib/view/expenseAutomationView/selectors/transactionCategorizationSelector.js +1 -20
- package/lib/view/expenseAutomationView/types/missingReceiptsViewState.d.ts +2 -20
- package/lib/view/expenseAutomationView/types/missingReceiptsViewState.js +4 -1
- package/lib/view/expenseAutomationView/types/transactionsViewState.d.ts +2 -41
- package/lib/view/financeStatement/financeStatementSelector.js +1 -1
- package/lib/view/profitAndLossProjectView/profitAndLossProjectViewSelectorTypes.d.ts +1 -1
- package/lib/view/spendManagement/chargeCards/cashbackDetail/cashbackDetailReducer.d.ts +1 -3
- package/lib/view/spendManagement/chargeCards/cashbackDetail/cashbackDetailReducer.js +2 -3
- package/lib/view/spendManagement/chargeCards/chargeCardConfig/chargeCardConfigReducer.d.ts +1 -3
- package/lib/view/spendManagement/chargeCards/chargeCardConfig/chargeCardConfigReducer.js +2 -3
- package/lib/view/spendManagement/chargeCards/chargeCardDetail/chargeCardDetailReducer.js +18 -55
- package/lib/view/spendManagement/chargeCards/chargeCardDetail/fetchChargeCardDetailEpic.js +2 -16
- package/lib/view/spendManagement/chargeCards/chargeCardDetail/fetchChargeCardDetailPageEpic.js +4 -5
- package/lib/view/spendManagement/chargeCards/chargeCardList/chargeCardListReducer.d.ts +3 -18
- package/lib/view/spendManagement/chargeCards/chargeCardList/chargeCardListReducer.js +10 -27
- package/lib/view/spendManagement/chargeCards/chargeCardList/fetchChargeCardListPageEpic.js +6 -9
- package/lib/view/spendManagement/chargeCards/chargeCardPaymentHistory/chargeCardPaymentHistoryReducer.d.ts +1 -3
- package/lib/view/spendManagement/chargeCards/chargeCardPaymentHistory/chargeCardPaymentHistoryReducer.js +2 -3
- package/lib/view/spendManagement/chargeCards/chargeCardPaymentHistory/fetchChargeCardPaymentPageEpic.js +1 -1
- package/lib/view/spendManagement/chargeCards/chargeCardRepaymentDetail/chargeCardRepaymentDetailReducer.d.ts +1 -3
- package/lib/view/spendManagement/chargeCards/chargeCardRepaymentDetail/chargeCardRepaymentDetailReducer.js +3 -7
- package/lib/view/transactionDetail/transactionDetailSelector.js +1 -7
- package/lib/view/zeniOAuthView/zeniOAuthSelector.d.ts +1 -1
- package/package.json +4 -9
- package/lib/commonStateTypes/cacheOverrideFetchReducer.d.ts +0 -17
- package/lib/commonStateTypes/cacheOverrideFetchReducer.js +0 -20
- package/lib/commonStateTypes/pusherActions.d.ts +0 -11
- package/lib/commonStateTypes/pusherActions.js +0 -6
- package/lib/esm/commonStateTypes/cacheOverrideFetchReducer.js +0 -16
- package/lib/esm/commonStateTypes/pusherActions.js +0 -3
- package/lib/esm/view/expenseAutomationView/epics/missingReceipts/refreshBatchDetailsForBatchIdEpic.js +0 -52
- package/lib/esm/view/expenseAutomationView/epics/missingReceipts/syncTabsAfterAutomatchEpic.js +0 -53
- package/lib/esm/view/expenseAutomationView/types/completedSubTab.js +0 -17
- package/lib/view/expenseAutomationView/epics/missingReceipts/refreshBatchDetailsForBatchIdEpic.d.ts +0 -18
- package/lib/view/expenseAutomationView/epics/missingReceipts/refreshBatchDetailsForBatchIdEpic.js +0 -56
- package/lib/view/expenseAutomationView/epics/missingReceipts/syncTabsAfterAutomatchEpic.d.ts +0 -28
- package/lib/view/expenseAutomationView/epics/missingReceipts/syncTabsAfterAutomatchEpic.js +0 -57
- package/lib/view/expenseAutomationView/types/completedSubTab.d.ts +0 -10
- package/lib/view/expenseAutomationView/types/completedSubTab.js +0 -21
|
@@ -1,52 +0,0 @@
|
|
|
1
|
-
import { EMPTY, concat, from, of } from 'rxjs';
|
|
2
|
-
import { catchError, filter, mergeMap } from 'rxjs/operators';
|
|
3
|
-
import { updateTransactions } from '../../../../entity/transaction/transactionReducer';
|
|
4
|
-
import { createZeniAPIStatus, isSuccessResponse, } from '../../../../responsePayload';
|
|
5
|
-
import { extractTransactionPayloadsFromBatchFiles, isBatchDetailsApiStatusCompleted, toBatchDetails, } from '../../payload/missingReceiptsPayload';
|
|
6
|
-
import { batchDetailFetchFailed, markBatchDetailRefreshAttempted, refreshBatchDetailsForBatchId, storeBatchDetails, } from '../../reducers/missingReceiptsViewReducer';
|
|
7
|
-
/**
|
|
8
|
-
* Pusher resends the same `completed` event in some cases (reconnect, server retry). Skip a
|
|
9
|
-
* targeted refresh if we issued one for the same batch within this window — the cached details
|
|
10
|
-
* are already fresh, so another `GET /1.0/batches/:id` is wasteful and visually flickers nothing.
|
|
11
|
-
*/
|
|
12
|
-
const TARGETED_REFRESH_DEDUPE_MS = 5000;
|
|
13
|
-
/**
|
|
14
|
-
* Single-batch stale-while-revalidate refresh. Triggered by `pusherBatchStatusCompletionEpic`
|
|
15
|
-
* (and any other path that wants to update one batch without wiping the cache). The response is
|
|
16
|
-
* stored via `storeBatchDetails`, which replaces the entry by `batchId` so the row updates in
|
|
17
|
-
* place — no skeleton, no list reflow.
|
|
18
|
-
*
|
|
19
|
-
* Throttle: `lastBatchDetailRefreshAtById[batchId]` is checked against `TARGETED_REFRESH_DEDUPE_MS`
|
|
20
|
-
* before issuing the call. The marker is emitted first so concurrent dispatches (e.g. Pusher
|
|
21
|
-
* resend during an in-flight request) see the dedupe timestamp and collapse to a single call.
|
|
22
|
-
*/
|
|
23
|
-
export const refreshBatchDetailsForBatchIdEpic = (actions$, state$, zeniAPI) => actions$.pipe(filter(refreshBatchDetailsForBatchId.match), mergeMap((action) => {
|
|
24
|
-
const { batchId } = action.payload;
|
|
25
|
-
const now = Date.now();
|
|
26
|
-
const lastAttempt = state$.value.expenseAutomationMissingReceiptsViewState.bulkUpload
|
|
27
|
-
.lastBatchDetailRefreshAtById[batchId];
|
|
28
|
-
if (lastAttempt != null &&
|
|
29
|
-
now - lastAttempt < TARGETED_REFRESH_DEDUPE_MS) {
|
|
30
|
-
return EMPTY;
|
|
31
|
-
}
|
|
32
|
-
const apiCall = zeniAPI
|
|
33
|
-
.getJSON(`${zeniAPI.apiEndPoints.communicationAgentMicroServiceBaseUrl}/1.0/batches/${batchId}`)
|
|
34
|
-
.pipe(mergeMap((response) => {
|
|
35
|
-
if (!isSuccessResponse(response) ||
|
|
36
|
-
response.data == null ||
|
|
37
|
-
!isBatchDetailsApiStatusCompleted(response.data.status)) {
|
|
38
|
-
return EMPTY;
|
|
39
|
-
}
|
|
40
|
-
const actions = [];
|
|
41
|
-
const transactionPayloads = extractTransactionPayloadsFromBatchFiles(response.data.files);
|
|
42
|
-
if (transactionPayloads.length > 0) {
|
|
43
|
-
actions.push(updateTransactions(transactionPayloads, (value) => value.transaction_id));
|
|
44
|
-
}
|
|
45
|
-
actions.push(storeBatchDetails(toBatchDetails(response.data, zeniAPI.apiEndPoints.fileMicroServiceBaseUrl)));
|
|
46
|
-
return from(actions);
|
|
47
|
-
}), catchError((error) => {
|
|
48
|
-
console.error(`Failed to refresh batch details for ${batchId}:`, createZeniAPIStatus('Unexpected Error', 'Refresh batch details errored out: ' + JSON.stringify(error)));
|
|
49
|
-
return of(batchDetailFetchFailed({ batchId }));
|
|
50
|
-
}));
|
|
51
|
-
return concat(of(markBatchDetailRefreshAttempted({ batchId, timestamp: now })), apiCall);
|
|
52
|
-
}));
|
package/lib/esm/view/expenseAutomationView/epics/missingReceipts/syncTabsAfterAutomatchEpic.js
DELETED
|
@@ -1,53 +0,0 @@
|
|
|
1
|
-
import { EMPTY, from, merge } from 'rxjs';
|
|
2
|
-
import { filter, switchMap, take, takeUntil } from 'rxjs/operators';
|
|
3
|
-
import { convertToPeriod, toAbsoluteDay, } from '../../../../commonStateTypes/timePeriod';
|
|
4
|
-
import { getCurrentTenant } from '../../../../entity/tenant/tenantSelector';
|
|
5
|
-
import { bulkUploadReceiptsSuccess, clearBulkUpload, fetchBulkUploadBatchDetailsSuccess, fetchCompletedTransactions, fetchMissingReceipts, restoreBulkUploadMatchingState, storeBatchDetails, } from '../../reducers/missingReceiptsViewReducer';
|
|
6
|
-
/**
|
|
7
|
-
* After automatch completes for the active bulk-upload batch, refresh the two
|
|
8
|
-
* caches that are not invalidated by the existing batch-details refresh path:
|
|
9
|
-
* - Missing Receipts list (`transactionIdsBySelectedPeriod`)
|
|
10
|
-
* - Completed transactions cache (`bulkUpload.completedTransactionsByPeriod`)
|
|
11
|
-
*
|
|
12
|
-
* The Unmatched tab is already kept fresh via `pusherBatchStatusCompletionEpic`
|
|
13
|
-
* dispatching `fetchBulkUploadBatches({invalidateBatchDetailsCache: true})`,
|
|
14
|
-
* which feeds `fetchMultipleBatchDetailsEpic` and re-stores batch details.
|
|
15
|
-
*
|
|
16
|
-
* Lifecycle mirrors `bulkUploadMatchResultToastEpic`: trigger on
|
|
17
|
-
* `bulkUploadReceiptsSuccess` (fresh upload) or `restoreBulkUploadMatchingState`
|
|
18
|
-
* (restored session), then wait for the first batch-details action for that
|
|
19
|
-
* batchId — landing as either `fetchBulkUploadBatchDetailsSuccess` or
|
|
20
|
-
* `storeBatchDetails`. `clearBulkUpload` cancels the in-flight wait.
|
|
21
|
-
*
|
|
22
|
-
* Refetches use `cacheOverride: true` to bypass per-tab cache guards, and
|
|
23
|
-
* `fetchMissingReceipts` uses `refreshViewInBackground: true` to keep the
|
|
24
|
-
* existing rows visible while fresh data is in flight (the authoritative
|
|
25
|
-
* server filter `is_attachment_missing_only=true` removes matched rows once
|
|
26
|
-
* the response lands).
|
|
27
|
-
*/
|
|
28
|
-
export const syncTabsAfterAutomatchEpic = (actions$, state$) => actions$.pipe(filter((action) => bulkUploadReceiptsSuccess.match(action) ||
|
|
29
|
-
restoreBulkUploadMatchingState.match(action)), switchMap((uploadAction) => {
|
|
30
|
-
const { batchId } = uploadAction.payload;
|
|
31
|
-
return merge(actions$.pipe(filter(fetchBulkUploadBatchDetailsSuccess.match)), actions$.pipe(filter(storeBatchDetails.match))).pipe(filter((a) => a.payload.batchId === batchId), take(1), switchMap((action) => {
|
|
32
|
-
const { summary } = action.payload;
|
|
33
|
-
if (summary.matched <= 0) {
|
|
34
|
-
return EMPTY;
|
|
35
|
-
}
|
|
36
|
-
const state = state$.value;
|
|
37
|
-
const currentTenant = getCurrentTenant(state);
|
|
38
|
-
const selectedPeriod = state.expenseAutomationViewState.selectedPeriodByTenantId[currentTenant.tenantId];
|
|
39
|
-
if (selectedPeriod == null) {
|
|
40
|
-
return from([fetchCompletedTransactions(undefined, true)]);
|
|
41
|
-
}
|
|
42
|
-
const period = convertToPeriod(selectedPeriod);
|
|
43
|
-
const timePeriodStart = toAbsoluteDay(period.start);
|
|
44
|
-
const timePeriodEnd = toAbsoluteDay(period.end);
|
|
45
|
-
if (timePeriodStart == null || timePeriodEnd == null) {
|
|
46
|
-
return from([fetchCompletedTransactions(undefined, true)]);
|
|
47
|
-
}
|
|
48
|
-
return from([
|
|
49
|
-
fetchMissingReceipts({ start: timePeriodStart, end: timePeriodEnd }, { amount: 75.0, currencyCode: 'USD', currencySymbol: '$' }, true, true),
|
|
50
|
-
fetchCompletedTransactions(undefined, true),
|
|
51
|
-
]);
|
|
52
|
-
}), takeUntil(actions$.pipe(filter(clearBulkUpload.match))));
|
|
53
|
-
}));
|
|
@@ -1,17 +0,0 @@
|
|
|
1
|
-
import { stringToUnion } from '../../../commonStateTypes/stringToUnion';
|
|
2
|
-
/**
|
|
3
|
-
* Sub-tabs that can appear under any "Completed" tab in the Expense Automation
|
|
4
|
-
* surface (Transaction Categorization Completed and Missing Receipts Completed
|
|
5
|
-
* both use this exact union). Forwarded verbatim to listing APIs as `sub_tab`
|
|
6
|
-
* / `match_type`. `'all'` preserves parent-tab semantics on the backend.
|
|
7
|
-
*/
|
|
8
|
-
const COMPLETED_SUB_TABS = ['all', 'ai_accountant', 'manual'];
|
|
9
|
-
export const toCompletedSubTab = (v) => stringToUnion(v.trim().toLowerCase(), COMPLETED_SUB_TABS);
|
|
10
|
-
/**
|
|
11
|
-
* "No sub-tab filter" sentinel — single source of truth for the default
|
|
12
|
-
* value of {@link CompletedSubTab}. Use this constant in initial slice
|
|
13
|
-
* state and at any call site that needs to fall back to the parent-tab
|
|
14
|
-
* listing semantics (review tab requests, manual-search overrides, etc.)
|
|
15
|
-
* so a future rename of the union doesn't require chasing literals.
|
|
16
|
-
*/
|
|
17
|
-
export const DEFAULT_COMPLETED_SUB_TAB = 'all';
|
package/lib/view/expenseAutomationView/epics/missingReceipts/refreshBatchDetailsForBatchIdEpic.d.ts
DELETED
|
@@ -1,18 +0,0 @@
|
|
|
1
|
-
import { ActionsObservable, StateObservable } from 'redux-observable';
|
|
2
|
-
import { Observable } from 'rxjs';
|
|
3
|
-
import { updateTransactions } from '../../../../entity/transaction/transactionReducer';
|
|
4
|
-
import { RootState } from '../../../../reducer';
|
|
5
|
-
import { ZeniAPI } from '../../../../zeniAPI';
|
|
6
|
-
import { batchDetailFetchFailed, markBatchDetailRefreshAttempted, refreshBatchDetailsForBatchId, storeBatchDetails } from '../../reducers/missingReceiptsViewReducer';
|
|
7
|
-
export type ActionType = ReturnType<typeof refreshBatchDetailsForBatchId> | ReturnType<typeof markBatchDetailRefreshAttempted> | ReturnType<typeof updateTransactions> | ReturnType<typeof storeBatchDetails> | ReturnType<typeof batchDetailFetchFailed>;
|
|
8
|
-
/**
|
|
9
|
-
* Single-batch stale-while-revalidate refresh. Triggered by `pusherBatchStatusCompletionEpic`
|
|
10
|
-
* (and any other path that wants to update one batch without wiping the cache). The response is
|
|
11
|
-
* stored via `storeBatchDetails`, which replaces the entry by `batchId` so the row updates in
|
|
12
|
-
* place — no skeleton, no list reflow.
|
|
13
|
-
*
|
|
14
|
-
* Throttle: `lastBatchDetailRefreshAtById[batchId]` is checked against `TARGETED_REFRESH_DEDUPE_MS`
|
|
15
|
-
* before issuing the call. The marker is emitted first so concurrent dispatches (e.g. Pusher
|
|
16
|
-
* resend during an in-flight request) see the dedupe timestamp and collapse to a single call.
|
|
17
|
-
*/
|
|
18
|
-
export declare const refreshBatchDetailsForBatchIdEpic: (actions$: ActionsObservable<ActionType>, state$: StateObservable<RootState>, zeniAPI: ZeniAPI) => Observable<ActionType>;
|
package/lib/view/expenseAutomationView/epics/missingReceipts/refreshBatchDetailsForBatchIdEpic.js
DELETED
|
@@ -1,56 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.refreshBatchDetailsForBatchIdEpic = void 0;
|
|
4
|
-
const rxjs_1 = require("rxjs");
|
|
5
|
-
const operators_1 = require("rxjs/operators");
|
|
6
|
-
const transactionReducer_1 = require("../../../../entity/transaction/transactionReducer");
|
|
7
|
-
const responsePayload_1 = require("../../../../responsePayload");
|
|
8
|
-
const missingReceiptsPayload_1 = require("../../payload/missingReceiptsPayload");
|
|
9
|
-
const missingReceiptsViewReducer_1 = require("../../reducers/missingReceiptsViewReducer");
|
|
10
|
-
/**
|
|
11
|
-
* Pusher resends the same `completed` event in some cases (reconnect, server retry). Skip a
|
|
12
|
-
* targeted refresh if we issued one for the same batch within this window — the cached details
|
|
13
|
-
* are already fresh, so another `GET /1.0/batches/:id` is wasteful and visually flickers nothing.
|
|
14
|
-
*/
|
|
15
|
-
const TARGETED_REFRESH_DEDUPE_MS = 5000;
|
|
16
|
-
/**
|
|
17
|
-
* Single-batch stale-while-revalidate refresh. Triggered by `pusherBatchStatusCompletionEpic`
|
|
18
|
-
* (and any other path that wants to update one batch without wiping the cache). The response is
|
|
19
|
-
* stored via `storeBatchDetails`, which replaces the entry by `batchId` so the row updates in
|
|
20
|
-
* place — no skeleton, no list reflow.
|
|
21
|
-
*
|
|
22
|
-
* Throttle: `lastBatchDetailRefreshAtById[batchId]` is checked against `TARGETED_REFRESH_DEDUPE_MS`
|
|
23
|
-
* before issuing the call. The marker is emitted first so concurrent dispatches (e.g. Pusher
|
|
24
|
-
* resend during an in-flight request) see the dedupe timestamp and collapse to a single call.
|
|
25
|
-
*/
|
|
26
|
-
const refreshBatchDetailsForBatchIdEpic = (actions$, state$, zeniAPI) => actions$.pipe((0, operators_1.filter)(missingReceiptsViewReducer_1.refreshBatchDetailsForBatchId.match), (0, operators_1.mergeMap)((action) => {
|
|
27
|
-
const { batchId } = action.payload;
|
|
28
|
-
const now = Date.now();
|
|
29
|
-
const lastAttempt = state$.value.expenseAutomationMissingReceiptsViewState.bulkUpload
|
|
30
|
-
.lastBatchDetailRefreshAtById[batchId];
|
|
31
|
-
if (lastAttempt != null &&
|
|
32
|
-
now - lastAttempt < TARGETED_REFRESH_DEDUPE_MS) {
|
|
33
|
-
return rxjs_1.EMPTY;
|
|
34
|
-
}
|
|
35
|
-
const apiCall = zeniAPI
|
|
36
|
-
.getJSON(`${zeniAPI.apiEndPoints.communicationAgentMicroServiceBaseUrl}/1.0/batches/${batchId}`)
|
|
37
|
-
.pipe((0, operators_1.mergeMap)((response) => {
|
|
38
|
-
if (!(0, responsePayload_1.isSuccessResponse)(response) ||
|
|
39
|
-
response.data == null ||
|
|
40
|
-
!(0, missingReceiptsPayload_1.isBatchDetailsApiStatusCompleted)(response.data.status)) {
|
|
41
|
-
return rxjs_1.EMPTY;
|
|
42
|
-
}
|
|
43
|
-
const actions = [];
|
|
44
|
-
const transactionPayloads = (0, missingReceiptsPayload_1.extractTransactionPayloadsFromBatchFiles)(response.data.files);
|
|
45
|
-
if (transactionPayloads.length > 0) {
|
|
46
|
-
actions.push((0, transactionReducer_1.updateTransactions)(transactionPayloads, (value) => value.transaction_id));
|
|
47
|
-
}
|
|
48
|
-
actions.push((0, missingReceiptsViewReducer_1.storeBatchDetails)((0, missingReceiptsPayload_1.toBatchDetails)(response.data, zeniAPI.apiEndPoints.fileMicroServiceBaseUrl)));
|
|
49
|
-
return (0, rxjs_1.from)(actions);
|
|
50
|
-
}), (0, operators_1.catchError)((error) => {
|
|
51
|
-
console.error(`Failed to refresh batch details for ${batchId}:`, (0, responsePayload_1.createZeniAPIStatus)('Unexpected Error', 'Refresh batch details errored out: ' + JSON.stringify(error)));
|
|
52
|
-
return (0, rxjs_1.of)((0, missingReceiptsViewReducer_1.batchDetailFetchFailed)({ batchId }));
|
|
53
|
-
}));
|
|
54
|
-
return (0, rxjs_1.concat)((0, rxjs_1.of)((0, missingReceiptsViewReducer_1.markBatchDetailRefreshAttempted)({ batchId, timestamp: now })), apiCall);
|
|
55
|
-
}));
|
|
56
|
-
exports.refreshBatchDetailsForBatchIdEpic = refreshBatchDetailsForBatchIdEpic;
|
package/lib/view/expenseAutomationView/epics/missingReceipts/syncTabsAfterAutomatchEpic.d.ts
DELETED
|
@@ -1,28 +0,0 @@
|
|
|
1
|
-
import { ActionsObservable, StateObservable } from 'redux-observable';
|
|
2
|
-
import { Observable } from 'rxjs';
|
|
3
|
-
import { RootState } from '../../../../reducer';
|
|
4
|
-
import { bulkUploadReceiptsSuccess, clearBulkUpload, fetchBulkUploadBatchDetailsSuccess, fetchCompletedTransactions, fetchMissingReceipts, restoreBulkUploadMatchingState, storeBatchDetails } from '../../reducers/missingReceiptsViewReducer';
|
|
5
|
-
export type ActionType = ReturnType<typeof bulkUploadReceiptsSuccess> | ReturnType<typeof restoreBulkUploadMatchingState> | ReturnType<typeof fetchBulkUploadBatchDetailsSuccess> | ReturnType<typeof storeBatchDetails> | ReturnType<typeof clearBulkUpload> | ReturnType<typeof fetchMissingReceipts> | ReturnType<typeof fetchCompletedTransactions>;
|
|
6
|
-
/**
|
|
7
|
-
* After automatch completes for the active bulk-upload batch, refresh the two
|
|
8
|
-
* caches that are not invalidated by the existing batch-details refresh path:
|
|
9
|
-
* - Missing Receipts list (`transactionIdsBySelectedPeriod`)
|
|
10
|
-
* - Completed transactions cache (`bulkUpload.completedTransactionsByPeriod`)
|
|
11
|
-
*
|
|
12
|
-
* The Unmatched tab is already kept fresh via `pusherBatchStatusCompletionEpic`
|
|
13
|
-
* dispatching `fetchBulkUploadBatches({invalidateBatchDetailsCache: true})`,
|
|
14
|
-
* which feeds `fetchMultipleBatchDetailsEpic` and re-stores batch details.
|
|
15
|
-
*
|
|
16
|
-
* Lifecycle mirrors `bulkUploadMatchResultToastEpic`: trigger on
|
|
17
|
-
* `bulkUploadReceiptsSuccess` (fresh upload) or `restoreBulkUploadMatchingState`
|
|
18
|
-
* (restored session), then wait for the first batch-details action for that
|
|
19
|
-
* batchId — landing as either `fetchBulkUploadBatchDetailsSuccess` or
|
|
20
|
-
* `storeBatchDetails`. `clearBulkUpload` cancels the in-flight wait.
|
|
21
|
-
*
|
|
22
|
-
* Refetches use `cacheOverride: true` to bypass per-tab cache guards, and
|
|
23
|
-
* `fetchMissingReceipts` uses `refreshViewInBackground: true` to keep the
|
|
24
|
-
* existing rows visible while fresh data is in flight (the authoritative
|
|
25
|
-
* server filter `is_attachment_missing_only=true` removes matched rows once
|
|
26
|
-
* the response lands).
|
|
27
|
-
*/
|
|
28
|
-
export declare const syncTabsAfterAutomatchEpic: (actions$: ActionsObservable<ActionType>, state$: StateObservable<RootState>) => Observable<ActionType>;
|
|
@@ -1,57 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.syncTabsAfterAutomatchEpic = void 0;
|
|
4
|
-
const rxjs_1 = require("rxjs");
|
|
5
|
-
const operators_1 = require("rxjs/operators");
|
|
6
|
-
const timePeriod_1 = require("../../../../commonStateTypes/timePeriod");
|
|
7
|
-
const tenantSelector_1 = require("../../../../entity/tenant/tenantSelector");
|
|
8
|
-
const missingReceiptsViewReducer_1 = require("../../reducers/missingReceiptsViewReducer");
|
|
9
|
-
/**
|
|
10
|
-
* After automatch completes for the active bulk-upload batch, refresh the two
|
|
11
|
-
* caches that are not invalidated by the existing batch-details refresh path:
|
|
12
|
-
* - Missing Receipts list (`transactionIdsBySelectedPeriod`)
|
|
13
|
-
* - Completed transactions cache (`bulkUpload.completedTransactionsByPeriod`)
|
|
14
|
-
*
|
|
15
|
-
* The Unmatched tab is already kept fresh via `pusherBatchStatusCompletionEpic`
|
|
16
|
-
* dispatching `fetchBulkUploadBatches({invalidateBatchDetailsCache: true})`,
|
|
17
|
-
* which feeds `fetchMultipleBatchDetailsEpic` and re-stores batch details.
|
|
18
|
-
*
|
|
19
|
-
* Lifecycle mirrors `bulkUploadMatchResultToastEpic`: trigger on
|
|
20
|
-
* `bulkUploadReceiptsSuccess` (fresh upload) or `restoreBulkUploadMatchingState`
|
|
21
|
-
* (restored session), then wait for the first batch-details action for that
|
|
22
|
-
* batchId — landing as either `fetchBulkUploadBatchDetailsSuccess` or
|
|
23
|
-
* `storeBatchDetails`. `clearBulkUpload` cancels the in-flight wait.
|
|
24
|
-
*
|
|
25
|
-
* Refetches use `cacheOverride: true` to bypass per-tab cache guards, and
|
|
26
|
-
* `fetchMissingReceipts` uses `refreshViewInBackground: true` to keep the
|
|
27
|
-
* existing rows visible while fresh data is in flight (the authoritative
|
|
28
|
-
* server filter `is_attachment_missing_only=true` removes matched rows once
|
|
29
|
-
* the response lands).
|
|
30
|
-
*/
|
|
31
|
-
const syncTabsAfterAutomatchEpic = (actions$, state$) => actions$.pipe((0, operators_1.filter)((action) => missingReceiptsViewReducer_1.bulkUploadReceiptsSuccess.match(action) ||
|
|
32
|
-
missingReceiptsViewReducer_1.restoreBulkUploadMatchingState.match(action)), (0, operators_1.switchMap)((uploadAction) => {
|
|
33
|
-
const { batchId } = uploadAction.payload;
|
|
34
|
-
return (0, rxjs_1.merge)(actions$.pipe((0, operators_1.filter)(missingReceiptsViewReducer_1.fetchBulkUploadBatchDetailsSuccess.match)), actions$.pipe((0, operators_1.filter)(missingReceiptsViewReducer_1.storeBatchDetails.match))).pipe((0, operators_1.filter)((a) => a.payload.batchId === batchId), (0, operators_1.take)(1), (0, operators_1.switchMap)((action) => {
|
|
35
|
-
const { summary } = action.payload;
|
|
36
|
-
if (summary.matched <= 0) {
|
|
37
|
-
return rxjs_1.EMPTY;
|
|
38
|
-
}
|
|
39
|
-
const state = state$.value;
|
|
40
|
-
const currentTenant = (0, tenantSelector_1.getCurrentTenant)(state);
|
|
41
|
-
const selectedPeriod = state.expenseAutomationViewState.selectedPeriodByTenantId[currentTenant.tenantId];
|
|
42
|
-
if (selectedPeriod == null) {
|
|
43
|
-
return (0, rxjs_1.from)([(0, missingReceiptsViewReducer_1.fetchCompletedTransactions)(undefined, true)]);
|
|
44
|
-
}
|
|
45
|
-
const period = (0, timePeriod_1.convertToPeriod)(selectedPeriod);
|
|
46
|
-
const timePeriodStart = (0, timePeriod_1.toAbsoluteDay)(period.start);
|
|
47
|
-
const timePeriodEnd = (0, timePeriod_1.toAbsoluteDay)(period.end);
|
|
48
|
-
if (timePeriodStart == null || timePeriodEnd == null) {
|
|
49
|
-
return (0, rxjs_1.from)([(0, missingReceiptsViewReducer_1.fetchCompletedTransactions)(undefined, true)]);
|
|
50
|
-
}
|
|
51
|
-
return (0, rxjs_1.from)([
|
|
52
|
-
(0, missingReceiptsViewReducer_1.fetchMissingReceipts)({ start: timePeriodStart, end: timePeriodEnd }, { amount: 75.0, currencyCode: 'USD', currencySymbol: '$' }, true, true),
|
|
53
|
-
(0, missingReceiptsViewReducer_1.fetchCompletedTransactions)(undefined, true),
|
|
54
|
-
]);
|
|
55
|
-
}), (0, operators_1.takeUntil)(actions$.pipe((0, operators_1.filter)(missingReceiptsViewReducer_1.clearBulkUpload.match))));
|
|
56
|
-
}));
|
|
57
|
-
exports.syncTabsAfterAutomatchEpic = syncTabsAfterAutomatchEpic;
|
|
@@ -1,10 +0,0 @@
|
|
|
1
|
-
export declare const toCompletedSubTab: (v: string) => "all" | "manual" | "ai_accountant";
|
|
2
|
-
export type CompletedSubTab = ReturnType<typeof toCompletedSubTab>;
|
|
3
|
-
/**
|
|
4
|
-
* "No sub-tab filter" sentinel — single source of truth for the default
|
|
5
|
-
* value of {@link CompletedSubTab}. Use this constant in initial slice
|
|
6
|
-
* state and at any call site that needs to fall back to the parent-tab
|
|
7
|
-
* listing semantics (review tab requests, manual-search overrides, etc.)
|
|
8
|
-
* so a future rename of the union doesn't require chasing literals.
|
|
9
|
-
*/
|
|
10
|
-
export declare const DEFAULT_COMPLETED_SUB_TAB: CompletedSubTab;
|
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.DEFAULT_COMPLETED_SUB_TAB = exports.toCompletedSubTab = void 0;
|
|
4
|
-
const stringToUnion_1 = require("../../../commonStateTypes/stringToUnion");
|
|
5
|
-
/**
|
|
6
|
-
* Sub-tabs that can appear under any "Completed" tab in the Expense Automation
|
|
7
|
-
* surface (Transaction Categorization Completed and Missing Receipts Completed
|
|
8
|
-
* both use this exact union). Forwarded verbatim to listing APIs as `sub_tab`
|
|
9
|
-
* / `match_type`. `'all'` preserves parent-tab semantics on the backend.
|
|
10
|
-
*/
|
|
11
|
-
const COMPLETED_SUB_TABS = ['all', 'ai_accountant', 'manual'];
|
|
12
|
-
const toCompletedSubTab = (v) => (0, stringToUnion_1.stringToUnion)(v.trim().toLowerCase(), COMPLETED_SUB_TABS);
|
|
13
|
-
exports.toCompletedSubTab = toCompletedSubTab;
|
|
14
|
-
/**
|
|
15
|
-
* "No sub-tab filter" sentinel — single source of truth for the default
|
|
16
|
-
* value of {@link CompletedSubTab}. Use this constant in initial slice
|
|
17
|
-
* state and at any call site that needs to fall back to the parent-tab
|
|
18
|
-
* listing semantics (review tab requests, manual-search overrides, etc.)
|
|
19
|
-
* so a future rename of the union doesn't require chasing literals.
|
|
20
|
-
*/
|
|
21
|
-
exports.DEFAULT_COMPLETED_SUB_TAB = 'all';
|