delete functionality implemented

This commit is contained in:
sumedh
2024-08-08 10:34:54 +05:30
parent ec5c382c3d
commit 4c54153dc8
5 changed files with 155 additions and 147 deletions

View File

@@ -55,7 +55,7 @@ function copyToClipboard() {
/* Enable positioning of child elements */
}
.class="button-container" {
.button-container {
position: sticky;
top: 10px;
/* Adjust as needed */

View File

@@ -2,7 +2,7 @@
<div className="card">
<DataTable v-model:filters="filters" :value="ksdocuments" paginator showGridlines :rows="10" dataKey="id"
filterDisplay="menu" :loading="loading"
:globalFilterFields="['name', 'fileName', 'ingestionStatus', 'ingestionDateFormat']">
:globalFilterFields="['ingestionInfo.metadata.KsApplicationName', 'ingestionInfo.metadata.KsFileSources', 'ingestionInfo.metadata.KsDocSource', 'ingestionStatus', 'ingestionDateFormat']">
<template #header>
<div class="flex items-center justify-between gap-4 p-4 ">
<span class="text-xl font-bold">KS Documents</span>
@@ -23,25 +23,39 @@
</template>
<template #empty>No Records found</template>
<template #loading>Loading Data. Please wait....</template>
<Column field="id" header="ksdocuments id" sortable style="min-width: 12rem" />
<Column field="ingestionInfo.id" header="ksingestioninfo id" sortable style="min-width: 12rem" />
<Column field="name" header="Name" sortable style="min-width: 12rem">
<Column field="id" header="id" sortable style="min-width: 12rem">
<template #body="slotProps">
<Tag>ksdocuments: {{ slotProps.data.id }}</Tag>
<Tag>ksingestioninfo: {{ slotProps.data.ingestionInfo.id }}</Tag>
</template>
</Column>
<!--Column field="ingestionInfo.id" header="ksingestioninfo id" sortable style="min-width: 12rem" /-->
<Column field="ingestionInfo.metadata.KsApplicationName" header="KSApplicationName" sortable
style="min-width: 12rem">
<template #body="{ data }">
{{ data.name }}
{{ data.ingestionInfo.metadata.KsApplicationName }}
</template>
<template #filter="{ filterModel, filterCallback }">
<InputText v-model="filterModel.value" type="text" @input="filterCallback()" placeholder="Search by File" />
</template>
</Column>
<Column field="fileName" header="File Name" sortable>
<Column field="ingestionInfo.metadata.KsFileSource" header="KsFileSource" sortable>
<template #body="{ data }">
{{ data.fileName }}
{{ data.ingestionInfo.metadata.KsFileSource }}
</template>
<template #filter="{ filterModel, filterCallback }">
<InputText v-model="filterModel.value" type="text" @input="filterCallback()"
placeholder="Search by File Name" />
</template>
</Column>
<Column field="ingestionInfo.metadata.KsDocSource" header="KsDocSource" sortable style="min-width: 12rem">
<template #body="{ data }">
{{ data.ingestionInfo.metadata.KsDocSource }}
</template>
<template #filter="{ filterModel, filterCallback }">
<InputText v-model="filterModel.value" type="text" @input="filterCallback()" placeholder="Search by File" />
</template>
</Column>
<Column field="ingestionStatus" header="Status" sortable>
<template #body="slotProps">
<Tag :value="slotProps.data.ingestionStatus" :severity="getStatus(slotProps.data)" />
@@ -69,13 +83,21 @@
<div class="flex justify-center items-center">
<Button type="button" icon="pi pi-pencil" rounded @click="editKsDocument(slotProps.data)"
v-tooltip="'Edit the information of document'" class="mr-4" />
<!--Tag :value="slotProps.data.id" /-->
<!--Tag :value="slotProps.data.ingestionInfo.id" /-->
<!--Button type="button" v-if="slotProps.data.ingestionStatus === 'NEW'" icon="pi pi-play" rounded
@click="startIndividualngestion(slotProps.data.id)" v-tooltip="'Start Ingestion of document'" class="mr-4" /-->
<Button type="button" icon="pi pi-play" rounded @click="startIndividualngestion(slotProps.data.id)"
v-tooltip="'Start Ingestion of document'" :disabled="slotProps.data.ingestionStatus === 'INGESTED'"
:class="{ 'p-button-danger': slotProps.data.ingestionStatus === 'INGESTED' }" class="mr-7" />
<Button type="button" icon="pi pi-trash" rounded @click="showConfirmDialog(slotProps.data.id)"
v-tooltip="'Delete the ingested Record'" :disabled="slotProps.data.ingestionStatus === 'NEW'"
:class="{ 'p-button-danger': slotProps.data.ingestionStatus === 'NEW' }" class="mr-7" />
<Dialog header="Confirm Deletion" :visible="confirmDialogVisible" modal @hide="resetConfirmDialog"
:style="{ width: '300px' }">
<p>Are you sure you want to delete this record?</p>
<template #footer>
<Button label="No" icon="pi pi-times" @click="confirmDialogVisible = false" class="p-button-text" />
<Button label="Yes" icon="pi pi-check" @click="confirmDelete" class="p-button-danger" />
</template>
</Dialog>
</div>
</template>
</Column>
@@ -113,12 +135,16 @@ const ingestionDialogVisible = ref(false);
const ingestionResult = ref('');
const filters = ref();
const confirmDialogVisible = ref(false);
const recordToDelete = ref(null);
const initFilters = () => {
filters.value = {
global: { value: null, matchMode: FilterMatchMode.CONTAINS },
id: { operator: FilterOperator.AND, constraints: [{ value: null, matchMode: FilterMatchMode.EQUALS }] },
name: { operator: FilterOperator.AND, constraints: [{ value: null, matchMode: FilterMatchMode.STARTS_WITH }] },
fileName: { operator: FilterOperator.AND, constraints: [{ value: null, matchMode: FilterMatchMode.STARTS_WITH }] },
'ingestionInfo.metadata.KsApplicationName': { operator: FilterOperator.AND, constraints: [{ value: null, matchMode: FilterMatchMode.STARTS_WITH }] },
'ingestionInfo.metadata.KsFileSource': { operator: FilterOperator.AND, constraints: [{ value: null, matchMode: FilterMatchMode.STARTS_WITH }] },
'ingestionInfo.metadata.KsDocSource': { operator: FilterOperator.AND, constraints: [{ value: null, matchMode: FilterMatchMode.STARTS_WITH }] },
ingestionDateFormat: { operator: FilterOperator.AND, constraints: [{ value: null, matchMode: FilterMatchMode.DATE_IS }] },
ingestionStatus: { operator: FilterOperator.OR, constraints: [{ value: null, matchMode: FilterMatchMode.EQUALS }] }
};
@@ -169,6 +195,53 @@ const editKsDocument = (data) => {
router.push({ name: 'ks-document-edit', params: { id: data.id } });
}
//delete functionality
function showConfirmDialog(id) {
recordToDelete.value = id;
confirmDialogVisible.value = true;
}
function confirmDelete() {
if (recordToDelete.value !== null) {
deleteRecordsFromVectorStore(recordToDelete.value);
recordToDelete.value = null;
}
confirmDialogVisible.value = false;
}
function resetConfirmDialog() {
recordToDelete.value = null;
}
const deleteRecordsFromVectorStore = (id) => {
const documentToDelete = ksdocuments.value.find(doc => doc.id === id);
if (!documentToDelete) {
console.error('Document not found');
return;
}
const requestPayload = {
ksDocumentId: id,
ksIngestionInfoId: documentToDelete.ingestionInfo.id,
ksDoctype: documentToDelete.ingestionInfo.metadata.KsDoctype,
ksDocSource: documentToDelete.ingestionInfo.metadata.KsDocSource,
ksFileSource: documentToDelete.ingestionInfo.metadata.KsFileSource,
ksApplicationName: documentToDelete.ingestionInfo.metadata.KsApplicationName,
};
axios.post('http://localhost:8082/fe-api/vector-store/deleteRecords', requestPayload)
.then(response => {
console.log('Delete resource:', response.data)
ksdocuments.value = ksdocuments.value.filter(doc => doc.id !== id);
})
.catch(error => {
console.error('Error deleting records: ', error)
});
}
//ingestion
const startIndividualngestion = (id) => {
axios.get(`http://localhost:8082/test/ingest_document/${id}`)
//axios.get('http://localhost:8082/test/ingestion_loop')
@@ -212,6 +285,7 @@ const startlngestion = () => {
});
};
//new record creation
const newKsDocument = () => {
console.log('new');
router.push({ name: 'ks-document-new' });

View File

@@ -8,71 +8,81 @@
<form @submit.prevent="submitForm" class="p-fluid">
<div class="lex flex-col md:flex-row gap-4">
<div class="flex flex-wrap gap-2 w-full">
<label for="description">Description</label>
<label for="description" v-tooltip="'A brief overview of the system purpose and functionality.'">System
Description</label>
<InputText id="description" type="text" v-model="formData.description" required class="w-full" />
</div>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="type">Type</label>
<label for="type"
v-tooltip="'Specify the type of file here. e.g, PDF Document, DOCX, TXT, MD Document etc..'">File
Type</label>
<InputText id="type" v-model="formData.type" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="ksApplicationName">KS Application Name</label>
<label for="ksApplicationName" v-tooltip="'Enter the application name here.'">KS Application Name</label>
<InputText id="ksApplicationName" v-model="formData.ksApplicationName" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="ksDocType">KS Doc Type</label>
<label for="ksDocType" v-tooltip="'Specify the type of document e.g, md, pdf,'">KS Document Type</label>
<InputText id="ksDocType" v-model="formData.ksDocType" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="ksDocSource">KS Doc Source</label>
<label for="ksDocSource"
v-tooltip="'The KS Document Source field is intended to capture the origin or source from where the document was obtained or associated. ex.. Retrieved from DevopsJ2Cloud Git Repository - CSV System Configuration '">KS
Document Source</label>
<InputText id="ksDocSource" v-model="formData.ksDocSource" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="defaultChunkSize">Default Chunk Size</label>
<label for="defaultChunkSize" v-tooltip="'Define the default size for chunks of data.'">Default Chunk
Size</label>
<InputNumber id="defaultChunkSize" v-model="formData.defaultChunkSize" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="minChunkSize">Min Chunk Size</label>
<label for="minChunkSize" v-tooltip="'Specify the minimum allowable size for chunks'">Min Chunk
Size</label>
<InputNumber id="minChunkSize" v-model="formData.minChunkSize" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="maxNumberOfChunks">Max Number of Chunks</label>
<label for="maxNumberOfChunks" v-tooltip="'Set the maximum number of chunks allowed.'">Max Number of
Chunks</label>
<InputNumber id="maxNumberOfChunks" v-model="formData.maxNumberOfChunks" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="minChunkSizeToEmbed">Min Chunk Size to Embed</label>
<label for="minChunkSizeToEmbed" v-tooltip="'Define the minimum chunk size that can be embedded.'">Min
Chunk Size to
Embed</label>
<InputNumber id="minChunkSizeToEmbed" v-model="formData.minChunkSizeToEmbed" required class="w-full" />
</span>
</div>
<div class="col-12 mb-4">
<label for="file" class="block text-lg mb-2">File</label>
<label for="file" class="block text-lg mb-2" v-tooltip="'Upload the file here.'">File</label>
<div class="flex align-items-center">
<FileUpload ref="fileUpload" mode="basic" :maxFileSize="10000000" chooseLabel="Select File"
<FileUpload ref="fileUpload" mode="basic" :maxFileSize="10000000000" chooseLabel="Select File"
class="p-button-rounded" @select="onFileSelect" />
</div>
</div>
@@ -81,81 +91,6 @@
</div>
</div>
</Fluid>
<!--div class="card-container">
<form @submit.prevent="submitForm" class="p-fluid">
<div class="grid">
<div class="col-12 mb-4">
<label for="file" class="block text-lg mb-2">File</label>
<div class="flex align-items-center">
<FileUpload
ref="fileUpload"
mode="basic"
:maxFileSize="10000000"
chooseLabel="Select File"
class="p-button-rounded"
@select="onFileSelect"
/>
</div>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="description">Description</label>
<InputText id="description" v-model="formData.description" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="type">Type</label>
<InputText id="type" v-model="formData.type" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="ksApplicationName">KS Application Name</label>
<InputText id="ksApplicationName" v-model="formData.ksApplicationName" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="ksDocType">KS Doc Type</label>
<InputText id="ksDocType" v-model="formData.ksDocType" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="ksDocSource">KS Doc Source</label>
<InputText id="ksDocSource" v-model="formData.ksDocSource" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="defaultChunkSize">Default Chunk Size</label>
<InputNumber id="defaultChunkSize" v-model="formData.defaultChunkSize" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="minChunkSize">Min Chunk Size</label>
<InputNumber id="minChunkSize" v-model="formData.minChunkSize" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="maxNumberOfChunks">Max Number of Chunks</label>
<InputNumber id="maxNumberOfChunks" v-model="formData.maxNumberOfChunks" required class="w-full" />
</span>
</div>
<div class="col-12 md:col-6 mb-4">
<span class="p-float-label">
<label for="minChunkSizeToEmbed">Min Chunk Size to Embed</label>
<InputNumber id="minChunkSizeToEmbed" v-model="formData.minChunkSizeToEmbed" required class="w-full" />
</span>
</div>
</div>
<Button type="submit" label="Submit" class="p-button-rounded p-button-lg" />
</form>
</div-->
</template>
<script setup>
@@ -163,17 +98,18 @@ import axios from 'axios';
import { useToast } from 'primevue/usetoast';
import { ref } from 'vue';
import { useRouter } from 'vue-router';
import Tooltip from 'primevue/tooltip';
const toast = useToast();
const router = useRouter();
const formData = ref({
description: 'Test-UI-DevopsJ2CSystem',
description: 'Jenkins DevopsJ2Cloud System CSV configuration md file',
ingestionStatus: 'NEW',
type: 'MD_DOCUMENT',
ksApplicationName: 'jenkins',
ksDocType: 'setup-documentation',
ksDocSource: 'guide-for-techincal-setup',
type: '.md file',
ksApplicationName: 'Jenkins-DevopsJ2Cloud',
ksDocType: 'md',
ksDocSource: 'Git Repository - DevopsJ2Cloud CSV System Configuration',
defaultChunkSize: 1000,
minChunkSize: 200,
maxNumberOfChunks: 1000,

View File

@@ -2,31 +2,27 @@
<Fluid>
<h2 class="text-4xl font-semibold text-center mb-4">Similarity Search</h2>
<div class="similarity-search">
<div v-if="messages.length > 0" class="results-container mt-6">
<Card v-for="(result, index) in messages" :key="index" class="result-card">
<template #content>
<ScrollPanel style="width: 100%; max-height: 400px">
<CodeSnippet :code="dynamicCode" language="systemd" />
</ScrollPanel>
</template>
</Card>
</div>
<div class="card-container flex flex-col gap-6">
<div class="flex flex-col gap-4">
<Textarea id="query" v-model="query" rows="6" placeholder="Enter your query..." class="input-textarea" />
<div class="select-container">
<SelectButton
id="type"
v-model="dropdownItem"
:options="dropdownItems"
optionLabel="name"
class="select-button"
/>
</div>
<div class="card-container flex flex-col gap-6">
<div class="flex flex-col gap-4">
<Textarea id="query" v-model="query" rows="6" placeholder="Enter your query..." class="input-textarea" />
<div class="select-container">
<!--SelectButton id="type" v-model="dropdownItem" :options="dropdownItems" optionLabel="name"
class="select-button" /-->
<InputText v-model="filterQuery" type="text" placeholder="Add filterQuery" />
</div>
<Button label="Send" icon="pi pi-send" @click="sendQuery" class="send-button" />
</div>
<Button label="Query" icon="pi pi-send" @click="sendQuery" class="send-button" />
</div>
<div v-if="messages.length > 0" class="results-container mt-6">
<Card v-for="(result, index) in messages" :key="index" class="result-card">
<template #content>
<ScrollPanel style="width: 100%; max-height: 400px">
<CodeSnippet :code="dynamicCode" language="systemd" />
</ScrollPanel>
</template>
</Card>
</div>
</div>
</Fluid>
</template>
@@ -45,6 +41,7 @@ const dropdownItem = ref(null);
const messages = ref([]);
const toast = useToast();
const dynamicCode = ref('');
const filterQuery = ref("'KsApplicationName' == 'atf'")
const dropdownItems = [
{ name: 'Documentation', code: 'setup-documentation' },
@@ -53,9 +50,9 @@ const dropdownItems = [
];
const sendQuery = async () => {
if (query.value.trim() !== '' && dropdownItem.value) {
if (query.value.trim() !== '' && filterQuery) {
try {
const response = await fetch(`http://localhost:8082/test/query_vector?query="${query.value}"&type=${dropdownItem.value.code}`);
const response = await fetch(`http://localhost:8082/test/query_vector?query="${query.value}"&filterQuery=${filterQuery.value}`);
const data = await response.json();
console.log('API response:', data);
@@ -69,8 +66,8 @@ const sendQuery = async () => {
console.error('Error sending query:', error);
toast.add({ severity: 'error', summary: 'Error', detail: 'Failed to send query', life: 3000 });
}
query.value = '';
dropdownItem.value = null;
//query.value = '';
//dropdownItem.value = null;
} else {
toast.add({ severity: 'warn', summary: 'Warning', detail: 'Please enter a query and select a type', life: 3000 });
}
@@ -104,7 +101,8 @@ watch(messages, (newMessages) => {
.input-textarea {
width: 100%;
resize: vertical;
min-height: 150px; /* Increased height for better readability */
min-height: 150px;
/* Increased height for better readability */
border-radius: 8px;
padding: 1rem;
border: 1px solid #ccc;

View File

@@ -2,7 +2,7 @@
<div className="card">
<DataTable v-model:filters="filters" :value="vectorDetails" dataKey="id" :loading="loading" paginator showGridlines
:rows="10" filterDisplay="menu"
:globalFilterFields="['id', 'metadata.ksApplicationName', 'metadata.ksDocSource', 'metadata.ksDoctype', 'metadata.source']">
:globalFilterFields="['id', 'metadata.ksApplicationName', 'metadata.ksDocSource', 'metadata.ksDoctype', 'metadata.ksFileSource']">
<template #header>
<div class="flex items-center justify-between gap-4 p-4 ">
<span class="text-xl font-bold">Vector Data</span>
@@ -26,7 +26,7 @@
<InputText v-model="filterModel.value" type="text" @input="filterCallback()" placeholder="Search By id" />
</template>
</Column>
<Column field="metadata.ksApplicationName" header="ksApplicationName" sortable>
<Column field="metadata.ksApplicationName" header="KsApplicationName" sortable>
<template #body="{ data }">
{{ data.metadata.ksApplicationName }}
</template>
@@ -35,7 +35,16 @@
placeholder="Search By Application name" />
</template>
</Column>
<Column field="metadata.ksDocSource" header="ksDocSource" sortable>
<Column field="metadata.ksFileSource" header="KsFileSource" sortable>
<template #body="{ data }">
{{ data.metadata.ksFileSource }}
</template>
<template #filter="{ filterModel, filterCallback }">
<InputText v-model="filterModel.value" type="text" @input="filterCallback()"
placeholder="Search By Source/Path" />
</template>
</Column>
<Column field="metadata.ksDocSource" header="KsDocSource" sortable>
<template #body="{ data }">
{{ data.metadata.ksDocSource }}
</template>
@@ -44,7 +53,7 @@
placeholder="Search By Document/Repo source" />
</template>
</Column>
<Column field="metadata.ksDoctype" header="ksDoctype" sortable>
<Column field="metadata.ksDoctype" header="KsDoctype" sortable>
<template #body="{ data }">
{{ data.metadata.ksDoctype }}
</template>
@@ -53,15 +62,6 @@
placeholder="Search By Document/Source type" />
</template>
</Column>
<Column field="metadata.source" header="source" sortable>
<template #body="{ data }">
{{ data.metadata.source }}
</template>
<template #filter="{ filterModel, filterCallback }">
<InputText v-model="filterModel.value" type="text" @input="filterCallback()"
placeholder="Search By Source/Path" />
</template>
</Column>
</DataTable>
</div>
</template>
@@ -90,7 +90,7 @@ const initFilters = () => {
'metadata.ksApplicationName': { operator: FilterOperator.AND, constraints: [{ value: null, matchMode: FilterMatchMode.STARTS_WITH }] },
'metadata.ksDocSource': { operator: FilterOperator.AND, constraints: [{ value: null, matchMode: FilterMatchMode.STARTS_WITH }] },
'metadata.ksDoctype': { operator: FilterOperator.AND, constraints: [{ value: null, matchMode: FilterMatchMode.STARTS_WITH }] },
'metadata.source': { operator: FilterOperator.AND, constraints: [{ value: null, matchMode: FilterMatchMode.STARTS_WITH }] }
'metadata.ksFileSource': { operator: FilterOperator.AND, constraints: [{ value: null, matchMode: FilterMatchMode.STARTS_WITH }] }
};
};