Registry (#7073)
* wip * wip * wip * wip * wip * Update registry.value.vue * wip * wip * wip * wip * typo
This commit is contained in:
parent
1286dee1ab
commit
6c975275f8
37 changed files with 1017 additions and 100 deletions
|
@ -24,6 +24,8 @@
|
|||
<span>{{ $ts._deck.columnMargin }}</span>
|
||||
<template #suffix>px</template>
|
||||
</FormInput>
|
||||
|
||||
<FormLink @click="setProfile">{{ $ts._deck.profile }}<template #suffix>{{ profile }}</template></FormLink>
|
||||
</FormBase>
|
||||
</template>
|
||||
|
||||
|
@ -31,7 +33,7 @@
|
|||
import { defineComponent } from 'vue';
|
||||
import { faImage, faCog, faColumns } from '@fortawesome/free-solid-svg-icons';
|
||||
import FormSwitch from '@/components/form/switch.vue';
|
||||
import FormSelect from '@/components/form/select.vue';
|
||||
import FormLink from '@/components/form/link.vue';
|
||||
import FormRadios from '@/components/form/radios.vue';
|
||||
import FormInput from '@/components/form/input.vue';
|
||||
import FormBase from '@/components/form/base.vue';
|
||||
|
@ -42,7 +44,7 @@ import * as os from '@/os';
|
|||
export default defineComponent({
|
||||
components: {
|
||||
FormSwitch,
|
||||
FormSelect,
|
||||
FormLink,
|
||||
FormInput,
|
||||
FormRadios,
|
||||
FormBase,
|
||||
|
@ -67,6 +69,7 @@ export default defineComponent({
|
|||
columnAlign: deckStore.makeGetterSetter('columnAlign'),
|
||||
columnMargin: deckStore.makeGetterSetter('columnMargin'),
|
||||
columnHeaderHeight: deckStore.makeGetterSetter('columnHeaderHeight'),
|
||||
profile: deckStore.makeGetterSetter('profile'),
|
||||
},
|
||||
|
||||
watch: {
|
||||
|
@ -85,5 +88,19 @@ export default defineComponent({
|
|||
mounted() {
|
||||
this.$emit('info', this.INFO);
|
||||
},
|
||||
|
||||
methods: {
|
||||
async setProfile() {
|
||||
const { canceled, result: name } = await os.dialog({
|
||||
title: this.$ts._deck.profile,
|
||||
input: {
|
||||
allowEmpty: false
|
||||
}
|
||||
});
|
||||
if (canceled) return;
|
||||
this.profile = name;
|
||||
location.reload();
|
||||
}
|
||||
}
|
||||
});
|
||||
</script>
|
||||
|
|
|
@ -35,13 +35,13 @@
|
|||
</FormGroup>
|
||||
</FormBase>
|
||||
<div class="main">
|
||||
<component :is="component" @info="onInfo"/>
|
||||
<component :is="component" :key="page" @info="onInfo" v-bind="pageProps"/>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
import { computed, defineAsyncComponent, defineComponent, nextTick, onMounted, ref, watch } from 'vue';
|
||||
import { computed, defineAsyncComponent, defineComponent, nextTick, onMounted, reactive, ref, watch } from 'vue';
|
||||
import { faCog, faPalette, faPlug, faUser, faListUl, faLock, faCommentSlash, faMusic, faCogs, faEllipsisH, faBan, faShareAlt, faLockOpen, faKey, faBoxes } from '@fortawesome/free-solid-svg-icons';
|
||||
import { faLaugh, faBell, faEnvelope } from '@fortawesome/free-regular-svg-icons';
|
||||
import { i18n } from '@/i18n';
|
||||
|
@ -78,7 +78,9 @@ export default defineComponent({
|
|||
const onInfo = (viewInfo) => {
|
||||
INFO.value = viewInfo;
|
||||
};
|
||||
const pageProps = ref({});
|
||||
const component = computed(() => {
|
||||
if (props.page == null) return null;
|
||||
switch (props.page) {
|
||||
case 'profile': return defineAsyncComponent(() => import('./profile.vue'));
|
||||
case 'privacy': return defineAsyncComponent(() => import('./privacy.vue'));
|
||||
|
@ -104,16 +106,35 @@ export default defineComponent({
|
|||
case 'plugins': return defineAsyncComponent(() => import('./plugins.vue'));
|
||||
case 'import-export': return defineAsyncComponent(() => import('./import-export.vue'));
|
||||
case 'account-info': return defineAsyncComponent(() => import('./account-info.vue'));
|
||||
case 'registry': return defineAsyncComponent(() => import('./registry.vue'));
|
||||
case 'experimental-features': return defineAsyncComponent(() => import('./experimental-features.vue'));
|
||||
default: return null;
|
||||
}
|
||||
if (props.page.startsWith('registry/keys/system/')) {
|
||||
return defineAsyncComponent(() => import('./registry.keys.vue'));
|
||||
}
|
||||
if (props.page.startsWith('registry/value/system/')) {
|
||||
return defineAsyncComponent(() => import('./registry.value.vue'));
|
||||
}
|
||||
});
|
||||
|
||||
watch(component, () => {
|
||||
pageProps.value = {};
|
||||
|
||||
if (props.page) {
|
||||
if (props.page.startsWith('registry/keys/system/')) {
|
||||
pageProps.value.scope = props.page.replace('registry/keys/system/', '').split('/');
|
||||
}
|
||||
if (props.page.startsWith('registry/value/system/')) {
|
||||
const path = props.page.replace('registry/value/system/', '').split('/');
|
||||
pageProps.value.xKey = path.pop();
|
||||
pageProps.value.scope = path;
|
||||
}
|
||||
}
|
||||
|
||||
nextTick(() => {
|
||||
scroll(el.value, 0);
|
||||
});
|
||||
});
|
||||
}, { immediate: true });
|
||||
|
||||
onMounted(() => {
|
||||
narrow.value = el.value.offsetWidth < 1025;
|
||||
|
@ -125,6 +146,7 @@ export default defineComponent({
|
|||
view,
|
||||
el,
|
||||
onInfo,
|
||||
pageProps,
|
||||
component,
|
||||
logout: () => {
|
||||
signout();
|
||||
|
|
|
@ -15,16 +15,17 @@
|
|||
DEBUG MODE
|
||||
</FormSwitch>
|
||||
<template v-if="debug">
|
||||
<FormLink to="/settings/regedit">RegEdit</FormLink>
|
||||
<FormButton @click="taskmanager">Task Manager</FormButton>
|
||||
</template>
|
||||
</FormGroup>
|
||||
|
||||
<FormLink to="/settings/registry"><template #icon><Fa :icon="faCogs"/></template>{{ $ts.registry }}</FormLink>
|
||||
</FormBase>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
import { defineAsyncComponent, defineComponent } from 'vue';
|
||||
import { faEllipsisH } from '@fortawesome/free-solid-svg-icons';
|
||||
import { faEllipsisH, faCogs } from '@fortawesome/free-solid-svg-icons';
|
||||
import FormSwitch from '@/components/form/switch.vue';
|
||||
import FormSelect from '@/components/form/select.vue';
|
||||
import FormLink from '@/components/form/link.vue';
|
||||
|
@ -53,7 +54,8 @@ export default defineComponent({
|
|||
title: this.$ts.other,
|
||||
icon: faEllipsisH
|
||||
},
|
||||
debug
|
||||
debug,
|
||||
faCogs
|
||||
}
|
||||
},
|
||||
|
||||
|
|
115
src/client/pages/settings/registry.keys.vue
Normal file
115
src/client/pages/settings/registry.keys.vue
Normal file
|
@ -0,0 +1,115 @@
|
|||
<template>
|
||||
<FormBase>
|
||||
<FormGroup>
|
||||
<FormKeyValueView>
|
||||
<template #key>{{ $ts._registry.domain }}</template>
|
||||
<template #value>{{ $ts.system }}</template>
|
||||
</FormKeyValueView>
|
||||
<FormKeyValueView>
|
||||
<template #key>{{ $ts._registry.scope }}</template>
|
||||
<template #value>{{ scope.join('/') }}</template>
|
||||
</FormKeyValueView>
|
||||
</FormGroup>
|
||||
|
||||
<FormGroup v-if="keys">
|
||||
<template #label>{{ $ts._registry.keys }}</template>
|
||||
<FormLink v-for="key in keys" :to="`/settings/registry/value/system/${scope.join('/')}/${key[0]}`" class="_monospace">{{ key[0] }}<template #suffix>{{ key[1].toUpperCase() }}</template></FormLink>
|
||||
</FormGroup>
|
||||
|
||||
<FormButton @click="createKey" primary>{{ $ts._registry.createKey }}</FormButton>
|
||||
</FormBase>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
import { defineAsyncComponent, defineComponent } from 'vue';
|
||||
import { faCogs } from '@fortawesome/free-solid-svg-icons';
|
||||
import * as JSON5 from 'json5';
|
||||
import MkInfo from '@/components/ui/info.vue';
|
||||
import FormSwitch from '@/components/form/switch.vue';
|
||||
import FormSelect from '@/components/form/select.vue';
|
||||
import FormLink from '@/components/form/link.vue';
|
||||
import FormBase from '@/components/form/base.vue';
|
||||
import FormGroup from '@/components/form/group.vue';
|
||||
import FormButton from '@/components/form/button.vue';
|
||||
import FormKeyValueView from '@/components/form/key-value-view.vue';
|
||||
import * as os from '@/os';
|
||||
|
||||
export default defineComponent({
|
||||
components: {
|
||||
MkInfo,
|
||||
FormBase,
|
||||
FormSelect,
|
||||
FormSwitch,
|
||||
FormButton,
|
||||
FormLink,
|
||||
FormGroup,
|
||||
FormKeyValueView,
|
||||
},
|
||||
|
||||
props: {
|
||||
scope: {
|
||||
required: true
|
||||
}
|
||||
},
|
||||
|
||||
emits: ['info'],
|
||||
|
||||
data() {
|
||||
return {
|
||||
INFO: {
|
||||
title: this.$ts.registry,
|
||||
icon: faCogs
|
||||
},
|
||||
keys: null,
|
||||
}
|
||||
},
|
||||
|
||||
watch: {
|
||||
scope() {
|
||||
this.fetch();
|
||||
}
|
||||
},
|
||||
|
||||
mounted() {
|
||||
this.$emit('info', this.INFO);
|
||||
this.fetch();
|
||||
},
|
||||
|
||||
methods: {
|
||||
fetch() {
|
||||
os.api('i/registry/keys-with-type', {
|
||||
scope: this.scope
|
||||
}).then(keys => {
|
||||
this.keys = Object.entries(keys).sort((a, b) => a[0].localeCompare(b[0]));
|
||||
});
|
||||
},
|
||||
|
||||
async createKey() {
|
||||
const { canceled, result } = await os.form(this.$ts._registry.createKey, {
|
||||
key: {
|
||||
type: 'string',
|
||||
label: this.$ts._registry.key,
|
||||
},
|
||||
value: {
|
||||
type: 'string',
|
||||
multiline: true,
|
||||
label: this.$ts.value,
|
||||
},
|
||||
scope: {
|
||||
type: 'string',
|
||||
label: this.$ts._registry.scope,
|
||||
default: this.scope.join('/')
|
||||
}
|
||||
});
|
||||
if (canceled) return;
|
||||
os.apiWithDialog('i/registry/set', {
|
||||
scope: result.scope.split('/'),
|
||||
key: result.key,
|
||||
value: JSON5.parse(result.value),
|
||||
}).then(() => {
|
||||
this.fetch();
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
</script>
|
149
src/client/pages/settings/registry.value.vue
Normal file
149
src/client/pages/settings/registry.value.vue
Normal file
|
@ -0,0 +1,149 @@
|
|||
<template>
|
||||
<FormBase>
|
||||
<MkInfo warn>{{ $ts.editTheseSettingsMayBreakAccount }}</MkInfo>
|
||||
|
||||
<template v-if="value">
|
||||
<FormGroup>
|
||||
<FormKeyValueView>
|
||||
<template #key>{{ $ts._registry.domain }}</template>
|
||||
<template #value>{{ $ts.system }}</template>
|
||||
</FormKeyValueView>
|
||||
<FormKeyValueView>
|
||||
<template #key>{{ $ts._registry.scope }}</template>
|
||||
<template #value>{{ scope.join('/') }}</template>
|
||||
</FormKeyValueView>
|
||||
<FormKeyValueView>
|
||||
<template #key>{{ $ts._registry.key }}</template>
|
||||
<template #value>{{ xKey }}</template>
|
||||
</FormKeyValueView>
|
||||
</FormGroup>
|
||||
|
||||
<FormGroup>
|
||||
<FormTextarea tall v-model:value="valueForEditor" class="_monospace" style="tab-size: 2;">
|
||||
<span>{{ $ts.value }} (JSON)</span>
|
||||
</FormTextarea>
|
||||
<FormButton @click="save" primary><Fa :icon="faSave"/> {{ $ts.save }}</FormButton>
|
||||
</FormGroup>
|
||||
|
||||
<FormKeyValueView>
|
||||
<template #key>{{ $ts.updatedAt }}</template>
|
||||
<template #value><MkTime :time="value.updatedAt" mode="detail"/></template>
|
||||
</FormKeyValueView>
|
||||
|
||||
<FormButton danger @click="del"><Fa :icon="faTrash"/> {{ $ts.delete }}</FormButton>
|
||||
</template>
|
||||
</FormBase>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
import { defineAsyncComponent, defineComponent } from 'vue';
|
||||
import { faCogs, faSave, faTrash } from '@fortawesome/free-solid-svg-icons';
|
||||
import * as JSON5 from 'json5';
|
||||
import MkInfo from '@/components/ui/info.vue';
|
||||
import FormSwitch from '@/components/form/switch.vue';
|
||||
import FormSelect from '@/components/form/select.vue';
|
||||
import FormTextarea from '@/components/form/textarea.vue';
|
||||
import FormBase from '@/components/form/base.vue';
|
||||
import FormGroup from '@/components/form/group.vue';
|
||||
import FormButton from '@/components/form/button.vue';
|
||||
import FormKeyValueView from '@/components/form/key-value-view.vue';
|
||||
import * as os from '@/os';
|
||||
|
||||
export default defineComponent({
|
||||
components: {
|
||||
MkInfo,
|
||||
FormBase,
|
||||
FormSelect,
|
||||
FormSwitch,
|
||||
FormButton,
|
||||
FormTextarea,
|
||||
FormGroup,
|
||||
FormKeyValueView,
|
||||
},
|
||||
|
||||
props: {
|
||||
scope: {
|
||||
required: true
|
||||
},
|
||||
xKey: {
|
||||
required: true
|
||||
},
|
||||
},
|
||||
|
||||
emits: ['info'],
|
||||
|
||||
data() {
|
||||
return {
|
||||
INFO: {
|
||||
title: this.$ts.registry,
|
||||
icon: faCogs
|
||||
},
|
||||
value: null,
|
||||
valueForEditor: null,
|
||||
faSave, faTrash,
|
||||
}
|
||||
},
|
||||
|
||||
watch: {
|
||||
key() {
|
||||
this.fetch();
|
||||
},
|
||||
},
|
||||
|
||||
mounted() {
|
||||
this.$emit('info', this.INFO);
|
||||
this.fetch();
|
||||
},
|
||||
|
||||
methods: {
|
||||
fetch() {
|
||||
os.api('i/registry/get-detail', {
|
||||
scope: this.scope,
|
||||
key: this.xKey
|
||||
}).then(value => {
|
||||
this.value = value;
|
||||
this.valueForEditor = JSON5.stringify(this.value.value, null, '\t');
|
||||
});
|
||||
},
|
||||
|
||||
save() {
|
||||
try {
|
||||
JSON5.parse(this.valueForEditor);
|
||||
} catch (e) {
|
||||
os.dialog({
|
||||
type: 'error',
|
||||
text: this.$ts.invalidValue
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
os.dialog({
|
||||
type: 'warning',
|
||||
text: this.$ts.saveConfirm,
|
||||
showCancelButton: true
|
||||
}).then(({ canceled }) => {
|
||||
if (canceled) return;
|
||||
os.apiWithDialog('i/registry/set', {
|
||||
scope: this.scope,
|
||||
key: this.xKey,
|
||||
value: JSON5.parse(this.valueForEditor)
|
||||
});
|
||||
});
|
||||
},
|
||||
|
||||
del() {
|
||||
os.dialog({
|
||||
type: 'warning',
|
||||
text: this.$ts.deleteConfirm,
|
||||
showCancelButton: true
|
||||
}).then(({ canceled }) => {
|
||||
if (canceled) return;
|
||||
os.apiWithDialog('i/registry/remove', {
|
||||
scope: this.scope,
|
||||
key: this.xKey
|
||||
});
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
</script>
|
91
src/client/pages/settings/registry.vue
Normal file
91
src/client/pages/settings/registry.vue
Normal file
|
@ -0,0 +1,91 @@
|
|||
<template>
|
||||
<FormBase>
|
||||
<FormGroup v-if="scopes">
|
||||
<template #label>{{ $ts.system }}</template>
|
||||
<FormLink v-for="scope in scopes" :to="`/settings/registry/keys/system/${scope.join('/')}`" class="_monospace">{{ scope.join('/') }}</FormLink>
|
||||
</FormGroup>
|
||||
<FormButton @click="createKey" primary>{{ $ts._registry.createKey }}</FormButton>
|
||||
</FormBase>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
import { defineAsyncComponent, defineComponent } from 'vue';
|
||||
import { faCogs } from '@fortawesome/free-solid-svg-icons';
|
||||
import * as JSON5 from 'json5';
|
||||
import MkInfo from '@/components/ui/info.vue';
|
||||
import FormSwitch from '@/components/form/switch.vue';
|
||||
import FormSelect from '@/components/form/select.vue';
|
||||
import FormLink from '@/components/form/link.vue';
|
||||
import FormBase from '@/components/form/base.vue';
|
||||
import FormGroup from '@/components/form/group.vue';
|
||||
import FormButton from '@/components/form/button.vue';
|
||||
import FormKeyValueView from '@/components/form/key-value-view.vue';
|
||||
import * as os from '@/os';
|
||||
|
||||
export default defineComponent({
|
||||
components: {
|
||||
MkInfo,
|
||||
FormBase,
|
||||
FormSelect,
|
||||
FormSwitch,
|
||||
FormButton,
|
||||
FormLink,
|
||||
FormGroup,
|
||||
FormKeyValueView,
|
||||
},
|
||||
|
||||
emits: ['info'],
|
||||
|
||||
data() {
|
||||
return {
|
||||
INFO: {
|
||||
title: this.$ts.registry,
|
||||
icon: faCogs
|
||||
},
|
||||
scopes: null,
|
||||
}
|
||||
},
|
||||
|
||||
created() {
|
||||
this.fetch();
|
||||
},
|
||||
|
||||
mounted() {
|
||||
this.$emit('info', this.INFO);
|
||||
},
|
||||
|
||||
methods: {
|
||||
fetch() {
|
||||
os.api('i/registry/scopes').then(scopes => {
|
||||
this.scopes = scopes.slice().sort((a, b) => a.join('/').localeCompare(b.join('/')));
|
||||
});
|
||||
},
|
||||
|
||||
async createKey() {
|
||||
const { canceled, result } = await os.form(this.$ts._registry.createKey, {
|
||||
key: {
|
||||
type: 'string',
|
||||
label: this.$ts._registry.key,
|
||||
},
|
||||
value: {
|
||||
type: 'string',
|
||||
multiline: true,
|
||||
label: this.$ts.value,
|
||||
},
|
||||
scope: {
|
||||
type: 'string',
|
||||
label: this.$ts._registry.scope,
|
||||
}
|
||||
});
|
||||
if (canceled) return;
|
||||
os.apiWithDialog('i/registry/set', {
|
||||
scope: result.scope.split('/'),
|
||||
key: result.key,
|
||||
value: JSON5.parse(result.value),
|
||||
}).then(() => {
|
||||
this.fetch();
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
</script>
|
Loading…
Add table
Add a link
Reference in a new issue