@topconsultnpm/sdkui-react 6.20.0-dev2.10 → 6.20.0-dev2.12

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.
@@ -3,7 +3,7 @@ import React, { useCallback, useEffect, useMemo, useRef, useState } from 'react'
3
3
  import { SDK_Globals, DataColumnTypes, MetadataDataDomains, DataListViewModes, MetadataFormats, LayoutModes, DcmtTypeListCacheService, SystemMIDsAsNumber, RetrieveFileOptions, DcmtOpers, GeneralRetrieveFormats, AccessLevelsEx, LayoutCacheService, UserListCacheService, AppModules } from '@topconsultnpm/sdk-ts';
4
4
  import styled from 'styled-components';
5
5
  import { getAllFieldSelectedDcmtsOrFocused, getCommandsMenuItems, getSelectedDcmtsOrFocused } from './TMSearchResultsMenuItems';
6
- import { genUniqueId, IconShow, IconBoard, IconDcmtTypeSys, SDKUI_Localizator, IconDelete, IconRefresh, IconMenuVertical, deepCompare, generateUniqueColumnKeys, searchResultDescriptorToSimpleArray, searchResultToMetadataValues, IconSearchCheck, TMImageLibrary, convertSearchResultDescriptorToFileItems, IconCustom, isApprovalWorkflowView, SDKUI_Globals, getMoreInfoTasksForDocument, IconInfo, IconCache, IconPlatform, getSearchToolbarVisibility } from '../../../helper';
6
+ import { genUniqueId, IconShow, IconBoard, IconDcmtTypeSys, SDKUI_Localizator, IconDelete, IconRefresh, IconMenuVertical, deepCompare, generateUniqueColumnKeys, searchResultDescriptorToSimpleArray, searchResultToMetadataValues, IconSearchCheck, TMImageLibrary, convertSearchResultDescriptorToFileItems, IconCustom, isApprovalWorkflowView, SDKUI_Globals, getMoreInfoTasksForDocument, IconCache, IconPlatform, getSearchToolbarVisibility } from '../../../helper';
7
7
  import { useDcmtOperations } from '../../../hooks/useDcmtOperations';
8
8
  import { useInputAttachmentsDialog, useInputCvtFormatDialog } from '../../../hooks/useInputDialog';
9
9
  import { useRelatedDocuments } from '../../../hooks/useRelatedDocuments';
@@ -101,7 +101,6 @@ const TMSearchResult = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, a
101
101
  const [indexingInfoCache, setIndexingInfoCache] = useState(new Map());
102
102
  const [showIndexingInfo, setShowIndexingInfo] = useState(false);
103
103
  const [loadingIndexingInfo, setLoadingIndexingInfo] = useState(false);
104
- const [openedDrawerItems, setOpenedDrawerItems] = useState(new Set());
105
104
  const floatingBarContainerRef = useRef(null);
106
105
  const [confirmFormat, ConfirmFormatDialog] = useInputCvtFormatDialog();
107
106
  const { openConfirmAttachmentsDialog, ConfirmAttachmentsDialog } = useInputAttachmentsDialog();
@@ -737,38 +736,47 @@ const TMSearchResult = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, a
737
736
  const tmBlog = useMemo(() => _jsx(TMDcmtBlog, { tid: focusedItem?.TID, did: focusedItem?.DID, fetchBlogDataTrigger: refreshBlogTrigger, allTasks: allTasks, getAllTasks: getAllTasks, deleteTaskByIdsCallback: deleteTaskByIdsCallback, addTaskCallback: addTaskCallback, editTaskCallback: editTaskCallback, handleNavigateToWGs: handleNavigateToWGs, handleNavigateToDossiers: handleNavigateToDossiers }), [focusedItem, allTasks, refreshBlogTrigger, handleNavigateToWGs, handleNavigateToDossiers]);
738
737
  const tmSysMetadata = useMemo(() => _jsx(TMMetadataValues, { layoutMode: LayoutModes.Update, openChooserBySingleClick: true, TID: focusedItem?.TID, isReadOnly: true, deviceType: deviceType, metadataValues: currentMetadataValues.filter(o => (o.mid != undefined && o.mid <= 100)), metadataValuesOrig: currentMetadataValues.filter(o => (o.mid != undefined && o.mid <= 100)), validationItems: [] }), [focusedItem, currentMetadataValues, deviceType]);
