From a5436544d6b4561a472b161177758ad1e421fef9 Mon Sep 17 00:00:00 2001 From: SeanLeRoy Date: Thu, 14 Nov 2024 12:10:19 -0800 Subject: [PATCH 1/3] Prevent duplicate loading of same description source --- .../core/services/DatabaseService/index.ts | 21 +++++++++++++++---- packages/core/state/selection/logics.ts | 4 ++++ 2 files changed, 21 insertions(+), 4 deletions(-) diff --git a/packages/core/services/DatabaseService/index.ts b/packages/core/services/DatabaseService/index.ts index ec6d82c7..2c089473 100644 --- a/packages/core/services/DatabaseService/index.ts +++ b/packages/core/services/DatabaseService/index.ts @@ -30,6 +30,7 @@ export default abstract class DatabaseService { ...Object.values(AnnotationType), DatabaseService.OPEN_FILE_LINK_TYPE, ]); + private sourceMetadataName?: string; private currentAggregateSource?: string; // Initialize with AICS FMS data source name to pretend it always exists protected readonly existingDataSources = new Set([AICS_FMS_DATA_SOURCE_NAME]); @@ -140,11 +141,12 @@ export default abstract class DatabaseService { } public async prepareSourceMetadata(sourceMetadata: Source): Promise { - if (sourceMetadata.type && sourceMetadata.uri) { - this.deleteDataSource(this.SOURCE_METADATA_TABLE); - this.dataSourceToAnnotationsMap.clear(); + const isOldSource = sourceMetadata.name === this.sourceMetadataName; + if (isOldSource) { + return; } + await this.deleteSourceMetadata(); await this.prepareDataSource( { ...sourceMetadata, @@ -152,6 +154,12 @@ export default abstract class DatabaseService { }, true ); + this.sourceMetadataName = sourceMetadata.name; + } + + public async deleteSourceMetadata(): Promise { + await this.deleteDataSource(this.SOURCE_METADATA_TABLE); + this.dataSourceToAnnotationsMap.clear(); } protected async deleteDataSource(dataSource: string): Promise { @@ -456,7 +464,12 @@ export default abstract class DatabaseService { public async fetchAnnotations(dataSourceNames: string[]): Promise { const aggregateDataSourceName = dataSourceNames.sort().join(", "); - if (!this.dataSourceToAnnotationsMap.has(aggregateDataSourceName)) { + const hasAnnotations = this.dataSourceToAnnotationsMap.has(aggregateDataSourceName); + const hasDescriptions = this.dataSourceToAnnotationsMap + .get(aggregateDataSourceName) + ?.some((annotation) => !!annotation.description); + const shouldHaveDescriptions = dataSourceNames.includes(this.SOURCE_METADATA_TABLE); + if (!hasAnnotations || (!hasDescriptions && shouldHaveDescriptions)) { const sql = new SQLBuilder() .select("column_name, data_type") .from('information_schema"."columns') diff --git a/packages/core/state/selection/logics.ts b/packages/core/state/selection/logics.ts index 710f446d..c9caaf23 100644 --- a/packages/core/state/selection/logics.ts +++ b/packages/core/state/selection/logics.ts @@ -555,6 +555,8 @@ const changeSourceMetadataLogic = createLogic({ ); if (selectedSourceMetadata) { await databaseService.prepareSourceMetadata(selectedSourceMetadata); + } else { + await databaseService.deleteSourceMetadata(); } dispatch(metadata.actions.requestAnnotations()); @@ -577,6 +579,8 @@ const addQueryLogic = createLogic({ await databaseService.prepareDataSources(newQuery.parts.sources); if (newQuery.parts.sourceMetadata) { await databaseService.prepareSourceMetadata(newQuery.parts.sourceMetadata); + } else { + await databaseService.deleteSourceMetadata(); } // Hide warning pop-up if present and remove datasource error from state dispatch(removeDataSourceReloadError()); From 7b3ab5eb6ba6b30f61fa3d9720d50f4654891084 Mon Sep 17 00:00:00 2001 From: SeanLeRoy Date: Thu, 14 Nov 2024 12:22:25 -0800 Subject: [PATCH 2/3] Ensure change data source is called --- .../services/DatabaseService/DatabaseServiceNoop.ts | 4 ++++ packages/core/state/selection/test/logics.test.ts | 13 +++++++++++++ 2 files changed, 17 insertions(+) diff --git a/packages/core/services/DatabaseService/DatabaseServiceNoop.ts b/packages/core/services/DatabaseService/DatabaseServiceNoop.ts index eb604500..f4e24e5c 100644 --- a/packages/core/services/DatabaseService/DatabaseServiceNoop.ts +++ b/packages/core/services/DatabaseService/DatabaseServiceNoop.ts @@ -1,6 +1,10 @@ import DatabaseService from "."; export default class DatabaseServiceNoop extends DatabaseService { + public deleteSourceMetadata(): Promise { + return Promise.reject("DatabaseServiceNoop:deleteSourceMetadata"); + } + public execute(): Promise { return Promise.reject("DatabaseServiceNoop:execute"); } diff --git a/packages/core/state/selection/test/logics.test.ts b/packages/core/state/selection/test/logics.test.ts index 662ff2b0..edb8a941 100644 --- a/packages/core/state/selection/test/logics.test.ts +++ b/packages/core/state/selection/test/logics.test.ts @@ -24,6 +24,7 @@ import { selectNearbyFile, SET_SORT_COLUMN, changeDataSources, + changeSourceMetadata, } from "../actions"; import { initialState, interaction } from "../../"; import Annotation from "../../../entity/Annotation"; @@ -40,6 +41,7 @@ import FileSort, { SortOrder } from "../../../entity/FileSort"; import { DatasetService } from "../../../services"; import { DataSource } from "../../../services/DataSourceService"; import HttpFileService from "../../../services/FileService/HttpFileService"; +import DatabaseServiceNoop from "../../../services/DatabaseService/DatabaseServiceNoop"; import FileDownloadServiceNoop from "../../../services/FileDownloadService/FileDownloadServiceNoop"; describe("Selection logics", () => { @@ -947,7 +949,17 @@ describe("Selection logics", () => { it("dispatches new hierarchy, filters, sort, source, & opened folders from given URL", async () => { // Arrange const annotations = annotationsJson.map((annotation) => new Annotation(annotation)); + class MockDatabaseService extends DatabaseServiceNoop { + public deleteSourceMetadata(): Promise { + return Promise.resolve(); + } + } const state = mergeState(initialState, { + interaction: { + platformDependentServices: { + databaseService: new MockDatabaseService(), + }, + }, metadata: { annotations, dataSources: mockDataSources, @@ -998,6 +1010,7 @@ describe("Selection logics", () => { payload: sortColumn, }) ).to.be.true; + expect(actions.includesMatch(changeSourceMetadata())).to.be.true; expect(actions.includesMatch(changeDataSources(mockDataSources))).to.be.true; }); }); From be80cb288de708db25e48365706b053de09ccdcd Mon Sep 17 00:00:00 2001 From: SeanLeRoy Date: Thu, 14 Nov 2024 14:04:30 -0800 Subject: [PATCH 3/3] Rename variable --- packages/core/services/DatabaseService/index.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/core/services/DatabaseService/index.ts b/packages/core/services/DatabaseService/index.ts index 2c089473..b001b840 100644 --- a/packages/core/services/DatabaseService/index.ts +++ b/packages/core/services/DatabaseService/index.ts @@ -141,8 +141,8 @@ export default abstract class DatabaseService { } public async prepareSourceMetadata(sourceMetadata: Source): Promise { - const isOldSource = sourceMetadata.name === this.sourceMetadataName; - if (isOldSource) { + const isPreviousSource = sourceMetadata.name === this.sourceMetadataName; + if (isPreviousSource) { return; }