1
1
mirror of https://github.com/Fabio286/antares.git synced 2025-06-05 21:59:22 +02:00

feat(UI): run procedures/functions from sidebar context menu

This commit is contained in:
2021-02-25 17:43:23 +01:00
parent 7e8167154f
commit 219da0aba4
2 changed files with 130 additions and 17 deletions

View File

@ -562,7 +562,7 @@ export class MySQLClient extends AntaresCore {
return { return {
name: param[1] ? param[1].replaceAll('`', '') : '', name: param[1] ? param[1].replaceAll('`', '') : '',
type: type[0].replaceAll('\n', ''), type: type[0].replaceAll('\n', ''),
length: +type[1].replace(/\D/g, ''), length: +type[1] ? +type[1].replace(/\D/g, '') : '',
context: param[0] ? param[0].replace('\n', '') : '' context: param[0] ? param[0].replace('\n', '') : ''
}; };
}).filter(el => el.name); }).filter(el => el.name);
@ -578,7 +578,7 @@ export class MySQLClient extends AntaresCore {
return { return {
definer: row['Create Procedure'].match(/(?<=DEFINER=).*?(?=\s)/gs)[0], definer: row['Create Procedure'].match(/(?<=DEFINER=).*?(?=\s)/gs)[0],
sql: row['Create Procedure'].match(/(BEGIN|begin)(.*)(END|end)/gs)[0], sql: row['Create Procedure'].match(/(BEGIN|begin)(.*)(END|end)/gs)[0],
parameters, parameters: parameters || [],
name: row.Procedure, name: row.Procedure,
comment: row['Create Procedure'].match(/(?<=COMMENT ').*?(?=')/gs) ? row['Create Procedure'].match(/(?<=COMMENT ').*?(?=')/gs)[0] : '', comment: row['Create Procedure'].match(/(?<=COMMENT ').*?(?=')/gs) ? row['Create Procedure'].match(/(?<=COMMENT ').*?(?=')/gs)[0] : '',
security: row['Create Procedure'].includes('SQL SECURITY INVOKER') ? 'INVOKER' : 'DEFINER', security: row['Create Procedure'].includes('SQL SECURITY INVOKER') ? 'INVOKER' : 'DEFINER',
@ -628,10 +628,12 @@ export class MySQLClient extends AntaresCore {
* @memberof MySQLClient * @memberof MySQLClient
*/ */
async createRoutine (routine) { async createRoutine (routine) {
const parameters = routine.parameters.reduce((acc, curr) => { const parameters = 'parameters' in routine
acc.push(`${curr.context} \`${curr.name}\` ${curr.type}${curr.length ? `(${curr.length})` : ''}`); ? routine.parameters.reduce((acc, curr) => {
return acc; acc.push(`${curr.context} \`${curr.name}\` ${curr.type}${curr.length ? `(${curr.length})` : ''}`);
}, []).join(','); return acc;
}, []).join(',')
: '';
const sql = `CREATE ${routine.definer ? `DEFINER=${routine.definer} ` : ''}PROCEDURE \`${routine.name}\`(${parameters}) const sql = `CREATE ${routine.definer ? `DEFINER=${routine.definer} ` : ''}PROCEDURE \`${routine.name}\`(${parameters})
LANGUAGE SQL LANGUAGE SQL
@ -683,7 +685,7 @@ export class MySQLClient extends AntaresCore {
return { return {
name: param[0] ? param[0].replaceAll('`', '') : '', name: param[0] ? param[0].replaceAll('`', '') : '',
type: type[0], type: type[0],
length: +type[1].replace(/\D/g, '') length: +type[1] ? +type[1].replace(/\D/g, '') : ''
}; };
}).filter(el => el.name); }).filter(el => el.name);
@ -700,7 +702,7 @@ export class MySQLClient extends AntaresCore {
return { return {
definer: row['Create Function'].match(/(?<=DEFINER=).*?(?=\s)/gs)[0], definer: row['Create Function'].match(/(?<=DEFINER=).*?(?=\s)/gs)[0],
sql: row['Create Function'].match(/(BEGIN|begin)(.*)(END|end)/gs)[0], sql: row['Create Function'].match(/(BEGIN|begin)(.*)(END|end)/gs)[0],
parameters, parameters: parameters || [],
name: row.Function, name: row.Function,
comment: row['Create Function'].match(/(?<=COMMENT ').*?(?=')/gs) ? row['Create Function'].match(/(?<=COMMENT ').*?(?=')/gs)[0] : '', comment: row['Create Function'].match(/(?<=COMMENT ').*?(?=')/gs) ? row['Create Function'].match(/(?<=COMMENT ').*?(?=')/gs)[0] : '',
security: row['Create Function'].includes('SQL SECURITY INVOKER') ? 'INVOKER' : 'DEFINER', security: row['Create Function'].includes('SQL SECURITY INVOKER') ? 'INVOKER' : 'DEFINER',

View File

@ -5,8 +5,8 @@
> >
<div <div
v-if="['procedure', 'function'].includes(selectedMisc.type)" v-if="['procedure', 'function'].includes(selectedMisc.type)"
class="context-element disabled" class="context-element"
@click="showRunModal" @click="runElementCheck"
> >
<span class="d-flex"><i class="mdi mdi-18px mdi-play text-light pr-1" /> {{ $t('word.run') }}</span> <span class="d-flex"><i class="mdi mdi-18px mdi-play text-light pr-1" /> {{ $t('word.run') }}</span>
</div> </div>
@ -29,6 +29,12 @@
</div> </div>
</div> </div>
</ConfirmModal> </ConfirmModal>
<ModalAskParameters
v-if="isAskingParameters"
:local-routine="localElement"
@confirm="runElement"
@close="hideAskParamsModal"
/>
</BaseContextMenu> </BaseContextMenu>
</template> </template>
@ -36,6 +42,7 @@
import { mapGetters, mapActions } from 'vuex'; import { mapGetters, mapActions } from 'vuex';
import BaseContextMenu from '@/components/BaseContextMenu'; import BaseContextMenu from '@/components/BaseContextMenu';
import ConfirmModal from '@/components/BaseConfirmModal'; import ConfirmModal from '@/components/BaseConfirmModal';
import ModalAskParameters from '@/components/ModalAskParameters';
import Triggers from '@/ipc-api/Triggers'; import Triggers from '@/ipc-api/Triggers';
import Routines from '@/ipc-api/Routines'; import Routines from '@/ipc-api/Routines';
import Functions from '@/ipc-api/Functions'; import Functions from '@/ipc-api/Functions';
@ -45,7 +52,8 @@ export default {
name: 'WorkspaceExploreBarMiscContext', name: 'WorkspaceExploreBarMiscContext',
components: { components: {
BaseContextMenu, BaseContextMenu,
ConfirmModal ConfirmModal,
ModalAskParameters
}, },
props: { props: {
contextEvent: MouseEvent, contextEvent: MouseEvent,
@ -54,7 +62,9 @@ export default {
data () { data () {
return { return {
isDeleteModal: false, isDeleteModal: false,
isRunModal: false isRunModal: false,
isAskingParameters: false,
localElement: {}
}; };
}, },
computed: { computed: {
@ -83,7 +93,8 @@ export default {
methods: { methods: {
...mapActions({ ...mapActions({
addNotification: 'notifications/addNotification', addNotification: 'notifications/addNotification',
changeBreadcrumbs: 'workspaces/changeBreadcrumbs' changeBreadcrumbs: 'workspaces/changeBreadcrumbs',
newTab: 'workspaces/newTab'
}), }),
showCreateTableModal () { showCreateTableModal () {
this.$emit('show-create-table-modal'); this.$emit('show-create-table-modal');
@ -94,11 +105,12 @@ export default {
hideDeleteModal () { hideDeleteModal () {
this.isDeleteModal = false; this.isDeleteModal = false;
}, },
showRunModal () { showAskParamsModal () {
this.isRunModal = true; this.isAskingParameters = true;
}, },
hideRunModal () { hideAskParamsModal () {
this.isRunModal = false; this.isAskingParameters = false;
this.closeContext();
}, },
closeContext () { closeContext () {
this.$emit('close-context'); this.$emit('close-context');
@ -148,6 +160,105 @@ export default {
catch (err) { catch (err) {
this.addNotification({ status: 'error', message: err.stack }); this.addNotification({ status: 'error', message: err.stack });
} }
},
runElementCheck () {
if (this.selectedMisc.type === 'procedure')
this.runRoutineCheck();
else if (this.selectedMisc.type === 'function')
this.runFunctionCheck();
},
runElement (params) {
if (this.selectedMisc.type === 'procedure')
this.runRoutine(params);
else if (this.selectedMisc.type === 'function')
this.runFunction(params);
},
async runRoutineCheck () {
const params = {
uid: this.selectedWorkspace,
schema: this.workspace.breadcrumbs.schema,
routine: this.workspace.breadcrumbs.procedure
};
try {
const { status, response } = await Routines.getRoutineInformations(params);
if (status === 'success')
this.localElement = response;
else
this.addNotification({ status: 'error', message: response });
}
catch (err) {
this.addNotification({ status: 'error', message: err.stack });
}
if (this.localElement.parameters.length)
this.showAskParamsModal();
else
this.runRoutine();
},
runRoutine (params) {
if (!params) params = [];
let sql;
switch (this.workspace.client) { // TODO: move in a better place
case 'maria':
case 'mysql':
case 'pg':
sql = `CALL \`${this.localElement.name}\` (${params.join(',')})`;
break;
case 'mssql':
sql = `EXEC ${this.localElement.name} ${params.join(',')}`;
break;
default:
sql = `CALL \`${this.localElement.name}\` (${params.join(',')})`;
}
this.newTab({ uid: this.workspace.uid, content: sql, autorun: true });
this.closeContext();
},
async runFunctionCheck () {
const params = {
uid: this.selectedWorkspace,
schema: this.workspace.breadcrumbs.schema,
func: this.workspace.breadcrumbs.function
};
try {
const { status, response } = await Functions.getFunctionInformations(params);
if (status === 'success')
this.localElement = response;
else
this.addNotification({ status: 'error', message: response });
}
catch (err) {
this.addNotification({ status: 'error', message: err.stack });
}
if (this.localElement.parameters.length)
this.showAskParamsModal();
else
this.runFunction();
},
runFunction (params) {
if (!params) params = [];
let sql;
switch (this.workspace.client) { // TODO: move in a better place
case 'maria':
case 'mysql':
case 'pg':
sql = `SELECT \`${this.localElement.name}\` (${params.join(',')})`;
break;
case 'mssql':
sql = `SELECT ${this.localElement.name} ${params.join(',')}`;
break;
default:
sql = `SELECT \`${this.localElement.name}\` (${params.join(',')})`;
}
this.newTab({ uid: this.workspace.uid, content: sql, autorun: true });
this.closeContext();
} }
} }
}; };