UNPKG

@adaptabletools/adaptable

Version:

Powerful data-agnostic HTML5 AG Grid extension which provides advanced, cutting-edge functionality to meet all DataGrid requirements

174 lines (173 loc) 8.45 kB
import { AdaptableModuleBase } from './AdaptableModuleBase'; import * as ModuleConstants from '../Utilities/Constants/ModuleConstants'; import { TEAMSHARING_GET, TEAMSHARING_IMPORT_ITEM, TEAMSHARING_LINK_ITEM, TEAMSHARING_PROCESS_IMPORT, TEAMSHARING_REMOVE_ITEM, TEAMSHARING_SET, TEAMSHARING_SHARE, TEAMSHARING_UPDATE_ITEM, TeamSharingUpdateItem, } from '../Redux/ActionsReducers/TeamSharingRedux'; import * as TeamSharingRedux from '../Redux/ActionsReducers/TeamSharingRedux'; import isEqual from 'lodash/isEqual'; import { LAYOUT_SAVE } from '../Redux/ActionsReducers/LayoutRedux'; import { getSharedEntityStaleDepsItemView, SharedEntityTypeItemView, getSharedEntityActiveStatusObjectView, } from '../View/TeamSharing/SharedEntityObjectView'; import { TeamSharingApplyButton } from '../View/TeamSharing/TeamSharingApplyButton'; import { SharedEntityDependencies } from '../View/TeamSharing/SharedEntityDependencies'; import ArrayExtensions from '../Utilities/Extensions/ArrayExtensions'; import flatten from 'lodash/flatten'; import AdaptableHelper from '../Utilities/Helpers/AdaptableHelper'; export class TeamSharingModule extends AdaptableModuleBase { constructor(api) { super(ModuleConstants.TeamSharingModuleId, ModuleConstants.TeamSharingFriendlyName, 'folder-shared', 'TeamSharingPopup', 'Team Sharing allows users to share - at run-time - Adaptable Objects between colleagues.', api); this.SKIP_TEAMSHARING_UPDATE_ACTIONS = [ TEAMSHARING_GET, TEAMSHARING_SET, TEAMSHARING_SHARE, TEAMSHARING_IMPORT_ITEM, TEAMSHARING_PROCESS_IMPORT, TEAMSHARING_REMOVE_ITEM, TEAMSHARING_LINK_ITEM, TEAMSHARING_UPDATE_ITEM, ]; } onAdaptableReady() { // make sure there is no zombie import process remaining (in case a previous import crashed) this.api.internalApi.dispatchReduxAction(TeamSharingRedux.TeamSharingCommitImport()); if (this.api.teamSharingApi.isTeamSharingAvailable()) { this.api.teamSharingApi.refreshTeamSharing(); } this.api.eventApi.on('AdaptableStateChanged', (adaptableStateChangedInfo) => this.handleStateChanged(adaptableStateChangedInfo)); } isModuleAvailable() { return super.isModuleAvailable() && this.api.teamSharingApi.isTeamSharingAvailable(); } isModuleObjectsShareable() { return false; } getPopupMaxWidth() { return 1000; } handleStateChanged(adaptableStateChangedInfo) { // check if TeamSharing is activated if (!this.api.teamSharingApi.isTeamSharingAvailable()) { return; } // skip all teamsharing actions, otherwise we could get in an infinite loop if (this.SKIP_TEAMSHARING_UPDATE_ACTIONS.includes(adaptableStateChangedInfo.action.type)) { return; } // check if there is any changed adaptable object const changedAdaptableObject = this.extractAdaptableObjectFromAction(adaptableStateChangedInfo.action); if (!changedAdaptableObject) { return; } // check if the changed adaptable object is active in TeamSharing const activeSharedEntity = this.api.internalApi.getState().TeamSharing.ActiveSharedEntityMap[changedAdaptableObject.Uuid]; if (!activeSharedEntity) { return; } // handle special case of LAYOUT_SAVE which might be called redundantly without actually changing the state const isLayoutStateUnchanged = adaptableStateChangedInfo.action.type === LAYOUT_SAVE && isEqual(adaptableStateChangedInfo.oldState.Layout, adaptableStateChangedInfo.newState.Layout); if (isLayoutStateUnchanged) { return; } this.api.internalApi.dispatchReduxAction(TeamSharingUpdateItem(changedAdaptableObject, adaptableStateChangedInfo.userName)); } extractAdaptableObjectFromAction(action) { // this implementation is based on the assumption that any action which mutates an AdaptableObject has // at most one(1) property which has an 'Uuid:TypeUuid' defined (and that is the AdaptableObject, of course) if (!action) { return; } return Object.values(action).find((actionPropertyValue) => AdaptableHelper.isAdaptableObject(actionPropertyValue)); } isAdaptableObjectPresentInLocalState(sharedEntity) { return !!this.api.internalApi .getModuleService() .getModuleById(sharedEntity.Module) ?.getModuleAdaptableObjects() .find((adaptableObject) => adaptableObject.Uuid === sharedEntity.Entity.Uuid); } isSharedEntityADependency(sharedEntity) { const allSharedEntries = this.api.teamSharingApi.getLoadedAdaptableSharedEntities(); return allSharedEntries.some((sharedEntryCandidate) => { return sharedEntryCandidate?.EntityDependencyIds?.includes(sharedEntity.Uuid); }); } isStaleAndActive(sharedEntity) { const staleActiveEntities = this.api.internalApi .getTeamSharingService() .getStaleActiveSharedEntities(); return (this.isAdaptableObjectPresentInLocalState(sharedEntity) && !!staleActiveEntities[sharedEntity.Uuid]); } getDependencies(sharedEntity) { if (!Array.isArray(sharedEntity.EntityDependencyIds) || sharedEntity.EntityDependencyIds.length === 0) { return [sharedEntity]; } const allSharedEntities = this.api.teamSharingApi.getLoadedAdaptableSharedEntities(); const dependencies = sharedEntity.EntityDependencyIds.map((dependencyUuid) => allSharedEntities.find((entity) => entity.Uuid === dependencyUuid)); return flatten(dependencies.map((dependency) => this.getDependencies(dependency))); } getStaleDependencies(sharedEntity) { return this.getDependencies(sharedEntity).filter((dependency) => dependency.Uuid !== sharedEntity.Uuid && this.isStaleAndActive(dependency)); } toView(sharedEntity) { const isDependency = this.isSharedEntityADependency(sharedEntity); const staleDependencies = this.getStaleDependencies(sharedEntity); const staleDependenciesViewItems = []; if (staleDependencies?.length) { staleDependenciesViewItems.push({ name: 'Stale Deps', view: getSharedEntityStaleDepsItemView(staleDependencies), }); } const sharedViewItems = []; const isStaleAndActive = this.isStaleAndActive(sharedEntity); if (!isDependency || isStaleAndActive) { sharedViewItems.push({ name: 'Shared', view: getSharedEntityActiveStatusObjectView(isDependency), }); } return { items: [ !isDependency && sharedEntity.Description && { name: 'Name', values: [sharedEntity.Description], }, !isDependency && { name: 'Share Mode', values: [sharedEntity.Type], }, ...sharedViewItems, { name: 'Type', view: SharedEntityTypeItemView, }, ...staleDependenciesViewItems, ArrayExtensions.IsNotNullOrEmpty(sharedEntity.EntityDependencyIds) && { name: 'Dependencies', isLabelInline: true, view: SharedEntityDependencies, }, ].filter(Boolean), abObject: sharedEntity, }; } toViewAll() { return ((this.api.teamSharingApi.getLoadedAdaptableSharedEntities() ?? []) // only top level .filter((sharedEntity) => !this.isSharedEntityADependency(sharedEntity)) .map((item) => this.toView(item))); } getViewProperties() { return { actions: [TeamSharingApplyButton], onMount: () => { this.api.teamSharingApi.refreshTeamSharing(); }, getDeleteAction: (sharedEntity) => { return TeamSharingRedux.TeamSharingRemoveItem(sharedEntity.Uuid); }, emptyView: 'Shared Items will appear here when available.', }; } }