739
738
  const tmDcmtPreview = useMemo(() => _jsx(TMDcmtPreviewWrapper, { currentDcmt: currentDcmt }, refreshPreviewTrigger), [currentDcmt, refreshPreviewTrigger]);
739
+ // Auto-fetch indexing info when drawer is open and focusedItem changes
740
740
  useEffect(() => {
741
- if (!focusedItem)
741
+ if (!focusedItem || !showIndexingInfo)
742
742
  return;
743
743
  const cacheKey = `${focusedItem.TID}-${focusedItem.DID}`;
744
- setShowIndexingInfo(openedDrawerItems.has(cacheKey));
745
- }, [focusedItem, openedDrawerItems]);
744
+ if (!indexingInfoCache.has(cacheKey)) {
745
+ const fetchData = async () => {
746
+ try {
747
+ setLoadingIndexingInfo(true);
748
+ const msg = await SDK_Globals.tmSession?.NewSearchEngine().FreeSearchGetDcmtInfoAsync(focusedItem.TID, focusedItem.DID);
749
+ setIndexingInfoCache(prev => new Map(prev).set(cacheKey, msg ?? ''));
750
+ }
751
+ catch (e) {
752
+ TMExceptionBoxManager.show({ exception: e });
753
+ }
754
+ finally {
755
+ setLoadingIndexingInfo(false);
756
+ }
757
+ };
758
+ fetchData();
759
+ }
760
+ }, [focusedItem, showIndexingInfo]);
746
761
  const handleToggleIndexingInfo = async () => {
747
762
  if (!focusedItem)
748
763
  return;
749
- const cacheKey = `${focusedItem.TID}-${focusedItem.DID}`;
750
- if (showIndexingInfo) {
751
- setOpenedDrawerItems(prev => {
752
- const newSet = new Set(prev);
753
- newSet.delete(cacheKey);
754
- return newSet;
755
- });
756
- setShowIndexingInfo(false);
757
- return;
758
- }
759
- setOpenedDrawerItems(prev => new Set(prev).add(cacheKey));
760
- setShowIndexingInfo(true);
761
- if (!indexingInfoCache.has(cacheKey)) {
762
- try {
763
- setLoadingIndexingInfo(true);
764
- const msg = await SDK_Globals.tmSession?.NewSearchEngine().FreeSearchGetDcmtInfoAsync(focusedItem.TID, focusedItem.DID);
765
- setIndexingInfoCache(prev => new Map(prev).set(cacheKey, msg ?? ''));
766
- }
767
- catch (e) {
768
- TMExceptionBoxManager.show({ exception: e });
769
- }
770
- finally {
771
- setLoadingIndexingInfo(false);
764
+ const newShowState = !showIndexingInfo;
765
+ setShowIndexingInfo(newShowState);
766
+ if (newShowState) {
767
+ const cacheKey = `${focusedItem.TID}-${focusedItem.DID}`;
768
+ if (!indexingInfoCache.has(cacheKey)) {
769
+ try {
770
+ setLoadingIndexingInfo(true);
771
+ const msg = await SDK_Globals.tmSession?.NewSearchEngine().FreeSearchGetDcmtInfoAsync(focusedItem.TID, focusedItem.DID);
772
+ setIndexingInfoCache(prev => new Map(prev).set(cacheKey, msg ?? ''));
773
+ }
774
+ catch (e) {
775
+ TMExceptionBoxManager.show({ exception: e });
776
+ }
777
+ finally {
778
+ setLoadingIndexingInfo(false);
779
+ }
772
780
  }
773
781
  }
774
782
  };
@@ -806,21 +814,21 @@ const TMSearchResult = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, a
806
814
  }
807
815
  const cacheKey = `${focusedItem.TID}-${focusedItem.DID}`;
808
816
  const cachedInfo = indexingInfoCache.get(cacheKey);
809
- return (_jsxs("div", { style: { display: 'flex', flexDirection: 'column', height: '100%', overflow: 'hidden', width: '100%' }, children: [_jsx("div", { style: { padding: '10px', overflow: 'auto', flex: 1 }, children: _jsx("div", { dangerouslySetInnerHTML: { __html: ftExplanation } }) }), _jsxs(StyledIndexingInfoSection, { children: [_jsxs(StyledIndexingToggle, { onClick: handleToggleIndexingInfo, disabled: loadingIndexingInfo, children: [_jsxs(StyledLeftContent, { children: [_jsx(IconInfo, {}), _jsx("span", { children: showIndexingInfo ? 'Nascondi' : SDKUI_Localizator.IndexingInformation })] }), _jsxs(StyledRightContent, { children: [cachedInfo && (_jsxs(_Fragment, { children: [_jsx(TMTooltip, { content: "Aggiorna", children: _jsx(StyledRefreshIcon, { onClick: (e) => { e.stopPropagation(); handleRefreshIndexingInfo(); }, children: _jsx(IconRefresh, {}) }) }), _jsx(TMTooltip, { content: "Da cache", children: _jsx(StyledCachedIcon, { children: _jsx(IconCache, {}) }) })] })), _jsx(StyledChevron, { "$isOpen": showIndexingInfo, children: "\u25BC" })] })] }), loadingIndexingInfo && !cachedInfo && (_jsxs("div", { style: { marginTop: '10px', color: '#666' }, children: [SDKUI_Localizator.Loading, "..."] })), showIndexingInfo && cachedInfo && (_jsxs(StyledIndexingInfoBox, { children: [_jsx("div", { dangerouslySetInnerHTML: { __html: cachedInfo } }), loadingIndexingInfo && (_jsxs("div", { style: { position: 'absolute', top: '50%', left: '50%', transform: 'translate(-50%, -50%)', background: 'rgba(255, 255, 255, 0.9)', padding: '10px', borderRadius: '4px', boxShadow: '0 2px 8px rgba(0,0,0,0.15)' }, children: [SDKUI_Localizator.Loading, "..."] }))] }))] })] }));
810
- }, [selectedSearchResult, focusedItem, indexingInfoCache, showIndexingInfo, loadingIndexingInfo]);
817
+ return (_jsxs("div", { style: { display: 'flex', flexDirection: 'column', height: '100%', overflow: 'hidden', width: '100%' }, children: [_jsx("div", { style: { padding: '10px', overflow: 'auto', flex: 1 }, children: _jsx("div", { dangerouslySetInnerHTML: { __html: ftExplanation } }) }), _jsxs(StyledIndexingInfoSection, { children: [_jsxs(StyledIndexingToggle, { onClick: handleToggleIndexingInfo, disabled: loadingIndexingInfo, children: [_jsxs(StyledLeftContent, { children: [_jsx("span", { children: SDKUI_Localizator.IndexingInformation }), cachedInfo && (_jsx(TMTooltip, { content: "Da cache", children: _jsx(StyledCachedIcon, { children: _jsx(IconCache, { fontSize: 13 }) }) }))] }), _jsxs(StyledRightContent, { children: [cachedInfo && (_jsx(TMTooltip, { content: "Aggiorna", children: _jsx(StyledRefreshIcon, { onClick: (e) => { e.stopPropagation(); handleRefreshIndexingInfo(); }, children: _jsx(IconRefresh, {}) }) })), _jsx(StyledChevron, { "$isOpen": showIndexingInfo, children: "\u25BC" })] })] }), loadingIndexingInfo && !cachedInfo && (_jsxs("div", { style: { marginTop: '10px', color: '#666' }, children: [SDKUI_Localizator.Loading, "..."] })), showIndexingInfo && cachedInfo && (_jsxs(StyledIndexingInfoBox, { children: [_jsx("div", { dangerouslySetInnerHTML: { __html: cachedInfo } }), loadingIndexingInfo && (_jsxs("div", { style: { position: 'absolute', top: '50%', left: '50%', transform: 'translate(-50%, -50%)', background: 'rgba(255, 255, 255, 0.9)', padding: '10px', borderRadius: '4px', boxShadow: '0 2px 8px rgba(0,0,0,0.15)' }, children: [SDKUI_Localizator.Loading, "..."] }))] }))] })] }));
818
+ }, [selectedSearchResult, focusedItem, indexingInfoCache, showIndexingInfo, loadingIndexingInfo, handleRefreshIndexingInfo]);
811
819
  const allInitialPanelVisibility = {
812
820
  'tmSearchResult': true,
813
821
  'tmBlog': false,
814
822
  'tmSysMetadata': false,
815
- 'tmDcmtPreview': false,
816
823
  'tmFullTextSearch': false,
824
+ 'tmDcmtPreview': false,
817
825
  };
