Skip to content

Commit

Permalink
Improved commenting. Removed unused functions. Tree data more concise.
Browse files Browse the repository at this point in the history
  • Loading branch information
kyle1morel committed Nov 17, 2023
1 parent 86fcec3 commit c45cd10
Show file tree
Hide file tree
Showing 5 changed files with 40 additions and 65 deletions.
70 changes: 34 additions & 36 deletions frontend/src/components/bucket/BucketTable.vue
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import { joinPath } from '@/utils/utils';
import type { TreeTableExpandedKeys } from 'primevue/treetable';
import type { Ref } from 'vue';
import type { Bucket, BucketTreeNode, BucketTreeNodeDummyData } from '@/types';
import type { Bucket, BucketTreeNode } from '@/types';
// Store
const bucketStore = useBucketStore();
Expand All @@ -23,10 +23,10 @@ const { getBuckets } = storeToRefs(bucketStore);
// State
const expandedKeys: Ref<TreeTableExpandedKeys> = ref({});
const treeData: Ref<Array<any>> = ref([]);
const permissionsVisible: Ref<boolean> = ref(false);
const permissionsBucketId: Ref<string> = ref('');
const permissionBucketName: Ref<string> = ref('');
const treeData: Ref<Array<BucketTreeNode>> = ref([]);
const emit = defineEmits(['show-bucket-config', 'show-sidebar-info']);
Expand Down Expand Up @@ -67,28 +67,22 @@ async function deleteBucket(bucketId: string) {
await bucketStore.fetchBuckets({ userId: getUserId.value, objectPerms: true });
}
// Returns a full canonical path to a Bucket or fake tree data
function getBucketPath(bucket: Bucket | BucketTreeNodeDummyData): string {
/** Returns a full canonical path to a Bucket or fake tree data */
function getBucketPath(bucket: Bucket): string {
return `${bucket.endpoint}/${bucket.bucket}/${bucket.key}`;
}
// Get the full path to the first part of its key
/** Get the full path to the first part of its key */
function getFirstKeyPartPath(node: BucketTreeNode): string {
const parts = node.data.key.split(DELIMITER).filter((part) => part);
return `${node.data.endpoint}/${node.data.bucket}/${parts[0]}`;
}
// Finds the nearest direct path to node
// Assumes the endpointMap paths have been pre sorted
function findParent(parentPath: string): BucketTreeNode | undefined {
if (bucketTreeNodeMap.has(parentPath)) return bucketTreeNodeMap.get(parentPath);
return undefined;
}
// Finds the nearest indirect path to node
// Assumes the endpointMap paths have been pre sorted
/**
* Finds the nearest indirect path to node \
* Assumes the endpointMap paths have been pre sorted
*/
function findNearestNeighbour(node: BucketTreeNode): BucketTreeNode | undefined {
const prefixParts = getBucketPath(node.data)
.split(DELIMITER)
Expand All @@ -98,24 +92,23 @@ function findNearestNeighbour(node: BucketTreeNode): BucketTreeNode | undefined
let path = joinPath(...prefixParts.slice(0, i));
// Fix broken endpoints caused by delimiter splitting
path = path.replace('http:/', 'http://');
path = path.replace('https:/', 'https://');
path = path.replace(/^https?:\//i, (match) => `${match}/`);
if (bucketTreeNodeMap.has(path)) {
return bucketTreeNodeMap.get(path);
}
}
// Failed to find anything based on key
// Is there a bucket mounted at the root?
if (bucketTreeNodeMap.has(`${node.data.endpoint}/${node.data.bucket}//`))
return bucketTreeNodeMap.get(`${node.data.endpoint}/${node.data.bucket}//`);
return undefined;
// Failed to find anything based on key so check root
// Double // at end required as the key of a bucket is stored as '/'
// Undefined if not found
return bucketTreeNodeMap.get(`${node.data.endpoint}/${node.data.bucket}//`);
}
// Creates the fake paths necessary between neighbour and node to mimic a folder hierarchy
// Returns the final node created
/**
* Creates the fake paths necessary between neighbour and node to mimic a folder hierarchy \
* Returns the final node created
*/
function createDummyNodes(neighbour: BucketTreeNode, node: BucketTreeNode) {
const neighbourParts = getBucketPath(neighbour.data)
.split(DELIMITER)
Expand All @@ -132,17 +125,21 @@ function createDummyNodes(neighbour: BucketTreeNode, node: BucketTreeNode) {
let key = joinPath(...nodeParts.slice(2, i));
// Fix broken endpoints caused by delimiter splitting
fullPath = fullPath.replace('http:/', 'http://');
fullPath = fullPath.replace('https:/', 'https://');
fullPath = fullPath.replace(/^https?:\//i, (match) => `${match}/`);
dummyNodes.push({
key: fullPath,
data: {
accessKeyId: '',
active: false,
bucket: node.data.bucket,
bucketId: '',
bucketName: nodeParts[i - 1],
dummy: true,
endpoint: node.data.endpoint,
key: key
key: key,
region: '',
secretAccessKey: ''
},
children: new Array(),
isRoot: false
Expand Down Expand Up @@ -187,11 +184,11 @@ watch(getBuckets, () => {
for (const row of col[1]) {
const path = getBucketPath(row);
const parentPath = path.substring(0, path.lastIndexOf('/'));
const parent = findParent(parentPath);
const parent = bucketTreeNodeMap.get(parentPath);
const node: BucketTreeNode = {
key: getBucketPath(row),
data: row,
data: { ...row, dummy: false },
children: new Array(),
isRoot: false
};
Expand All @@ -210,11 +207,16 @@ watch(getBuckets, () => {
const dummyRootNode: BucketTreeNode = {
key: rootFullPath,
data: {
accessKeyId: '',
active: false,
bucket: node.data.bucket,
bucketId: '',
bucketName: rootKey,
dummy: true,
endpoint: node.data.endpoint,
key: rootKey
key: rootKey,
region: '',
secretAccessKey: ''
},
children: new Array(),
isRoot: true
Expand All @@ -234,11 +236,7 @@ watch(getBuckets, () => {
}
// Expand all nodes and set tree state
let _expandedKeys = { ...expandedKeys.value };
for (const nodes of bucketTreeNodeMap) {
_expandedKeys[nodes[0]] = true;
}
expandedKeys.value = _expandedKeys;
bucketTreeNodeMap.forEach((_v, k) => (expandedKeys.value[k] = true));
treeData.value = tree;
});
</script>
Expand Down
4 changes: 2 additions & 2 deletions frontend/src/components/bucket/BucketTableBucketName.vue
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ const props = withDefaults(defineProps<Props>(), {});
</script>

<template>
<span v-if="(props.node.data as any).dummy">
<span v-if="props.node.data.dummy">
{{ props.node.data.bucketName }}
<span
v-if="node.isRoot"
Expand All @@ -22,7 +22,7 @@ const props = withDefaults(defineProps<Props>(), {});
</span>
</span>
<span v-else>
<router-link :to="{ name: RouteNames.LIST_OBJECTS, query: { bucketId: (props.node.data as any).bucketId } }">
<router-link :to="{ name: RouteNames.LIST_OBJECTS, query: { bucketId: props.node.data.bucketId } }">
{{ node.data.bucketName }}
</router-link>
<span
Expand Down
10 changes: 3 additions & 7 deletions frontend/src/types/BucketTreeNode.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,11 @@ import type { Bucket } from '@/types';

export type BucketTreeNode = {
key: string;
data: Bucket | BucketTreeNodeDummyData;
data: BucketTreeNodeData;
isRoot: boolean;
children: Array<BucketTreeNode>;
};

export type BucketTreeNodeDummyData = {
bucket: string;
bucketName: string;
export type BucketTreeNodeData = {
dummy: boolean;
endpoint: string;
key: string;
};
} & Bucket;
2 changes: 1 addition & 1 deletion frontend/src/types/index.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
export type { Bucket } from './Bucket';
export type { BucketPermission } from './BucketPermission';
export type { BucketTreeNode, BucketTreeNodeDummyData } from './BucketTreeNode';
export type { BucketTreeNode, BucketTreeNodeData } from './BucketTreeNode';
export type { COMSObject } from './COMSObject';
export type { COMSObjectPermission } from './COMSObjectPermission';
export type { IdentityProvider } from './IdentityProvider';
Expand Down
19 changes: 0 additions & 19 deletions frontend/src/utils/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,25 +13,6 @@ export function differential(source: any, comparer: any): any {
return Object.fromEntries(Object.entries(source).filter(([key, value]) => comparer[key] !== value));
}

/**
* @function isAtPath
* Predicate function determining if the `path` is a non-directory member of the `prefix` path
* @param {string} prefix The base "folder"
* @param {string} path The "file" to check
* @returns {boolean} True if path is member of prefix. False in all other cases.
*/
export function isAtPath(prefix: string, path: string) {
if (prefix === path) return true; // Matching strings are always at the at the path
if (path.endsWith(DELIMITER)) return false; // Trailing slashes references the folder

const pathParts = path.split(DELIMITER).filter((part) => part);
const prefixParts = prefix.split(DELIMITER).filter((part) => part);
return (
prefixParts.every((part, i) => pathParts[i] === part) &&
pathParts.filter((part) => !prefixParts.includes(part)).length === 1
);
}

/**
* @function isDebugMode
* Checks if the app is currently running in debug mode
Expand Down

0 comments on commit c45cd10

Please sign in to comment.