[AAE-5612] FE - [ADF] Destination picker it's not displaying my files folder if the destination Folder path type of string/folder variable is set to a folder part of trash (#7224)

* [AAE-5612] FE - [ADF] Destination picker it's not displaying my files folder if the destination Folder path type of string/folder variable is set to a folder part of trash

* * Refactored getDestinationFolderPath

* * Updated attachFileCloudWidget unit tests

* * Renamed method name

* * Added unit tests to the content-cloud-node-selector service

* * Fixed comments

* * Removed mock obj

* * fixed lint error

* * Fixed lint error
This commit is contained in:
siva kumar
2021-09-28 16:18:48 +05:30
committed by GitHub
parent f963c6d15e
commit e73d3c3213
6 changed files with 297 additions and 163 deletions

View File

@@ -39,3 +39,4 @@ export * from './group.model';
export * from './form-variable.model';
export * from './process-variable.model';
export * from './upload-widget-content-link.model';
export * from './form-field-file-source';

View File

@@ -38,17 +38,13 @@ import {
mockNodeId,
fakeLocalPngResponse,
onlyLocalParams,
allSourceWithRootParams,
allSourceWithWrongAliasParams,
allSourceWithNoAliasParams,
allSourceWithoutDestinationFolderPath,
allSourceWithoutValueProperty,
fakeNodeWithProperties,
menuTestSourceParam,
expectedValues,
fakeLocalPngAnswer,
allSourceWithStringTypeEmptyValue,
allSourceWithFolderTypeEmptyValue,
mockNodeIdBasedOnStringVariableValue,
mockAllFileSourceWithStringVariablePathType,
mockAllFileSourceWithFolderVariablePathType,
@@ -57,7 +53,6 @@ import {
formVariables,
processVariables,
mockAllFileSourceWithRenamedFolderVariablePathType,
allSourceParamsWithWrongRelativePath,
allSourceParamsWithRelativePath,
fakeLocalPhysicalRecordResponse
} from '../../../mocks/attach-file-cloud-widget.mock';
@@ -165,7 +160,7 @@ describe('AttachFileCloudWidgetComponent', () => {
});
it('should be able to attach files coming from all files source', async () => {
spyOn(contentCloudNodeSelectorService, 'fetchNodeIdFromRelativePath').and.returnValue(mockNodeId);
spyOn(contentCloudNodeSelectorService, 'getNodeIdFromPath').and.returnValue(mockNodeId);
createUploadWidgetField(new FormModel(), 'attach-file-alfresco', [], allSourceParams);
fixture.detectChanges();
await fixture.whenStable();
@@ -205,7 +200,7 @@ describe('AttachFileCloudWidgetComponent', () => {
describe('destinationFolderPath', () => {
it('should be able to fetch nodeId if destinationFolderPath is defined', async () => {
const fetchNodeIdFromRelativePathSpy = spyOn(contentCloudNodeSelectorService, 'fetchNodeIdFromRelativePath').and.returnValue(mockNodeId);
const getNodeIdFromPathSpy = spyOn(contentCloudNodeSelectorService, 'getNodeIdFromPath').and.returnValue(mockNodeId);
createUploadWidgetField(new FormModel(), 'attach-file-alfresco', [], allSourceParams);
fixture.detectChanges();
@@ -215,37 +210,15 @@ describe('AttachFileCloudWidgetComponent', () => {
fixture.detectChanges();
await fixture.whenStable();
const alias = '-root-';
const opt = { relativePath: '/myfiles' };
const mockDestinationPath = { alias: '-root-', path: '/myfiles' };
expect(fetchNodeIdFromRelativePathSpy).toHaveBeenCalledWith(alias, opt);
expect(getNodeIdFromPathSpy).toHaveBeenCalledWith(mockDestinationPath);
expect(widget.field.params.fileSource.destinationFolderPath.value).toBe('-root-/myfiles');
expect(widget.rootNodeId).toEqual('mock-node-id');
});
it('should be able to fetch nodeId based on given alias if the relative path is wrong', async () => {
const fetchNodeIdFromRelativePathSpy = spyOn(contentCloudNodeSelectorService, 'fetchNodeIdFromRelativePath').and.returnValue(new Promise((reject) => reject(undefined)));
const fetchAliasNodeIdSpy = spyOn(contentCloudNodeSelectorService, 'fetchAliasNodeId').and.returnValue(mockNodeId);
createUploadWidgetField(new FormModel(), 'attach-file-alfresco', [], allSourceParamsWithWrongRelativePath);
fixture.detectChanges();
await fixture.whenStable();
clickOnAttachFileWidget('attach-file-alfresco');
fixture.detectChanges();
await fixture.whenStable();
const alias = '-shared-';
const opt = { relativePath: '/wrongRelativePath' };
expect(fetchNodeIdFromRelativePathSpy).toHaveBeenCalledWith(alias, opt);
expect(fetchAliasNodeIdSpy).toHaveBeenCalledWith(alias);
expect(widget.rootNodeId).toEqual('mock-node-id');
});
it('should be able to fetch relativePath nodeId if the given relative path is correct', async () => {
const fetchNodeIdFromRelativePathSpy = spyOn(contentCloudNodeSelectorService, 'fetchNodeIdFromRelativePath').and.returnValue(mockNodeId);
const fetchAliasNodeIdSpy = spyOn(contentCloudNodeSelectorService, 'fetchAliasNodeId');
const getNodeIdFromPathSpy = spyOn(contentCloudNodeSelectorService, 'getNodeIdFromPath').and.returnValue(mockNodeId);
createUploadWidgetField(new FormModel(), 'attach-file-alfresco', [], allSourceParamsWithRelativePath);
fixture.detectChanges();
@@ -255,16 +228,14 @@ describe('AttachFileCloudWidgetComponent', () => {
fixture.detectChanges();
await fixture.whenStable();
const alias = '-shared-';
const opt = { relativePath: '/myfiles' };
const mockDestinationPath = { alias: '-shared-', path: '/myfiles' };
expect(fetchNodeIdFromRelativePathSpy).toHaveBeenCalledWith(alias, opt);
expect(fetchAliasNodeIdSpy).not.toHaveBeenCalledWith(alias);
expect(getNodeIdFromPathSpy).toHaveBeenCalledWith(mockDestinationPath);
expect(widget.rootNodeId).toEqual('mock-node-id');
});
it('should be able to use mapped string variable value if the destinationFolderPath set to string type variable', async () => {
const fetchNodeIdFromRelativePathSpy = spyOn(contentCloudNodeSelectorService, 'fetchNodeIdFromRelativePath').and.returnValue(mockNodeIdBasedOnStringVariableValue);
const getNodeIdFromPathSpy = spyOn(contentCloudNodeSelectorService, 'getNodeIdFromPath').and.returnValue(mockNodeIdBasedOnStringVariableValue);
const form = new FormModel({ formVariables, processVariables});
createUploadWidgetField(form, 'attach-file-alfresco', [], mockAllFileSourceWithStringVariablePathType);
@@ -274,15 +245,14 @@ describe('AttachFileCloudWidgetComponent', () => {
fixture.detectChanges();
await fixture.whenStable();
const alias = '-root-';
const opt = { relativePath: '/pathBasedOnStringvariablevalue' };
const mockDestinationPath = { alias: '-root-', path: '/pathBasedOnStringvariablevalue' };
expect(fetchNodeIdFromRelativePathSpy).toHaveBeenCalledWith(alias, opt);
expect(getNodeIdFromPathSpy).toHaveBeenCalledWith(mockDestinationPath);
expect(widget.rootNodeId).toEqual('mock-string-value-node-id');
});
it('should be able to use default location if mapped string variable value is undefined/empty', async () => {
const fetchAliasNodeIdSpy = spyOn(contentCloudNodeSelectorService, 'fetchAliasNodeId').and.returnValue(mockNodeId);
const getNodeIdFromPathSpy = spyOn(contentCloudNodeSelectorService, 'getNodeIdFromPath').and.returnValue(mockNodeId);
createUploadWidgetField(new FormModel(), 'attach-file-alfresco', [], allSourceWithStringTypeEmptyValue);
fixture.detectChanges();
await fixture.whenStable();
@@ -291,15 +261,15 @@ describe('AttachFileCloudWidgetComponent', () => {
fixture.detectChanges();
await fixture.whenStable();
const alias = '-my-';
const mockDestinationPath = { alias: '-my-', path: undefined };
expect(fetchAliasNodeIdSpy).toHaveBeenCalledWith(alias);
expect(getNodeIdFromPathSpy).toHaveBeenCalledWith(mockDestinationPath);
expect(widget.rootNodeId).toEqual('mock-node-id');
});
it('should be able to use mapped folder variable value if destinationFolderPath set to folder type variable', async () => {
const fetchNodeIdFromRelativePathSpy = spyOn(contentCloudNodeSelectorService, 'fetchNodeIdFromRelativePath');
const form = new FormModel({ formVariables, processVariables});
const verifyFolderSpy = spyOn(contentCloudNodeSelectorService, 'getNodeIdFromFolderVariableValue').and.returnValue(mockNodeId);
const form = new FormModel({ formVariables, processVariables });
createUploadWidgetField(form, 'attach-file-alfresco', [], mockAllFileSourceWithFolderVariablePathType);
fixture.detectChanges();
await fixture.whenStable();
@@ -307,38 +277,10 @@ describe('AttachFileCloudWidgetComponent', () => {
fixture.detectChanges();
await fixture.whenStable();
expect(fetchNodeIdFromRelativePathSpy).not.toHaveBeenCalled();
expect(widget.rootNodeId).toBe('mock-folder-id');
});
it('should be able to use default location if the mapped folder variable value is undefined/empty', async () => {
const fetchAliasNodeIdSpy = spyOn(contentCloudNodeSelectorService, 'fetchAliasNodeId').and.returnValue(mockNodeId);
createUploadWidgetField(new FormModel(), 'attach-file-alfresco', [], allSourceWithFolderTypeEmptyValue);
fixture.detectChanges();
await fixture.whenStable();
clickOnAttachFileWidget('attach-file-alfresco');
fixture.detectChanges();
await fixture.whenStable();
const alias = '-my-';
expect(fetchAliasNodeIdSpy).toHaveBeenCalledWith(alias);
expect(verifyFolderSpy).toHaveBeenCalled();
expect(widget.rootNodeId).toBe('mock-node-id');
});
it('Should be able to set given alias as rootNodeId if the nodeId of the alias is not fetched from the api', async () => {
createUploadWidgetField(new FormModel(), 'attach-file-alfresco', [], allSourceWithRootParams);
fixture.detectChanges();
await fixture.whenStable();
clickOnAttachFileWidget('attach-file-alfresco');
fixture.detectChanges();
await fixture.whenStable();
expect(widget.rootNodeId).toEqual('-root-');
expect(openUploadFileDialogSpy).toHaveBeenCalledWith('-root-', 'single', true, true);
});
it('Should set default user alias (-my-) as rootNodeId if destinationFolderPath contains wrong alias and single upload for Alfresco Content + Locale', async () => {
createUploadWidgetField(new FormModel(), 'attach-file-alfresco', [], allSourceWithWrongAliasParams, false);
fixture.detectChanges();
@@ -376,32 +318,6 @@ describe('AttachFileCloudWidgetComponent', () => {
expect(openUploadFileDialogSpy).toHaveBeenCalledWith('-my-', 'multiple', true, true);
});
it('Should set default user alias (-my-) as rootNodeId if destinationFolderPath is not defined', async () => {
const getAliasAndPathSpy = spyOn(widget, 'getAliasAndRelativePathFromDestinationFolderPath').and.callThrough();
createUploadWidgetField(new FormModel(), 'attach-file-alfresco', [], allSourceWithoutDestinationFolderPath);
fixture.detectChanges();
await fixture.whenStable();
clickOnAttachFileWidget('attach-file-alfresco');
fixture.detectChanges();
await fixture.whenStable();
expect(getAliasAndPathSpy).not.toHaveBeenCalled();
expect(widget.rootNodeId).toEqual('-my-');
});
it('Should set default user alias (-my-) as rootNodeId if value property missing from destinationFolderPath', async () => {
const getAliasAndPathSpy = spyOn(widget, 'getAliasAndRelativePathFromDestinationFolderPath').and.callThrough();
createUploadWidgetField(new FormModel(), 'attach-file-alfresco', [], allSourceWithoutValueProperty);
fixture.detectChanges();
await fixture.whenStable();
clickOnAttachFileWidget('attach-file-alfresco');
fixture.detectChanges();
await fixture.whenStable();
expect(getAliasAndPathSpy).not.toHaveBeenCalled();
expect(widget.rootNodeId).toEqual('-my-');
});
it('should return the application name in case -appname- placeholder is present', () => {
appConfigService.config = Object.assign(appConfigService.config, {
'alfresco-deployed-apps': [
@@ -420,7 +336,7 @@ describe('AttachFileCloudWidgetComponent', () => {
describe('FilesSource', () => {
it('Should be able to fetch nodeId of default user alias (-my-) if fileSource set only to Alfresco Content', async () => {
const fetchAliasNodeIdSpy = spyOn(contentCloudNodeSelectorService, 'fetchAliasNodeId').and.returnValue(mockNodeId);
const getNodeIdFromPathSpy = spyOn(contentCloudNodeSelectorService, 'getNodeIdFromPath').and.returnValue(mockNodeId);
createUploadWidgetField(new FormModel(), 'attach-file-alfresco', [], contentSourceParam, false);
fixture.detectChanges();
await fixture.whenStable();
@@ -428,15 +344,15 @@ describe('AttachFileCloudWidgetComponent', () => {
fixture.detectChanges();
await fixture.whenStable();
const alias = '-my-';
const mockDestinationPath = { alias: '-my-', path: undefined };
expect(fetchAliasNodeIdSpy).toHaveBeenCalledWith(alias);
expect(getNodeIdFromPathSpy).toHaveBeenCalledWith(mockDestinationPath);
expect(widget.rootNodeId).toEqual('mock-node-id');
expect(openUploadFileDialogSpy).toHaveBeenCalledWith('mock-node-id', 'single', false, true);
});
it('Should be able to fetch nodeId of default user alias (-my-) if fileSource set to multiple upload for Alfresco Content', async () => {
const fetchAliasNodeIdSpy = spyOn(contentCloudNodeSelectorService, 'fetchAliasNodeId').and.returnValue(mockNodeId);
const getNodeIdFromPathSpy = spyOn(contentCloudNodeSelectorService, 'getNodeIdFromPath').and.returnValue(mockNodeId);
createUploadWidgetField(new FormModel(), 'attach-file-alfresco', [], contentSourceParam, true);
fixture.detectChanges();
@@ -445,9 +361,9 @@ describe('AttachFileCloudWidgetComponent', () => {
fixture.detectChanges();
await fixture.whenStable();
const alias = '-my-';
const mockDestinationPath = { alias: '-my-', path: undefined };
expect(fetchAliasNodeIdSpy).toHaveBeenCalledWith(alias);
expect(getNodeIdFromPathSpy).toHaveBeenCalledWith(mockDestinationPath);
expect(widget.rootNodeId).toEqual('mock-node-id');
expect(openUploadFileDialogSpy).toHaveBeenCalledWith('mock-node-id', 'multiple', false, true);
});
@@ -531,7 +447,7 @@ describe('AttachFileCloudWidgetComponent', () => {
describe('when a file is uploaded', () => {
beforeEach(async () => {
apiServiceSpy = spyOn(widget['nodesApi'], 'getNode').and.returnValue(new Promise(resolve => resolve({entry: fakeNodeWithProperties})));
spyOn(contentCloudNodeSelectorService, 'fetchNodeIdFromRelativePath').and.returnValue(new Promise(resolve => resolve('fake-properties')));
spyOn(contentCloudNodeSelectorService, 'getNodeIdFromPath').and.returnValue(new Promise(resolve => resolve('fake-properties')));
openUploadFileDialogSpy.and.returnValue(of([fakeNodeWithProperties]));
widget.field = new FormFieldModel(new FormModel(), {
type: FormFieldTypes.UPLOAD,

View File

@@ -27,7 +27,8 @@ import {
ContentLinkModel,
AppConfigService,
AlfrescoApiService,
UploadWidgetContentLinkModel
UploadWidgetContentLinkModel,
DestinationFolderPath
} from '@alfresco/adf-core';
import { Node, NodesApi, RelatedContentRepresentation } from '@alfresco/js-api';
import { ContentCloudNodeSelectorService } from '../../../services/content-cloud-node-selector.service';
@@ -143,37 +144,44 @@ export class AttachFileCloudWidgetComponent extends UploadCloudWidgetComponent i
private async getDestinationFolderNodeId(): Promise<string> {
let rootNodeId: string;
let destinationFolderPath = <DestinationFolderPathModel> { alias: AttachFileCloudWidgetComponent.ALIAS_USER_FOLDER, path: '' };
if (this.isAlfrescoAndLocal() && this.hasDestinationFolder()) {
if (this.isPathVariableType(DestinationFolderPathType.STRING_TYPE) || this.isPathStaticType()) {
destinationFolderPath = this.getAliasAndRelativePathFromDestinationFolderPath(this.field.params.fileSource.destinationFolderPath.value);
destinationFolderPath.path = this.replaceAppNameAliasWithValue(destinationFolderPath.path);
}
if (this.isPathVariableType(DestinationFolderPathType.FOLDER_TYPE)) {
rootNodeId = this.field.params.fileSource.destinationFolderPath.value;
}
}
if (!rootNodeId) {
try {
const nodeId = await this.getNodeIdBasedOnPath(destinationFolderPath);
rootNodeId = nodeId ? nodeId : destinationFolderPath.alias;
} catch (error) {
this.logService.error(error);
}
switch (this.field?.params?.fileSource?.destinationFolderPath?.type) {
case DestinationFolderPathType.STATIC_TYPE:
rootNodeId = await this.getNodeIdFromPath(this.field.params.fileSource.destinationFolderPath);
break;
case DestinationFolderPathType.STRING_TYPE:
rootNodeId = await this.getNodeIdFromPath(this.field.params.fileSource.destinationFolderPath);
break;
case DestinationFolderPathType.FOLDER_TYPE:
rootNodeId = await this.getNodeIdFromFolderVariableValue(this.field.params.fileSource.destinationFolderPath);
break;
default:
rootNodeId = await this.getNodeIdFromPath({ type: '', value: AttachFileCloudWidgetComponent.ALIAS_USER_FOLDER });
break;
}
return rootNodeId;
}
private async getNodeIdBasedOnPath(destinationFolderPath: DestinationFolderPathModel) {
async getNodeIdFromPath(destinationFolderPath: DestinationFolderPath): Promise<string> {
let nodeId: string;
if (destinationFolderPath.path) {
nodeId = await this.contentNodeSelectorService.fetchNodeIdFromRelativePath(destinationFolderPath.alias, { relativePath: destinationFolderPath.path });
const destinationPath = this.getAliasAndRelativePathFromDestinationFolderPath(destinationFolderPath.value);
destinationPath.path = this.replaceAppNameAliasWithValue(destinationPath.path);
try {
nodeId = await this.contentNodeSelectorService.getNodeIdFromPath(destinationPath);
} catch (error) {
this.logService.error(error);
}
if (!nodeId) {
nodeId = await this.contentNodeSelectorService.fetchAliasNodeId(destinationFolderPath.alias);
return nodeId;
}
async getNodeIdFromFolderVariableValue(destinationFolderPath: DestinationFolderPath): Promise<string> {
let nodeId: string;
try {
nodeId = await this.contentNodeSelectorService.getNodeIdFromFolderVariableValue(destinationFolderPath.value, AttachFileCloudWidgetComponent.ALIAS_USER_FOLDER);
} catch (error) {
this.logService.error(error);
}
return nodeId;
@@ -251,10 +259,6 @@ export class AttachFileCloudWidgetComponent extends UploadCloudWidgetComponent i
return alias && AttachFileCloudWidgetComponent.VALID_ALIAS.includes(alias);
}
private hasDestinationFolder(): boolean {
return !!this.field?.params?.fileSource?.destinationFolderPath?.value;
}
ngOnDestroy() {
this.contentNodeSelectorPanelService.customModels = [];
}

View File

@@ -95,17 +95,6 @@ export const menuTestSourceParam = {
}
};
export const allSourceParamsWithWrongRelativePath = {
fileSource: {
name: 'all file sources',
serviceId: FileSourceTypes.ALL_FILE_SOURCES_SERVICE_ID,
destinationFolderPath: {
value: '-shared-/wrongRelativePath',
type: DestinationFolderPathType.STATIC_TYPE
}
}
};
export const allSourceParamsWithRelativePath = {
fileSource: {
name: 'all file sources',

View File

@@ -0,0 +1,195 @@
/*!
* @license
* Copyright 2019 Alfresco Software, Ltd.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import { TestBed } from '@angular/core/testing';
import { AlfrescoApiService, AlfrescoApiServiceMock, NotificationService, setupTestBed } from '@alfresco/adf-core';
import { ProcessServiceCloudTestingModule } from '../../testing/process-service-cloud.testing.module';
import { TranslateModule } from '@ngx-translate/core';
import { ContentCloudNodeSelectorService } from 'process-services-cloud';
import { MatDialog, MatDialogModule } from '@angular/material/dialog';
import { of, Subject } from 'rxjs';
describe('ContentCloudNodeSelectorService', () => {
let service: ContentCloudNodeSelectorService;
let notificationService: NotificationService;
let getNodeSpy: jasmine.Spy;
let dialog: MatDialog;
let openDialogSpy: jasmine.Spy;
let showWarningSpy: jasmine.Spy;
const relativePathNodeResponseBody = {
entry: {
id: 'mock-relative-path-node-id'
}
};
const aliasNodeResponseBody = {
entry: {
id: 'mock-alias-node-id'
}
};
const folderVariableValueResponseBody = {
entry: {
id: 'mock-folder-id'
}
};
setupTestBed({
imports: [TranslateModule.forRoot(), ProcessServiceCloudTestingModule, MatDialogModule],
providers: [
{ provide: AlfrescoApiService, useClass: AlfrescoApiServiceMock }
]
});
beforeEach(() => {
service = TestBed.inject(ContentCloudNodeSelectorService);
notificationService = TestBed.inject(NotificationService);
dialog = TestBed.inject(MatDialog);
showWarningSpy = spyOn(notificationService, 'showWarning');
openDialogSpy = spyOn(dialog, 'open').and.returnValue({
afterOpened: () => of({}),
afterClosed: () => of({}),
componentInstance: {
error: new Subject<any>()
}
});
getNodeSpy = spyOn(service.nodesApi, 'getNode');
});
it('should be able to fetch nodeId from given relative path', async () => {
getNodeSpy.and.returnValue(Promise.resolve(relativePathNodeResponseBody));
const relativePathNodeEntry = await service.getNodeIdFromPath({ alias: 'mock-alias', path: 'mock-relativePath' });
expect(relativePathNodeEntry).toBe(relativePathNodeResponseBody.entry.id);
expect(getNodeSpy).toHaveBeenCalledWith('mock-alias', {
relativePath: 'mock-relativePath'
});
});
it('should fetch nodeId based on alias if the relative path is undefined', async () => {
getNodeSpy.and.returnValue(Promise.resolve(aliasNodeResponseBody));
const aliasNodeId = await service.getNodeIdFromPath({ alias: 'mock-alias', path: undefined });
expect(getNodeSpy).toHaveBeenCalledWith('mock-alias', undefined);
expect(aliasNodeId).toEqual('mock-alias-node-id');
});
it('should be able to verify and return nodeId from given folderId', async () => {
getNodeSpy.and.returnValue(Promise.resolve(folderVariableValueResponseBody));
const relativePathNodeEntry = await service.getNodeIdFromFolderVariableValue('mock-folder-id', '-my-');
expect(relativePathNodeEntry).toBe('mock-folder-id');
expect(getNodeSpy).toHaveBeenCalledWith('mock-folder-id', undefined);
});
it('should return defined alias nodeId if the relative path does not exist', async () => {
getNodeSpy.and.returnValues(Promise.reject('Relative does not exists'), Promise.resolve(aliasNodeResponseBody));
const aliasNodeId = await service.getNodeIdFromPath({ alias: 'mock-alias', path: 'mock-relativePath' });
expect(getNodeSpy).toHaveBeenCalledTimes(2);
expect(aliasNodeId).toEqual('mock-alias-node-id');
});
it('should fetch default nodeId if the folderId is not defined', async () => {
getNodeSpy.and.returnValue(Promise.resolve(aliasNodeResponseBody));
await service.getNodeIdFromFolderVariableValue('', '-my-');
expect(getNodeSpy).toHaveBeenCalledWith('-my-', undefined);
});
it('should return default nodeId if the given folder does not exist', async () => {
getNodeSpy.and.returnValues(Promise.reject('Folder does not exists'), Promise.resolve(aliasNodeResponseBody));
const aliasNodeId = await service.getNodeIdFromFolderVariableValue('mock-folder-id', '-my-');
expect(getNodeSpy).toHaveBeenCalledTimes(2);
expect(aliasNodeId).toEqual('mock-alias-node-id');
});
it('should be able to fetch nodeId from given alias', async () => {
getNodeSpy.and.returnValue(Promise.resolve(aliasNodeResponseBody));
const aliasNodeId = await service.getNodeIdFromPath({ alias: 'mock-alias', path: undefined });
expect(getNodeSpy).toHaveBeenCalledWith('mock-alias', undefined);
expect(aliasNodeId).toEqual('mock-alias-node-id');
});
it('should be able to open the content node selector panel dialog', () => {
service.openUploadFileDialog('nodeId', 'single', true, true);
expect(openDialogSpy).toHaveBeenCalled();
});
it('should show a warning notification if the relative path is invalid/deleted', async () => {
getNodeSpy.and.returnValue(Promise.reject('Relative path does not exists'));
try {
expect(service.sourceNodeNotFound).toBe(false);
await service.getNodeIdFromPath({ alias: 'mock-alias', path: 'mock-relativePath' });
fail('An error should have been thrown');
} catch (error) {
expect(error).toEqual('Relative path does not exists');
expect(service.sourceNodeNotFound).toBe(true);
}
await service.openUploadFileDialog('nodeId', 'single', true, true);
expect(openDialogSpy).toHaveBeenCalled();
expect(showWarningSpy).toHaveBeenCalledWith('ADF_CLOUD_TASK_FORM.ERROR.DESTINATION_FOLDER_PATH_ERROR');
});
it('should show a warning notification if the defined folderVariable value is invalid/deleted', async () => {
getNodeSpy.and.returnValue(Promise.reject('Folder does not exists'));
try {
expect(service.sourceNodeNotFound).toBe(false);
await service.getNodeIdFromFolderVariableValue('mock-folder-id', '-my-');
fail('An error should have been thrown');
} catch (error) {
expect(error).toEqual('Folder does not exists');
expect(service.sourceNodeNotFound).toBe(true);
}
await service.openUploadFileDialog('nodeId', 'single', true, true);
expect(openDialogSpy).toHaveBeenCalled();
expect(showWarningSpy).toHaveBeenCalledWith('ADF_CLOUD_TASK_FORM.ERROR.DESTINATION_FOLDER_PATH_ERROR');
});
it('should not show a notification if the relative path is valid', async () => {
getNodeSpy.and.returnValue(Promise.resolve(relativePathNodeResponseBody));
await service.getNodeIdFromPath({ alias: 'mock-alias', path: 'mock-relativePath' });
service.openUploadFileDialog('nodeId', 'single', true, true);
expect(openDialogSpy).toHaveBeenCalled();
expect(service.sourceNodeNotFound).toBe(false);
expect(showWarningSpy).not.toHaveBeenCalled();
});
it('should not show a notification if the given folderVariable value is valid', async () => {
getNodeSpy.and.returnValue(Promise.resolve(folderVariableValueResponseBody));
await service.getNodeIdFromFolderVariableValue('mock-folder-id');
service.openUploadFileDialog('nodeId', 'single', true, true);
expect(openDialogSpy).toHaveBeenCalled();
expect(service.sourceNodeNotFound).toBe(false);
expect(showWarningSpy).not.toHaveBeenCalled();
});
});

View File

@@ -16,22 +16,24 @@
*/
import { Injectable } from '@angular/core';
import { AlfrescoApiService, NotificationService } from '@alfresco/adf-core';
import { AlfrescoApiService, LogService, NotificationService } from '@alfresco/adf-core';
import { MatDialog } from '@angular/material/dialog';
import {
ContentNodeSelectorComponent,
ContentNodeSelectorComponentData,
NodeAction
} from '@alfresco/adf-content-services';
import { Node, NodesApi } from '@alfresco/js-api';
import { Observable, Subject, throwError } from 'rxjs';
import { Node, NodeEntry, NodesApi } from '@alfresco/js-api';
import { from, Observable, Subject, throwError } from 'rxjs';
import { catchError, map, mapTo } from 'rxjs/operators';
import { DestinationFolderPathModel } from '../models/form-cloud-representation.model';
@Injectable({
providedIn: 'root'
})
export class ContentCloudNodeSelectorService {
_nodesApi: NodesApi;
private _nodesApi: NodesApi;
get nodesApi(): NodesApi {
this._nodesApi = this._nodesApi ?? new NodesApi(this.apiService.getInstance());
return this._nodesApi;
@@ -42,6 +44,7 @@ export class ContentCloudNodeSelectorService {
constructor(
private apiService: AlfrescoApiService,
private notificationService: NotificationService,
private logService: LogService,
private dialog: MatDialog) {
}
@@ -64,21 +67,47 @@ export class ContentCloudNodeSelectorService {
return select;
}
async fetchNodeIdFromRelativePath(alias: string, opts: { relativePath: string }): Promise<string> {
const relativePathNodeEntry: any = await this.nodesApi
.getNode(alias, opts)
.catch((err) => {
this.sourceNodeNotFound = true;
return this.handleError(err);
});
return relativePathNodeEntry?.entry?.id;
async getNodeIdFromPath(destinationFolderPath: DestinationFolderPathModel): Promise<string> {
if (destinationFolderPath.alias && destinationFolderPath.path) {
try {
return await this.getNodeId(destinationFolderPath.alias, destinationFolderPath.path).toPromise();
} catch (error) {
this.logService.error(error);
}
}
return this.getNodeId(destinationFolderPath.alias).toPromise();
}
async fetchAliasNodeId(alias: string): Promise<string> {
const aliasNodeEntry: any = await this.nodesApi
.getNode(alias)
.catch((err) => this.handleError(err));
return aliasNodeEntry?.entry?.id;
async getNodeIdFromFolderVariableValue(variableValue: string, defaultAlias?: string): Promise<string> {
const isExistingNode = await this.isExistingNode(variableValue);
return isExistingNode ? variableValue : this.getNodeId(defaultAlias).toPromise();
}
async isExistingNode(nodeId: string): Promise<boolean> {
let isExistingNode = false;
if (nodeId) {
try {
isExistingNode = await this.getNodeId(nodeId).pipe(mapTo(true)).toPromise();
} catch (error) {
this.logService.error(error);
}
}
return isExistingNode;
}
private getNodeId(nodeId: string, relativePath?: string): Observable<string> {
let opts: any;
if (relativePath) {
opts = { relativePath };
}
return from(this.nodesApi.getNode(nodeId, opts)).pipe(
map((nodeEntry: NodeEntry) => nodeEntry.entry.id),
catchError((error) => {
this.sourceNodeNotFound = true;
return this.handleError(error);
})
);
}
private openContentNodeDialog(data: ContentNodeSelectorComponentData, currentPanelClass: string, chosenWidth: string) {