Handle expanded state

This commit is contained in:
Nora
2023-01-09 15:01:57 +00:00
parent 29c29f0b77
commit c4df8bf7b2
4 changed files with 190 additions and 10 deletions

View File

@@ -9,7 +9,6 @@ import {
SelectedDbItem, SelectedDbItem,
SelectedDbItemKind, SelectedDbItemKind,
} from "./db-config"; } from "./db-config";
import * as lodash from "lodash";
import * as chokidar from "chokidar"; import * as chokidar from "chokidar";
import { DisposableObject, DisposeHandler } from "../../pure/disposable-object"; import { DisposableObject, DisposeHandler } from "../../pure/disposable-object";
import { DbConfigValidator } from "./db-config-validator"; import { DbConfigValidator } from "./db-config-validator";
@@ -27,7 +26,10 @@ import {
DbItem, DbItem,
DbItemKind, DbItemKind,
} from "../db-item"; } from "../db-item";
import { mapDbItemToSelectedDbItem } from "../db-item-selection"; import {
compareSelectedKindIsEqual,
mapDbItemToSelectedDbItem,
} from "../db-item-selection";
export class DbConfigStore extends DisposableObject { export class DbConfigStore extends DisposableObject {
public readonly onDidChangeConfig: AppEvent<void>; public readonly onDidChangeConfig: AppEvent<void>;
@@ -98,7 +100,7 @@ export class DbConfigStore extends DisposableObject {
throw Error("Cannot remove item if config is not loaded"); throw Error("Cannot remove item if config is not loaded");
} }
const config: DbConfig = cloneDbConfig(this.config); const config = cloneDbConfig(this.config);
const selectedItem: SelectedDbItem | undefined = config.selected; const selectedItem: SelectedDbItem | undefined = config.selected;
// Remove item from databases // Remove item from databases
@@ -115,7 +117,7 @@ export class DbConfigStore extends DisposableObject {
); );
break; break;
case DbItemKind.LocalDatabase: case DbItemKind.LocalDatabase:
// TODO: Remove databases from Disk once implemented // When we start using local databases these need to be removed from disk as well.
if (dbItem.parentListName) { if (dbItem.parentListName) {
const parent = config.databases.local.lists.find( const parent = config.databases.local.lists.find(
(list) => list.name === dbItem.parentListName, (list) => list.name === dbItem.parentListName,
@@ -162,12 +164,11 @@ export class DbConfigStore extends DisposableObject {
// Remove item from selected // Remove item from selected
const removedItem = mapDbItemToSelectedDbItem(dbItem); const removedItem = mapDbItemToSelectedDbItem(dbItem);
if (selectedItem) { if (selectedItem && removedItem) {
// if removedItem has a parentList, check if parentList is selectedItem // if removedItem has a parentList, check if parentList is selectedItem
if ( if (
removedItem && removedItem.kind === SelectedDbItemKind.LocalUserDefinedList ||
(removedItem.kind === SelectedDbItemKind.LocalUserDefinedList || removedItem.kind === SelectedDbItemKind.RemoteUserDefinedList
removedItem.kind === SelectedDbItemKind.RemoteUserDefinedList)
) { ) {
if ( if (
(selectedItem.kind === SelectedDbItemKind.LocalDatabase || (selectedItem.kind === SelectedDbItemKind.LocalDatabase ||
@@ -176,7 +177,8 @@ export class DbConfigStore extends DisposableObject {
) { ) {
config.selected = undefined; config.selected = undefined;
} }
} else if (lodash.isEqual(removedItem, selectedItem)) { }
if (compareSelectedKindIsEqual(removedItem, selectedItem)) {
config.selected = undefined; config.selected = undefined;
} }
} }

View File

@@ -1,5 +1,12 @@
import { DbItem, DbItemKind, LocalDbItem, RemoteDbItem } from "./db-item"; import { DbItem, DbItemKind, LocalDbItem, RemoteDbItem } from "./db-item";
import { SelectedDbItem, SelectedDbItemKind } from "./config/db-config"; import {
SelectedDbItem,
SelectedDbItemKind,
SelectedLocalDatabase,
SelectedLocalUserDefinedList,
SelectedRemoteOwner,
SelectedRemoteRepository,
} from "./config/db-config";
export function getSelectedDbItem(dbItems: DbItem[]): DbItem | undefined { export function getSelectedDbItem(dbItems: DbItem[]): DbItem | undefined {
for (const dbItem of dbItems) { for (const dbItem of dbItems) {
@@ -92,3 +99,39 @@ export function mapDbItemToSelectedDbItem(
}; };
} }
} }
export function compareSelectedKindIsEqual(
item1: SelectedDbItem,
item2: SelectedDbItem,
): boolean {
if (item1.kind === item2.kind) {
switch (item1.kind) {
case SelectedDbItemKind.LocalUserDefinedList:
case SelectedDbItemKind.RemoteUserDefinedList:
case SelectedDbItemKind.RemoteSystemDefinedList:
return (
item1.listName === (item2 as SelectedLocalUserDefinedList).listName
);
case SelectedDbItemKind.RemoteOwner:
return item1.ownerName === (item2 as SelectedRemoteOwner).ownerName;
case SelectedDbItemKind.LocalDatabase: {
const selectedItem = item2 as SelectedLocalDatabase;
return (
item1.databaseName === selectedItem.databaseName &&
item1.listName === selectedItem.listName
);
}
case SelectedDbItemKind.RemoteRepository: {
const selectedItem = item2 as SelectedRemoteRepository;
return (
item1.repositoryName === selectedItem.repositoryName &&
item1.listName === selectedItem.listName
);
}
default:
return false;
}
} else {
return false;
}
}

View File

@@ -77,6 +77,10 @@ export class DbManager {
public async removeDbItem(dbItem: DbItem): Promise<void> { public async removeDbItem(dbItem: DbItem): Promise<void> {
await this.dbConfigStore.removeDbItem(dbItem); await this.dbConfigStore.removeDbItem(dbItem);
// Updating the expanded items takes care of cleaning up
// any non-existent items.
await this.updateExpandedItems(this.getExpandedItems());
} }
public async updateDbItemExpandedState( public async updateDbItemExpandedState(

View File

@@ -13,6 +13,8 @@ import {
import { import {
createLocalDatabaseDbItem, createLocalDatabaseDbItem,
createLocalListDbItem, createLocalListDbItem,
createRemoteOwnerDbItem,
createRemoteRepoDbItem,
createRemoteUserDefinedListDbItem, createRemoteUserDefinedListDbItem,
} from "../../../factories/db-item-factories"; } from "../../../factories/db-item-factories";
import { createMockApp } from "../../../__mocks__/appMock"; import { createMockApp } from "../../../__mocks__/appMock";
@@ -365,4 +367,133 @@ describe("db config store", () => {
configStore.dispose(); configStore.dispose();
}); });
}); });
describe("db and list deletion", () => {
let app: App;
let configPath: string;
beforeEach(async () => {
app = createMockApp({
extensionPath,
workspaceStoragePath: tempWorkspaceStoragePath,
});
configPath = join(tempWorkspaceStoragePath, "workspace-databases.json");
});
it("should remove a single db item", async () => {
// Initial set up
const dbConfig = createDbConfig({
remoteOwners: ["owner1", "owner2"],
selected: {
kind: SelectedDbItemKind.RemoteOwner,
ownerName: "owner1",
},
});
await writeJSON(configPath, dbConfig);
const configStore = new DbConfigStore(app);
await configStore.initialize();
// Remove
const currentDbItem = createRemoteOwnerDbItem({
ownerName: "owner1",
});
await configStore.removeDbItem(currentDbItem);
// Read the config file
const updatedDbConfig = (await readJSON(configPath)) as DbConfig;
// Check that the config file has been updated
const updatedRemoteDbs = updatedDbConfig.databases.remote;
expect(updatedRemoteDbs.owners).toHaveLength(1);
expect(updatedRemoteDbs.owners[0]).toEqual("owner2");
expect(updatedDbConfig.selected).toEqual(undefined);
configStore.dispose();
});
it("should remove a list db item", async () => {
// Initial set up
const dbConfig = createDbConfig({
remoteLists: [
{
name: "list1",
repositories: ["owner/repo1", "owner/repo2"],
},
],
selected: {
kind: SelectedDbItemKind.RemoteUserDefinedList,
listName: "list1",
},
});
await writeJSON(configPath, dbConfig);
const configStore = new DbConfigStore(app);
await configStore.initialize();
// Remove
const currentDbItem = createRemoteUserDefinedListDbItem({
listName: "list1",
});
await configStore.removeDbItem(currentDbItem);
// Read the config file
const updatedDbConfig = (await readJSON(configPath)) as DbConfig;
// Check that the config file has been updated
const updatedRemoteDbs = updatedDbConfig.databases.remote;
expect(updatedRemoteDbs.repositoryLists).toHaveLength(0);
expect(updatedDbConfig.selected).toEqual(undefined);
configStore.dispose();
});
it("should remove a db item in a list", async () => {
// Initial set up
const dbConfig = createDbConfig({
remoteLists: [
{
name: "list1",
repositories: ["owner/repo1", "owner/repo2"],
},
],
selected: {
kind: SelectedDbItemKind.RemoteRepository,
repositoryName: "owner/repo1",
listName: "list1",
},
});
await writeJSON(configPath, dbConfig);
const configStore = new DbConfigStore(app);
await configStore.initialize();
// Remove
const currentDbItem = createRemoteRepoDbItem({
repoFullName: "owner/repo1",
parentListName: "list1",
});
await configStore.removeDbItem(currentDbItem);
// Read the config file
const updatedDbConfig = (await readJSON(configPath)) as DbConfig;
// Check that the config file has been updated
const updatedRemoteDbs = updatedDbConfig.databases.remote;
expect(updatedRemoteDbs.repositoryLists[0].repositories).toHaveLength(1);
expect(updatedRemoteDbs.repositoryLists[0].repositories[0]).toEqual(
"owner/repo2",
);
expect(updatedDbConfig.selected).toEqual(undefined);
configStore.dispose();
});
});
}); });