818
826
  const initialPanelDimensions = {
819
827
  'tmSearchResult': { width: '25%', height: '100%' },
820
828
  'tmBlog': { width: '25%', height: '100%' },
821
829
  'tmSysMetadata': { width: '25%', height: '100%' },
822
- 'tmDcmtPreview': { width: '25%', height: '100%' },
823
830
  'tmFullTextSearch': { width: '25%', height: '100%' },
831
+ 'tmDcmtPreview': { width: '25%', height: '100%' },
824
832
  };
825
833
  const initialPanels = useMemo(() => [
826
834
  {
@@ -853,12 +861,6 @@ const TMSearchResult = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, a
853
861
  contentOptions: { component: tmSysMetadata, panelContainer: { title: SDKUI_Localizator.MetadataSystem, allowMaximize: !isMobile } },
854
862
  toolbarOptions: { icon: _jsx(IconDcmtTypeSys, { fontSize: 24 }), visible: getSearchToolbarVisibility(SDK_Globals.tmSession?.SessionDescr?.appModuleID ?? AppModules.SURFER).tmSysMetadata, orderNumber: 3, isActive: allInitialPanelVisibility['tmSysMetadata'] }
855
863
  },
856
- {
857
- id: 'tmDcmtPreview',
858
- name: SDKUI_Localizator.PreviewDocument,
859
- contentOptions: { component: tmDcmtPreview },
860
- toolbarOptions: { icon: _jsx(IconShow, { fontSize: 24 }), visible: getSearchToolbarVisibility(SDK_Globals.tmSession?.SessionDescr?.appModuleID ?? AppModules.SURFER).tmDcmtPreview, orderNumber: 4, isActive: allInitialPanelVisibility['tmDcmtPreview'] }
861
- },
862
864
  ...(context === SearchResultContext.FREE_SEARCH ? [
863
865
  {
864
866
  id: 'tmFullTextSearch',
@@ -866,7 +868,13 @@ const TMSearchResult = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, a
866
868
  contentOptions: { component: tmFullTextSearch, panelContainer: { title: SDKUI_Localizator.ResultDetails, allowMaximize: !isMobile } },
867
869
  toolbarOptions: { icon: _jsx(IconPlatform, { fontSize: 20 }), visible: getSearchToolbarVisibility(SDK_Globals.tmSession?.SessionDescr?.appModuleID ?? AppModules.SURFER).tmFullTextSearch, orderNumber: 5, isActive: allInitialPanelVisibility['tmFullTextSearch'] }
868
870
  }
869
- ] : [])
871
+ ] : []),
872
+ {
873
+ id: 'tmDcmtPreview',
874
+ name: SDKUI_Localizator.PreviewDocument,
875
+ contentOptions: { component: tmDcmtPreview },
876
+ toolbarOptions: { icon: _jsx(IconShow, { fontSize: 24 }), visible: getSearchToolbarVisibility(SDK_Globals.tmSession?.SessionDescr?.appModuleID ?? AppModules.SURFER).tmDcmtPreview, orderNumber: 4, isActive: allInitialPanelVisibility['tmDcmtPreview'] }
877
+ }
870
878
  ], [tmSearchResult, tmBlog, tmSysMetadata, tmDcmtPreview, tmFullTextSearch, showToolbarHeader, context, isMobile]);
