5 changed files with 247 additions and 14 deletions
-
3package.json
-
52src/App.vue
-
195src/components/ServiceConfiguration.vue
-
10src/utils/ApiClient.js
-
1vue.config.js
@ -1,27 +1,55 @@ |
|||
<template> |
|||
<a-layout class="h-full"> |
|||
<a-layout-sider> |
|||
<a-menu class="h-full" |
|||
:items="menuItems" |
|||
@click="actionMenuItemClick" |
|||
></a-menu> |
|||
<a-menu class="h-full" :items="menuItems" @click="actionMenuItemClick"></a-menu> |
|||
</a-layout-sider> |
|||
<a-layout> |
|||
<a-layout-content> |
|||
<router-view /> |
|||
<service-configuration :service-key="activeServiceKey"></service-configuration> |
|||
</a-layout-content> |
|||
</a-layout> |
|||
</a-layout> |
|||
<a-modal :open="isGuest" :closable="false" title="操作认证"> |
|||
<a-input-password v-model:value="password" /> |
|||
<template #footer> |
|||
<a-button type="primary" @click="actionVerifyPassword">验证</a-button> |
|||
</template> |
|||
</a-modal> |
|||
</template> |
|||
<script setup> |
|||
import { useRouter } from 'vue-router' |
|||
const router = useRouter(); |
|||
const menuItems = [ |
|||
{key: 'feeder', label: '进出料', path:'feeder'}, |
|||
{key: 'tube-pre-process', label : '样本预处理', path:'tube-pre-process'}, |
|||
]; |
|||
import { onMounted, ref } from 'vue'; |
|||
import ApiClient from '@/utils/ApiClient'; |
|||
import ServiceConfiguration from './components/ServiceConfiguration.vue'; |
|||
// service menu items |
|||
const menuItems = ref([]); |
|||
/** @var {string} */ |
|||
const activeServiceKey = ref(null); |
|||
/** @var {Boolean} */ |
|||
const isGuest = ref(true); |
|||
/** @var {String} */ |
|||
const password = ref(''); |
|||
// on mounted |
|||
onMounted(mounted); |
|||
|
|||
// on mounted |
|||
async function mounted() { |
|||
menuItems.value = []; |
|||
let client = ApiClient.getClient(); |
|||
let services = await client.call('service-config/service-list'); |
|||
for ( let item of services ) { |
|||
menuItems.value.push({id:item.key, key:item.key, label:item.name}); |
|||
} |
|||
} |
|||
|
|||
// handle menu item click |
|||
function actionMenuItemClick( event ) { |
|||
router.push({name:event.item.path}); |
|||
activeServiceKey.value = event.item.id; |
|||
} |
|||
|
|||
// verify passoed |
|||
function actionVerifyPassword() { |
|||
if ( 'zwsdzwsd' === password.value ) { |
|||
isGuest.value = false; |
|||
} |
|||
} |
|||
</script> |
@ -0,0 +1,195 @@ |
|||
<template> |
|||
<div class="h-full flex flex-col"> |
|||
<div class="bg-white border-b p-5"> |
|||
<div v-for="(status,index) in statuses" :key="index" class="inline-block py-1 px-2 rounded border ml-1"> |
|||
{{ status.name }} : {{ status.value }} |
|||
</div> |
|||
</div> |
|||
<a-row class="h-0 grow"> |
|||
<a-col class="border-r h-full overflow-y-auto" :span="16"> |
|||
<div class="p-5 border-t border-b" v-if="0 < params.length"> |
|||
<fieldset class="border my-1" v-for="group in params" :key="group.name"> |
|||
<legend>{{ group.name }}</legend> |
|||
<div class="p-1 inline-block w-64" v-for="item in group.items" :key="item.key"> |
|||
<a-input v-model:value="item.value" :prefix="`${item.name} : `" /> |
|||
</div> |
|||
</fieldset> |
|||
<div class="p-1"> |
|||
<a-button class="mr-1" @click="actionServiceParamReload">刷新</a-button> |
|||
<a-button @click="actionServiceParamSave">保存</a-button> |
|||
</div> |
|||
</div> |
|||
<div class="p-5"> |
|||
<fieldset v-for="(group,groupIndex) in actions" :key="groupIndex" class="border my-1 p-1"> |
|||
<legend>{{ group.name }}</legend> |
|||
<div v-for="action in group.items" :key="action.key"> |
|||
<a-button v-if="0 === action.params.length" class="my-1" |
|||
:loading="action.isExecuting" |
|||
@click="actionServiceExecute(action)" |
|||
>{{ action.name }}</a-button> |
|||
<div v-else class="border rounded-md my-1 px-3 bg-white"> |
|||
<span>{{ action.name }}</span> |
|||
<div class="inline-block mx-2" v-for="actionParam in action.params" :key="actionParam.key"> |
|||
{{ actionParam.name }} : |
|||
<a-switch v-if="'java.lang.Boolean' === actionParam.type" v-model:checked="actionParam.value" /> |
|||
<a-input v-else-if="'java.lang.String' === actionParam.type" class="w-24" v-model:value="actionParam.value" /> |
|||
<a-input-number v-else-if="'java.lang.Integer' === actionParam.type" class="w-24" v-model:value="actionParam.value" /> |
|||
<a-select v-else-if="'Enum' === actionParam.type" v-model:value="actionParam.value" :dropdownMatchSelectWidth="false"> |
|||
<a-select-option v-for="(enumItem,enumIndex) in actionParam.options" :key="enumIndex" :value="enumItem.value">{{ enumItem.name }}</a-select-option> |
|||
</a-select> |
|||
<span v-else>{{ actionParam }}</span> |
|||
</div> |
|||
<a-button class="m-1" :loading="action.isExecuting" @click="actionServiceExecute(action)">执行</a-button> |
|||
</div> |
|||
</div> |
|||
</fieldset> |
|||
</div> |
|||
</a-col> |
|||
<a-col :span="8" class="p-5 h-full"> |
|||
<div class="border rounded p-5 whitespace-pre h-full overflow-y-auto bg-white" |
|||
>{{ logContent }}</div> |
|||
</a-col> |
|||
</a-row> |
|||
</div> |
|||
</template> |
|||
<script setup> |
|||
import { onUnmounted, ref, watch } from 'vue'; |
|||
import ApiClient from '@/utils/ApiClient'; |
|||
/** @var {Object} */ |
|||
const props = defineProps({ |
|||
serviceKey : String, |
|||
}); |
|||
/** @var {Array} */ |
|||
const params = ref([]); |
|||
/** @var {Array} */ |
|||
const actions = ref([]); |
|||
/** @var {Array} */ |
|||
const statuses = ref([]); |
|||
/** @var {String} */ |
|||
const logContent = ref(''); |
|||
/** @var {Integer} */ |
|||
let statusRefreshTimer = null; |
|||
// watch service key |
|||
watch(() => props.serviceKey, handleServiceKeyChange); |
|||
// on unmounted |
|||
onUnmounted(() => { |
|||
if ( null !== statusRefreshTimer ) { |
|||
clearTimeout(statusRefreshTimer); |
|||
statusRefreshTimer = false; |
|||
} |
|||
}); |
|||
|
|||
// on mounted |
|||
async function handleServiceKeyChange() { |
|||
logContent.value = ''; |
|||
if ( null !== statusRefreshTimer ) { |
|||
clearTimeout(statusRefreshTimer); |
|||
statusRefreshTimer = null; |
|||
} |
|||
if ( null === props.serviceKey ) { |
|||
return ; |
|||
} |
|||
|
|||
await actionServiceParamReload(); |
|||
await serviceActionReload(); |
|||
await refreshServiceStatusList(); |
|||
} |
|||
|
|||
// refresh service status list |
|||
async function refreshServiceStatusList() { |
|||
try { |
|||
let client = ApiClient.getClient(); |
|||
statuses.value = await client.call('service-config/service-status-list', {serviceKey:props.serviceKey}); |
|||
if ( false !== statusRefreshTimer ) { |
|||
statusRefreshTimer = setTimeout(refreshServiceStatusList, 500); |
|||
} |
|||
} catch ( e ) {/** nothing to do here */} |
|||
} |
|||
|
|||
// service param reload |
|||
async function actionServiceParamReload() { |
|||
try { |
|||
params.value = []; |
|||
let client = ApiClient.getClient(); |
|||
let list = await client.call('service-config/service-params-list', {serviceKey:props.serviceKey}); |
|||
for ( var item of list ) { |
|||
let groupName = item.group; |
|||
let group = params.value.find( i => i.name === groupName); |
|||
if ( undefined === group ) { |
|||
group = {name:groupName, items:[]}; |
|||
params.value.push(group); |
|||
} |
|||
group.items.push(item); |
|||
} |
|||
params.value.sort((a,b) => a.name.localeCompare(b.name)); |
|||
} catch ( e ) {/** nothing to do here */} |
|||
} |
|||
|
|||
// service param save |
|||
async function actionServiceParamSave() { |
|||
try { |
|||
let values = {}; |
|||
for ( let group of params.value ) { |
|||
for ( let item of group.items ) { |
|||
values[item.key] = item.value; |
|||
} |
|||
} |
|||
let client = ApiClient.getClient(); |
|||
await client.call('service-config/service-params-update', {serviceKey:props.serviceKey,params:values}); |
|||
await actionServiceParamReload(); |
|||
} catch ( e ) {/** nothing to do here */} |
|||
} |
|||
|
|||
// service actions reload |
|||
async function serviceActionReload() { |
|||
try { |
|||
actions.value = []; |
|||
let client = ApiClient.getClient(); |
|||
let list = await client.call('service-config/service-action-list', {serviceKey:props.serviceKey}); |
|||
for ( let item of list ) { |
|||
let group = actions.value.find(i => i.name === item.group); |
|||
if ( undefined === group ) { |
|||
group = {name:item.group, items:[]}; |
|||
actions.value.push(group); |
|||
} |
|||
group.items.push(item); |
|||
} |
|||
actions.value.sort((a,b) => a.name.localeCompare(b.name)); |
|||
} catch ( e ) {/** nothing to do here */} |
|||
} |
|||
|
|||
// service action execute |
|||
async function actionServiceExecute(action) { |
|||
try { |
|||
let client = ApiClient.getClient(); |
|||
let params = {}; |
|||
params.serviceKey = props.serviceKey; |
|||
params.action = action.key; |
|||
params.params = []; |
|||
params.paramTypes = []; |
|||
for ( let item of action.params ) { |
|||
params.params.push(item.value); |
|||
let type = item.type; |
|||
if ( 'Enum' === type ) { |
|||
type = item.typeEnum; |
|||
} |
|||
params.paramTypes.push(type); |
|||
} |
|||
|
|||
var log = []; |
|||
log.push(`Execute : ${params.action}`); |
|||
log.push(''); |
|||
log.push(`Params : `); |
|||
log.push(JSON.stringify(params.params, null, 2)); |
|||
log.push(''); |
|||
|
|||
logContent.value = log.join("\n"); |
|||
action.isExecuting = true; |
|||
let res = await client.call('service-config/service-action-exec',params); |
|||
action.isExecuting = false; |
|||
log.push('Result : '); |
|||
log.push(JSON.stringify(res, null, 2)); |
|||
logContent.value = log.join("\n"); |
|||
} catch ( e ) {/** nothing to do here */} |
|||
} |
|||
</script> |
@ -1,6 +1,7 @@ |
|||
const { defineConfig } = require('@vue/cli-service') |
|||
module.exports = defineConfig({ |
|||
transpileDependencies: true, |
|||
publicPath : './', |
|||
configureWebpack : { |
|||
devtool:"source-map" |
|||
}, |
|||
|
Write
Preview
Loading…
Cancel
Save
Reference in new issue