!39 feat: 表和schema超出20条后启用模糊高亮过滤

Merge pull request !39 from zongyangleo/dev_20230213_1
This commit is contained in:
Coder慌
2023-02-14 06:36:41 +00:00
committed by Gitee
3 changed files with 96 additions and 31 deletions

View File

@@ -4,6 +4,8 @@
"scripts": {
"dev": "vite",
"build": "vite build",
"preview": "vite preview",
"build-preview": "npm run build && npm run preview",
"lint-fix": "eslint --fix --ext .js --ext .jsx --ext .vue src/"
},
"dependencies": {

View File

@@ -266,7 +266,8 @@ const registerSqlCompletionItemProvider = () => {
// 如果是.触发代码提示,则进行【 库.表名联想 】 或 【 表别名.表字段联想 】
let str = lastToken.substring(0, lastToken.lastIndexOf('.'))
// 库.表名联想
if (dbs.indexOf(str) > -1) {
if (dbs.filter((a:any)=>a.name === str)?.length > 0) {
let tables = await dbInst.loadTables(str)
let suggestions: languages.CompletionItem[] = []
for (let item of tables) {
@@ -294,7 +295,7 @@ const registerSqlCompletionItemProvider = () => {
let dbHits = await dbInst.loadDbHints(db)
let columns = dbHits[table]
let suggestions: languages.CompletionItem[] = []
columns.forEach((a: string, index: any) => {
columns?.forEach((a: string, index: any) => {
// 字段数据格式 字段名 字段注释, 如: create_time [datetime][创建时间]
const nameAndComment = a.split(" ")
const fieldName = nameAndComment[0]
@@ -368,14 +369,14 @@ const registerSqlCompletionItemProvider = () => {
})
// 库名提示
dbs.forEach((a: string) => {
dbs.forEach((a: any) => {
suggestions.push({
label: {
label: a,
label: a.name,
description: 'schema'
},
kind: monaco.languages.CompletionItemKind.Folder,
insertText: a,
insertText: a.name,
range
});
})

View File

@@ -23,62 +23,73 @@
</template>
</el-popover>
</template>
<el-menu-item v-if="dbs[inst.id]?.length> 20" :index="'schema-filter-' + inst.id" :key="'schema-filter-' + inst.id">
<template #title>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
<el-input size="small" placeholder="过滤数据库" clearable
@change="filterSchemaName(inst.id)"
@keyup="(e: any) => filterSchemaName(inst.id, e)"
v-model="state.schemaFilterParam[inst.id]" />
</template>
</el-menu-item>
<!-- 第三级数据库 -->
<el-sub-menu v-for="schema in dbs[inst.id]" :index="inst.id + schema" :key="inst.id + schema"
:class="state.nowSchema === (inst.id + schema) && 'checked'"
@click.stop="changeSchema(inst, schema)">
<el-sub-menu v-show="schema.show" v-for="schema in dbs[inst.id]" :index="inst.id + schema.name" :key="inst.id + schema.name"
:class="state.nowSchema === (inst.id + schema.name) && 'checked'"
@click.stop="changeSchema(inst, schema.name)">
<template #title>
<span class="checked-schema ml20">
<el-icon>
<Coin color="#67c23a" />
</el-icon>{{ schema }}</span>
</el-icon>
<span v-html="schema.showName || schema.name"></span>
</span>
</template>
<!-- 第四级 01 -->
<el-sub-menu :index="inst.id + schema + '-table'">
<el-sub-menu :index="inst.id + schema.name + '-table'">
<template #title>
<div class="ml30" style="width: 100%" @click="loadSchemaTables(inst, schema)">
<div class="ml30" style="width: 100%" @click="loadSchemaTables(inst, schema.name)">
<el-icon>
<Calendar color="#409eff" />
</el-icon>
<span></span>
<el-icon v-show="state.loading[inst.id + schema]" class="is-loading">
<el-icon v-show="state.loading[inst.id + schema.name]" class="is-loading">
<Loading />
</el-icon>
</div>
</template>
<el-menu-item :index="inst.id + schema + '-tableSearch'"
:key="inst.id + schema + '-tableSearch'">
<el-menu-item v-if="tables[inst.id + schema.name]?.length> 20" :index="inst.id + schema.name + '-tableSearch'"
:key="inst.id + schema.name + '-tableSearch'">
<template #title>
<span class="ml35">
<el-input size="small" placeholder="表名、备注过滤表" clearable
@change="filterTableName(inst.id, schema)"
@keyup="(e: any) => filterTableName(inst.id, schema, e)"
v-model="state.filterParam[inst.id + schema]" />
@change="filterTableName(inst.id, schema.name)"
@keyup="(e: any) => filterTableName(inst.id, schema.name, e)"
v-model="state.filterParam[inst.id + schema.name]" />
</span>
</template>
</el-menu-item>
<template v-for="tb in tables[inst.id + schema]">
<el-menu-item :index="inst.id + schema + tb.tableName"
:key="inst.id + schema + tb.tableName" v-if="tb.show"
@click="clickSchemaTable(inst, schema, tb.tableName)">
<template v-for="tb in tables[inst.id + schema.name]">
<el-menu-item :index="inst.id + schema.name + tb.tableName"
:key="inst.id + schema.name + tb.tableName" v-if="tb.show"
@click="clickSchemaTable(inst, schema.name, tb.tableName)">
<template #title>
<div class="ml35" style="width: 100%">
<el-icon>
<Calendar color="#409eff" />
</el-icon>
<el-tooltip v-if="tb.tableComment" effect="customized"
:content="tb.tableComment" placement="right">
{{ tb.tableName }}
:content="tb.tableComment" placement="right" >
<span v-html="tb.showName || tb.tableName"></span>
</el-tooltip>
<span v-else>{{ tb.tableName }}</span>
<span v-else v-html="tb.showName || tb.tableName"></span>
</div>
</template>
</el-menu-item>
</template>
</el-sub-menu>
<!-- 第四级 02sql -->
<el-sub-menu @click.stop="loadSqls(inst, schema)" :index="inst.id + schema + '-sql'">
<el-sub-menu @click.stop="loadSqls(inst, schema.name)" :index="inst.id + schema.name + '-sql'">
<template #title>
<span class="ml30">
<el-icon>
@@ -88,9 +99,9 @@
</span>
</template>
<template v-for="sql in sqls[inst.id + schema]">
<el-menu-item v-if="sql.show" :index="inst.id + schema + sql.name"
:key="inst.id + schema + sql.name" @click="clickSqlName(inst, schema, sql.name)">
<template v-for="sql in sqls[inst.id + schema.name]">
<el-menu-item v-if="sql.show" :index="inst.id + schema.name + sql.name"
:key="inst.id + schema.name + sql.name" @click="clickSqlName(inst, schema.name, sql.name)">
<template #title>
<div class="ml35" style="width: 100%">
<el-icon>
@@ -129,6 +140,7 @@ const state = reactive({
sqls: {},
nowSchema: '',
filterParam: {},
schemaFilterParam: {},
loading: {},
instanceMenuMaxHeight: '850px',
})
@@ -158,7 +170,10 @@ const loadInstances = async () => {
state.tree[db.tagId] = arr;
// dbs
state.dbs[db.id] = db.database.split(' ')
let databases = db.database.split(' ')
let dbs = [] as any [];
databases.forEach((a: string) =>dbs.push({name: a, show: true}))
state.dbs[db.id] = dbs
}
}
@@ -215,12 +230,59 @@ const filterTableName = (instId: number, schema: string, event?: any) => {
state.filterParam[key] = event.target.value
}
let param = state.filterParam[key] as string
param = param?.replace('/', '\/')
state.tables[key].forEach((a: any) => {
a.show = param ? eval('/' + param.split('').join('[_\w]*') + '[_\w]*/ig').test(a.tableName) || eval('/' + param.split('').join('[_\w]*') + '[_\w]*/ig').test(a.tableComment) : true
let {match, showName} = matchAndHighLight(param, a.tableName+a.tableComment, a.tableName)
a.show = match;
a.showName = showName
})
}
const filterSchemaName = (instId: number, event?: any) => {
if (event) {
state.schemaFilterParam[instId] = event.target.value
}
let param = state.schemaFilterParam[instId] as string
param = param?.replace('/', '\/')
state.dbs[instId].forEach((a: any) => {
let {match, showName} = matchAndHighLight(param, a.name, a.name)
a.show = match
a.showName = showName
})
}
const matchAndHighLight = (searchParam: string, param: string, title: string): {match: boolean, showName: string} => {
if(!searchParam){
return {match: true, showName: ''}
}
let str = '';
for(let c of searchParam?.replace('/', '\/')){
str += `(${c}).*`
}
let regex = eval(`/${str}/i`)
let res = param.match(regex);
if(res?.length){
if(res?.length){
let tmp = '', showName = '';
for(let i =1; i<=res.length-1; i++){
let head = (tmp || title).replace(res[i], `###${res[i]}!!!`);
let idx = head.lastIndexOf('!!!')+3;
tmp = head.substring(idx);
showName += head.substring(0, idx)
if(!tmp){
break
}
}
showName += tmp;
showName = showName.replaceAll('###','<span style="color: red">')
showName = showName.replaceAll('!!!','</span>')
return {match: true, showName}
}
}
return {match: false, showName: ''}
}
/**
* 加载用户保存的sql脚本
*