871
879
  return (_jsxs(StyledMultiViewPanel, { "$isVisible": isVisible, children: [_jsx(StyledMultiViewPanel, { "$isVisible": !isOpenDcmtForm && !isOpenDetails && !isOpenMaster, style: {
872
880
  display: 'flex',
@@ -225,9 +225,6 @@ export const useRelatedDocuments = ({ selectedSearchResult, focusedItem, current
225
225
  const filterRelationsWithAssociations = (relations) => {
226
226
  return relations.filter(rel => rel.associations && rel.associations.length > 0);
227
227
  };
228
- const getRelatedDcmt = async (relation, type) => {
229
- return await DcmtTypeListCacheService.GetAsync(type === 'detail' ? relation.detailTID : relation.masterTID);
230
- };
231
228
  const showNoRelationsAlert = (type) => {
232
229
  ShowAlert({
233
230
  message: type === 'detail'
@@ -282,6 +279,26 @@ export const useRelatedDocuments = ({ selectedSearchResult, focusedItem, current
282
279
  TMExceptionBoxManager.show({ exception: error });
283
280
  }
284
281
  }, [mapAssociationsToMids]);
282
+ const filterRelationsByPermission = async (relations, type) => {
283
+ const dataSourcePromises = relations.map(async (rel) => {
284
+ const targetTID = type === 'detail' ? rel.detailTID : rel.masterTID;
285
+ const dtd = await DcmtTypeListCacheService.GetWithNotGrantedAsync(targetTID, undefined);
286
+ const hasPermission = dtd?.perm?.canArchive === AccessLevelsEx.Yes || dtd?.perm?.canArchive === AccessLevelsEx.Mixed;
287
+ return { id: rel?.id, name: dtd?.name, hasPermission, relation: rel };
288
+ });
289
+ const allResults = await Promise.all(dataSourcePromises);
290
+ return allResults.filter(r => r.hasPermission);
291
+ };
292
+ const showNoPermissionAlert = (type) => {
293
+ ShowAlert({
294
+ message: type === 'detail'
295
+ ? SDKUI_Localizator.YouDoNotHavePermissionsToArchiveDetailDocumentsOfThisType
296
+ : SDKUI_Localizator.YouDoNotHavePermissionsToArchiveMasterDocumentsOfThisType,
297
+ mode: 'warning',
298
+ title: type === 'detail' ? SDKUI_Localizator.DcmtsDetail : SDKUI_Localizator.DcmtsMaster,
299
+ duration: 5000
300
+ });
301
+ };
285
302
  const archiveRelatedDocuments = useCallback(async (tid, type) => {
286
303
  try {
287
304
  TMSpinner.show({ description: SDKUI_Localizator.Loading });
@@ -300,14 +317,20 @@ export const useRelatedDocuments = ({ selectedSearchResult, focusedItem, current
300
317
  }
301
318
  setRelatedDcmts(withAssociations);
302
319
  if (withAssociations.length > 1) {
303
- const dataSourcePromises = withAssociations.map(async (rel) => {
304
- const relatedDcmt = await getRelatedDcmt(rel, type);
305
- return { id: rel?.id, name: relatedDcmt?.name };
306
- });
307
- const dataSource = await Promise.all(dataSourcePromises);
308
- setRelatedDcmtsChooserDataSource(dataSource);
309
- setArchiveType(type);
310
- setShowRelatedDcmtsChooser(true);
320
+ const permittedResults = await filterRelationsByPermission(withAssociations, type);
321
+ if (permittedResults.length === 0) {
322
+ showNoPermissionAlert(type);
323
+ return;
324
+ }
325
+ if (permittedResults.length === 1) {
326
+ await archiveRelatedDcmtHandler(permittedResults[0].relation, type);
327
+ }
328
+ else {
329
+ const dataSource = permittedResults.map(r => ({ id: r.id, name: r.name }));
330
+ setRelatedDcmtsChooserDataSource(dataSource);
331
+ setArchiveType(type);
332
+ setShowRelatedDcmtsChooser(true);
333
+ }
311
334
  }
312
335
  else {
313
336
  await archiveRelatedDcmtHandler(withAssociations[0], type);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@topconsultnpm/sdkui-react",
3
- "version": "6.20.0-dev2.10",
3
+ "version": "6.20.0-dev2.12",
4
4
  "description": "",
5
5
  "scripts": {
6
6
  "test": "echo \"Error: no test specified\" && exit 1",