Merge 25b3eb9de6
into 5f5d88036f
This commit is contained in:
commit
9cdc35aebf
|
@ -67,6 +67,7 @@
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@misskey-dev/eslint-plugin": "2.1.0",
|
"@misskey-dev/eslint-plugin": "2.1.0",
|
||||||
|
"@types/js-yaml": "4.0.9",
|
||||||
"@types/node": "22.17.2",
|
"@types/node": "22.17.2",
|
||||||
"@typescript-eslint/eslint-plugin": "8.40.0",
|
"@typescript-eslint/eslint-plugin": "8.40.0",
|
||||||
"@typescript-eslint/parser": "8.40.0",
|
"@typescript-eslint/parser": "8.40.0",
|
||||||
|
|
|
@ -127,7 +127,7 @@ export function galleryPost(isSensitive = false) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export function file(isSensitive = false) {
|
export function file(isSensitive = false): entities.DriveFile {
|
||||||
return {
|
return {
|
||||||
id: 'somefileid',
|
id: 'somefileid',
|
||||||
createdAt: '2016-12-28T22:49:51.000Z',
|
createdAt: '2016-12-28T22:49:51.000Z',
|
||||||
|
|
|
@ -86,7 +86,7 @@ export function createAiScriptEnv(opts: { storageKey: string, token?: string })
|
||||||
throw new errors.AiScriptRuntimeError('expected param');
|
throw new errors.AiScriptRuntimeError('expected param');
|
||||||
}
|
}
|
||||||
utils.assertObject(param);
|
utils.assertObject(param);
|
||||||
return misskeyApi(ep.value, utils.valToJs(param) as object, actualToken).then(res => {
|
return misskeyApi(ep.value as keyof Misskey.Endpoints, utils.valToJs(param) as object, actualToken).then(res => {
|
||||||
return utils.jsToVal(res);
|
return utils.jsToVal(res);
|
||||||
}, err => {
|
}, err => {
|
||||||
return values.ERROR('request_failed', utils.jsToVal(err));
|
return values.ERROR('request_failed', utils.jsToVal(err));
|
||||||
|
|
|
@ -167,9 +167,13 @@ async function init() {
|
||||||
for (const user of usersRes) {
|
for (const user of usersRes) {
|
||||||
if (users.value.has(user.id)) continue;
|
if (users.value.has(user.id)) continue;
|
||||||
|
|
||||||
|
const account = accounts.find(a => a.id === user.id);
|
||||||
|
|
||||||
|
if (!account || account.token == null) continue;
|
||||||
|
|
||||||
users.value.set(user.id, {
|
users.value.set(user.id, {
|
||||||
...user,
|
...user,
|
||||||
token: accounts.find(a => a.id === user.id)!.token,
|
token: account.token,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -25,7 +25,7 @@ SPDX-License-Identifier: AGPL-3.0-only
|
||||||
<MkCustomEmoji v-if="'isCustomEmoji' in emoji && emoji.isCustomEmoji" :name="emoji.emoji" :class="$style.emoji" :fallbackToImage="true"/>
|
<MkCustomEmoji v-if="'isCustomEmoji' in emoji && emoji.isCustomEmoji" :name="emoji.emoji" :class="$style.emoji" :fallbackToImage="true"/>
|
||||||
<MkEmoji v-else :emoji="emoji.emoji" :class="$style.emoji"/>
|
<MkEmoji v-else :emoji="emoji.emoji" :class="$style.emoji"/>
|
||||||
<!-- eslint-disable-next-line vue/no-v-html -->
|
<!-- eslint-disable-next-line vue/no-v-html -->
|
||||||
<span v-if="q" :class="$style.emojiName" v-html="sanitizeHtml(emoji.name.replace(q, `<b>${q}</b>`))"></span>
|
<span v-if="q != null && typeof q === 'string'" :class="$style.emojiName" v-html="sanitizeHtml(emoji.name.replace(q, `<b>${q}</b>`))"></span>
|
||||||
<span v-else v-text="emoji.name"></span>
|
<span v-else v-text="emoji.name"></span>
|
||||||
<span v-if="emoji.aliasOf" :class="$style.emojiAlias">({{ emoji.aliasOf }})</span>
|
<span v-if="emoji.aliasOf" :class="$style.emojiAlias">({{ emoji.aliasOf }})</span>
|
||||||
</li>
|
</li>
|
||||||
|
@ -36,7 +36,7 @@ SPDX-License-Identifier: AGPL-3.0-only
|
||||||
</li>
|
</li>
|
||||||
</ol>
|
</ol>
|
||||||
<ol v-else-if="type === 'mfmParam' && mfmParams.length > 0" ref="suggests" :class="$style.list">
|
<ol v-else-if="type === 'mfmParam' && mfmParams.length > 0" ref="suggests" :class="$style.list">
|
||||||
<li v-for="param in mfmParams" tabindex="-1" :class="$style.item" @click="complete(type, q.params.toSpliced(-1, 1, param).join(','))" @keydown="onKeydown">
|
<li v-for="param in mfmParams" tabindex="-1" :class="$style.item" @click="completeMfmParam(param)" @keydown="onKeydown">
|
||||||
<span>{{ param }}</span>
|
<span>{{ param }}</span>
|
||||||
</li>
|
</li>
|
||||||
</ol>
|
</ol>
|
||||||
|
@ -194,6 +194,11 @@ const mfmParams = ref<string[]>([]);
|
||||||
const select = ref(-1);
|
const select = ref(-1);
|
||||||
const zIndex = os.claimZIndex('high');
|
const zIndex = os.claimZIndex('high');
|
||||||
|
|
||||||
|
function completeMfmParam(param: string) {
|
||||||
|
if (props.type !== 'mfmParam') throw new Error('Invalid type');
|
||||||
|
complete('mfmParam', props.q.params.toSpliced(-1, 1, param).join(','));
|
||||||
|
}
|
||||||
|
|
||||||
function complete<T extends keyof CompleteInfo>(type: T, value: CompleteInfo[T]['payload']) {
|
function complete<T extends keyof CompleteInfo>(type: T, value: CompleteInfo[T]['payload']) {
|
||||||
emit('done', { type, value });
|
emit('done', { type, value });
|
||||||
emit('closed');
|
emit('closed');
|
||||||
|
|
|
@ -38,7 +38,7 @@ export const Default = {
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
args: {
|
args: {
|
||||||
file: file(),
|
imageFile: file(),
|
||||||
aspectRatio: NaN,
|
aspectRatio: NaN,
|
||||||
},
|
},
|
||||||
parameters: {
|
parameters: {
|
||||||
|
|
|
@ -699,7 +699,7 @@ useGlobalEvent('driveFoldersDeleted', (folders) => {
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
let connection: Misskey.ChannelConnection<Misskey.Channels['drive']> | null = null;
|
let connection: Misskey.IChannelConnection<Misskey.Channels['drive']> | null = null;
|
||||||
|
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
if (store.s.realtimeMode) {
|
if (store.s.realtimeMode) {
|
||||||
|
|
|
@ -160,7 +160,7 @@ const embedPreviewUrl = computed(() => {
|
||||||
|
|
||||||
const isEmbedWithScrollbar = computed(() => embedRouteWithScrollbar.includes(props.entity));
|
const isEmbedWithScrollbar = computed(() => embedRouteWithScrollbar.includes(props.entity));
|
||||||
const header = ref(props.params?.header ?? true);
|
const header = ref(props.params?.header ?? true);
|
||||||
const maxHeight = ref(props.params?.maxHeight !== 0 ? props.params?.maxHeight ?? undefined : 500);
|
const maxHeight = ref(props.params?.maxHeight !== 0 ? props.params?.maxHeight ?? null : 500);
|
||||||
|
|
||||||
const colorMode = ref<'light' | 'dark' | 'auto'>(props.params?.colorMode ?? 'auto');
|
const colorMode = ref<'light' | 'dark' | 'auto'>(props.params?.colorMode ?? 'auto');
|
||||||
const rounded = ref(props.params?.rounded ?? true);
|
const rounded = ref(props.params?.rounded ?? true);
|
||||||
|
|
|
@ -41,11 +41,11 @@ SPDX-License-Identifier: AGPL-3.0-only
|
||||||
</MkSwitch>
|
</MkSwitch>
|
||||||
<MkSelect v-else-if="v.type === 'enum'" v-model="values[k]">
|
<MkSelect v-else-if="v.type === 'enum'" v-model="values[k]">
|
||||||
<template #label><span v-text="v.label || k"></span><span v-if="v.required === false"> ({{ i18n.ts.optional }})</span></template>
|
<template #label><span v-text="v.label || k"></span><span v-if="v.required === false"> ({{ i18n.ts.optional }})</span></template>
|
||||||
<option v-for="option in v.enum" :key="option.value" :value="option.value">{{ option.label }}</option>
|
<option v-for="option in v.enum" :key="getEnumKey(option)" :value="getEnumValue(option)">{{ getEnumLabel(option) }}</option>
|
||||||
</MkSelect>
|
</MkSelect>
|
||||||
<MkRadios v-else-if="v.type === 'radio'" v-model="values[k]">
|
<MkRadios v-else-if="v.type === 'radio'" v-model="values[k]">
|
||||||
<template #label><span v-text="v.label || k"></span><span v-if="v.required === false"> ({{ i18n.ts.optional }})</span></template>
|
<template #label><span v-text="v.label || k"></span><span v-if="v.required === false"> ({{ i18n.ts.optional }})</span></template>
|
||||||
<option v-for="option in v.options" :key="option.value" :value="option.value">{{ option.label }}</option>
|
<option v-for="option in v.options" :key="getRadioKey(option)" :value="option.value">{{ option.label }}</option>
|
||||||
</MkRadios>
|
</MkRadios>
|
||||||
<MkRange v-else-if="v.type === 'range'" v-model="values[k]" :min="v.min" :max="v.max" :step="v.step" :textConverter="v.textConverter">
|
<MkRange v-else-if="v.type === 'range'" v-model="values[k]" :min="v.min" :max="v.max" :step="v.step" :textConverter="v.textConverter">
|
||||||
<template #label><span v-text="v.label || k"></span><span v-if="v.required === false"> ({{ i18n.ts.optional }})</span></template>
|
<template #label><span v-text="v.label || k"></span><span v-if="v.required === false"> ({{ i18n.ts.optional }})</span></template>
|
||||||
|
@ -77,7 +77,7 @@ import MkRange from './MkRange.vue';
|
||||||
import MkButton from './MkButton.vue';
|
import MkButton from './MkButton.vue';
|
||||||
import MkRadios from './MkRadios.vue';
|
import MkRadios from './MkRadios.vue';
|
||||||
import XFile from './MkFormDialog.file.vue';
|
import XFile from './MkFormDialog.file.vue';
|
||||||
import type { Form } from '@/utility/form.js';
|
import type { EnumItem, Form, RadioFormItem } from '@/utility/form.js';
|
||||||
import MkModalWindow from '@/components/MkModalWindow.vue';
|
import MkModalWindow from '@/components/MkModalWindow.vue';
|
||||||
import { i18n } from '@/i18n.js';
|
import { i18n } from '@/i18n.js';
|
||||||
|
|
||||||
|
@ -99,7 +99,11 @@ const dialog = useTemplateRef('dialog');
|
||||||
const values = reactive({});
|
const values = reactive({});
|
||||||
|
|
||||||
for (const item in props.form) {
|
for (const item in props.form) {
|
||||||
|
if ('default' in props.form[item]) {
|
||||||
values[item] = props.form[item].default ?? null;
|
values[item] = props.form[item].default ?? null;
|
||||||
|
} else {
|
||||||
|
values[item] = null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function ok() {
|
function ok() {
|
||||||
|
@ -115,4 +119,20 @@ function cancel() {
|
||||||
});
|
});
|
||||||
dialog.value?.close();
|
dialog.value?.close();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function getEnumLabel(e: EnumItem) {
|
||||||
|
return typeof e === 'string' ? e : e.label;
|
||||||
|
}
|
||||||
|
|
||||||
|
function getEnumValue(e: EnumItem) {
|
||||||
|
return typeof e === 'string' ? e : e.value;
|
||||||
|
}
|
||||||
|
|
||||||
|
function getEnumKey(e: EnumItem) {
|
||||||
|
return typeof e === 'string' ? e : typeof e.value === 'string' ? e.value : JSON.stringify(e.value);
|
||||||
|
}
|
||||||
|
|
||||||
|
function getRadioKey(e: RadioFormItem['options'][number]) {
|
||||||
|
return typeof e.value === 'string' ? e.value : JSON.stringify(e.value);
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
|
@ -43,7 +43,15 @@ SPDX-License-Identifier: AGPL-3.0-only
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script lang="ts" setup>
|
<script lang="ts">
|
||||||
|
type SupportedTypes = 'text' | 'password' | 'email' | 'url' | 'tel' | 'number' | 'search';
|
||||||
|
type ModelValueType<T extends SupportedTypes> =
|
||||||
|
T extends 'number' ? number :
|
||||||
|
T extends 'text' | 'password' | 'email' | 'url' | 'tel' | 'search' ? string :
|
||||||
|
never;
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<script lang="ts" setup generic="T extends SupportedTypes = 'text'">
|
||||||
import { onMounted, onUnmounted, nextTick, ref, useTemplateRef, watch, computed, toRefs } from 'vue';
|
import { onMounted, onUnmounted, nextTick, ref, useTemplateRef, watch, computed, toRefs } from 'vue';
|
||||||
import { debounce } from 'throttle-debounce';
|
import { debounce } from 'throttle-debounce';
|
||||||
import { useInterval } from '@@/js/use-interval.js';
|
import { useInterval } from '@@/js/use-interval.js';
|
||||||
|
@ -55,8 +63,8 @@ import { Autocomplete } from '@/utility/autocomplete.js';
|
||||||
import { genId } from '@/utility/id.js';
|
import { genId } from '@/utility/id.js';
|
||||||
|
|
||||||
const props = defineProps<{
|
const props = defineProps<{
|
||||||
modelValue: string | number | null;
|
modelValue: ModelValueType<T> | null;
|
||||||
type?: InputHTMLAttributes['type'];
|
type?: T;
|
||||||
required?: boolean;
|
required?: boolean;
|
||||||
readonly?: boolean;
|
readonly?: boolean;
|
||||||
disabled?: boolean;
|
disabled?: boolean;
|
||||||
|
@ -83,11 +91,11 @@ const emit = defineEmits<{
|
||||||
(ev: 'change', _ev: KeyboardEvent): void;
|
(ev: 'change', _ev: KeyboardEvent): void;
|
||||||
(ev: 'keydown', _ev: KeyboardEvent): void;
|
(ev: 'keydown', _ev: KeyboardEvent): void;
|
||||||
(ev: 'enter', _ev: KeyboardEvent): void;
|
(ev: 'enter', _ev: KeyboardEvent): void;
|
||||||
(ev: 'update:modelValue', value: string | number): void;
|
(ev: 'update:modelValue', value: ModelValueType<T>): void;
|
||||||
}>();
|
}>();
|
||||||
|
|
||||||
const { modelValue, type, autofocus } = toRefs(props);
|
const { modelValue } = toRefs(props);
|
||||||
const v = ref(modelValue.value);
|
const v = ref<ModelValueType<T> | null>(modelValue.value);
|
||||||
const id = genId();
|
const id = genId();
|
||||||
const focused = ref(false);
|
const focused = ref(false);
|
||||||
const changed = ref(false);
|
const changed = ref(false);
|
||||||
|
@ -120,8 +128,8 @@ const onKeydown = (ev: KeyboardEvent) => {
|
||||||
|
|
||||||
const updated = () => {
|
const updated = () => {
|
||||||
changed.value = false;
|
changed.value = false;
|
||||||
if (type.value === 'number') {
|
if (props.type === 'number') {
|
||||||
emit('update:modelValue', typeof v.value === 'number' ? v.value : parseFloat(v.value ?? '0'));
|
emit('update:modelValue', typeof v.value === 'number' ? v.value as ModelValueType<T> : parseFloat(v.value ?? '0') as ModelValueType<T>);
|
||||||
} else {
|
} else {
|
||||||
emit('update:modelValue', v.value ?? '');
|
emit('update:modelValue', v.value ?? '');
|
||||||
}
|
}
|
||||||
|
@ -167,7 +175,7 @@ useInterval(() => {
|
||||||
|
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
nextTick(() => {
|
nextTick(() => {
|
||||||
if (autofocus.value) {
|
if (props.autofocus) {
|
||||||
focus();
|
focus();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
|
@ -89,6 +89,7 @@ import { Chart } from 'chart.js';
|
||||||
import type { HeatmapSource } from '@/components/MkHeatmap.vue';
|
import type { HeatmapSource } from '@/components/MkHeatmap.vue';
|
||||||
import MkSelect from '@/components/MkSelect.vue';
|
import MkSelect from '@/components/MkSelect.vue';
|
||||||
import MkChart from '@/components/MkChart.vue';
|
import MkChart from '@/components/MkChart.vue';
|
||||||
|
import type { ChartSrc } from '@/components/MkChart.vue';
|
||||||
import { useChartTooltip } from '@/composables/use-chart-tooltip.js';
|
import { useChartTooltip } from '@/composables/use-chart-tooltip.js';
|
||||||
import { $i } from '@/i.js';
|
import { $i } from '@/i.js';
|
||||||
import * as os from '@/os.js';
|
import * as os from '@/os.js';
|
||||||
|
@ -107,7 +108,7 @@ const shouldShowFederation = computed(() => instance.federation !== 'none' || $i
|
||||||
|
|
||||||
const chartLimit = 500;
|
const chartLimit = 500;
|
||||||
const chartSpan = ref<'hour' | 'day'>('hour');
|
const chartSpan = ref<'hour' | 'day'>('hour');
|
||||||
const chartSrc = ref('active-users');
|
const chartSrc = ref<ChartSrc>('active-users');
|
||||||
const heatmapSrc = ref<HeatmapSource>('active-users');
|
const heatmapSrc = ref<HeatmapSource>('active-users');
|
||||||
const subDoughnutEl = useTemplateRef('subDoughnutEl');
|
const subDoughnutEl = useTemplateRef('subDoughnutEl');
|
||||||
const pubDoughnutEl = useTemplateRef('pubDoughnutEl');
|
const pubDoughnutEl = useTemplateRef('pubDoughnutEl');
|
||||||
|
|
|
@ -11,7 +11,7 @@ SPDX-License-Identifier: AGPL-3.0-only
|
||||||
:class="[$style.root, { [$style.showActionsOnlyHover]: prefer.s.showNoteActionsOnlyHover, [$style.skipRender]: prefer.s.skipNoteRender }]"
|
:class="[$style.root, { [$style.showActionsOnlyHover]: prefer.s.showNoteActionsOnlyHover, [$style.skipRender]: prefer.s.skipNoteRender }]"
|
||||||
tabindex="0"
|
tabindex="0"
|
||||||
>
|
>
|
||||||
<MkNoteSub v-if="appearNote.replyId && !renoteCollapsed" :note="appearNote.reply" :class="$style.replyTo"/>
|
<MkNoteSub v-if="appearNote.replyId && !renoteCollapsed" :note="appearNote?.reply ?? null" :class="$style.replyTo"/>
|
||||||
<div v-if="pinned" :class="$style.tip"><i class="ti ti-pin"></i> {{ i18n.ts.pinnedNote }}</div>
|
<div v-if="pinned" :class="$style.tip"><i class="ti ti-pin"></i> {{ i18n.ts.pinnedNote }}</div>
|
||||||
<div v-if="isRenote" :class="$style.renote">
|
<div v-if="isRenote" :class="$style.renote">
|
||||||
<div v-if="note.channel" :class="$style.colorBar" :style="{ background: note.channel.color }"></div>
|
<div v-if="note.channel" :class="$style.colorBar" :style="{ background: note.channel.color }"></div>
|
||||||
|
@ -99,7 +99,7 @@ SPDX-License-Identifier: AGPL-3.0-only
|
||||||
<div v-if="isEnabledUrlPreview">
|
<div v-if="isEnabledUrlPreview">
|
||||||
<MkUrlPreview v-for="url in urls" :key="url" :url="url" :compact="true" :detail="false" :class="$style.urlPreview"/>
|
<MkUrlPreview v-for="url in urls" :key="url" :url="url" :compact="true" :detail="false" :class="$style.urlPreview"/>
|
||||||
</div>
|
</div>
|
||||||
<div v-if="appearNote.renoteId" :class="$style.quote"><MkNoteSimple :note="appearNote.renote" :class="$style.quoteNote"/></div>
|
<div v-if="appearNote.renoteId" :class="$style.quote"><MkNoteSimple :note="appearNote?.renote ?? null" :class="$style.quoteNote"/></div>
|
||||||
<button v-if="isLong && collapsed" :class="$style.collapsed" class="_button" @click="collapsed = false">
|
<button v-if="isLong && collapsed" :class="$style.collapsed" class="_button" @click="collapsed = false">
|
||||||
<span :class="$style.collapsedLabel">{{ i18n.ts.showMore }}</span>
|
<span :class="$style.collapsedLabel">{{ i18n.ts.showMore }}</span>
|
||||||
</button>
|
</button>
|
||||||
|
|
|
@ -31,7 +31,7 @@ SPDX-License-Identifier: AGPL-3.0-only
|
||||||
</MkButton>
|
</MkButton>
|
||||||
<MkLoading v-else/>
|
<MkLoading v-else/>
|
||||||
</div>
|
</div>
|
||||||
<slot :items="unref(paginator.items)" :fetching="paginator.fetching.value || paginator.fetchingOlder.value"></slot>
|
<slot :items="getValue(paginator.items)" :fetching="paginator.fetching.value || paginator.fetchingOlder.value"></slot>
|
||||||
<div v-if="direction === 'down' || direction === 'both'" v-show="downButtonVisible">
|
<div v-if="direction === 'down' || direction === 'both'" v-show="downButtonVisible">
|
||||||
<MkButton v-if="!downButtonLoading" :class="$style.more" primary rounded @click="downButtonClick">
|
<MkButton v-if="!downButtonLoading" :class="$style.more" primary rounded @click="downButtonClick">
|
||||||
{{ i18n.ts.loadMore }}
|
{{ i18n.ts.loadMore }}
|
||||||
|
@ -90,6 +90,10 @@ function onContextmenu(ev: MouseEvent) {
|
||||||
}], ev);
|
}], ev);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function getValue(v: IPaginator['items']) {
|
||||||
|
return unref(v) as UnwrapRef<T['items']>;
|
||||||
|
}
|
||||||
|
|
||||||
if (props.autoLoad) {
|
if (props.autoLoad) {
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
props.paginator.init();
|
props.paginator.init();
|
||||||
|
@ -134,7 +138,7 @@ function downButtonClick() {
|
||||||
|
|
||||||
defineSlots<{
|
defineSlots<{
|
||||||
empty: () => void;
|
empty: () => void;
|
||||||
default: (props: { items: UnwrapRef<T['items']> }) => void;
|
default: (props: { items: UnwrapRef<T['items']>, fetching: boolean }) => void;
|
||||||
}>();
|
}>();
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
|
|
|
@ -134,7 +134,7 @@ SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
<div>
|
<div>
|
||||||
<div><b>{{ i18n.ts._serverSettings.entrancePageStyle }}:</b></div>
|
<div><b>{{ i18n.ts._serverSettings.entrancePageStyle }}:</b></div>
|
||||||
<div>{{ serverSettings.clientOptions.entrancePageStyle }}</div>
|
<div>{{ serverSettings.clientOptions?.entrancePageStyle }}</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div>
|
<div>
|
||||||
|
@ -240,12 +240,12 @@ const serverSettings = computed<Misskey.entities.AdminUpdateMetaRequest>(() => {
|
||||||
enableReactionsBuffering,
|
enableReactionsBuffering,
|
||||||
clientOptions: {
|
clientOptions: {
|
||||||
entrancePageStyle: q_use.value === 'open' ? 'classic' : 'simple',
|
entrancePageStyle: q_use.value === 'open' ? 'classic' : 'simple',
|
||||||
},
|
} as any,
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
const defaultPolicies = computed<Partial<Record<typeof ROLE_POLICIES[number], any>>>(() => {
|
const defaultPolicies = computed<Partial<Misskey.entities.RolePolicies>>(() => {
|
||||||
let driveCapacityMb;
|
let driveCapacityMb: Misskey.entities.RolePolicies['driveCapacityMb'] | undefined;
|
||||||
if (q_use.value === 'single') {
|
if (q_use.value === 'single') {
|
||||||
driveCapacityMb = 8192;
|
driveCapacityMb = 8192;
|
||||||
} else if (q_use.value === 'group') {
|
} else if (q_use.value === 'group') {
|
||||||
|
@ -254,7 +254,7 @@ const defaultPolicies = computed<Partial<Record<typeof ROLE_POLICIES[number], an
|
||||||
driveCapacityMb = 100;
|
driveCapacityMb = 100;
|
||||||
}
|
}
|
||||||
|
|
||||||
let rateLimitFactor;
|
let rateLimitFactor: Misskey.entities.RolePolicies['rateLimitFactor'] | undefined;
|
||||||
if (q_use.value === 'single') {
|
if (q_use.value === 'single') {
|
||||||
rateLimitFactor = 0.3;
|
rateLimitFactor = 0.3;
|
||||||
} else if (q_use.value === 'group') {
|
} else if (q_use.value === 'group') {
|
||||||
|
@ -269,7 +269,7 @@ const defaultPolicies = computed<Partial<Record<typeof ROLE_POLICIES[number], an
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let userListLimit;
|
let userListLimit: Misskey.entities.RolePolicies['userListLimit'] | undefined;
|
||||||
if (q_use.value === 'single') {
|
if (q_use.value === 'single') {
|
||||||
userListLimit = 100;
|
userListLimit = 100;
|
||||||
} else if (q_use.value === 'group') {
|
} else if (q_use.value === 'group') {
|
||||||
|
@ -278,7 +278,7 @@ const defaultPolicies = computed<Partial<Record<typeof ROLE_POLICIES[number], an
|
||||||
userListLimit = 3;
|
userListLimit = 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
let antennaLimit;
|
let antennaLimit: Misskey.entities.RolePolicies['antennaLimit'] | undefined;
|
||||||
if (q_use.value === 'single') {
|
if (q_use.value === 'single') {
|
||||||
antennaLimit = 100;
|
antennaLimit = 100;
|
||||||
} else if (q_use.value === 'group') {
|
} else if (q_use.value === 'group') {
|
||||||
|
@ -287,7 +287,7 @@ const defaultPolicies = computed<Partial<Record<typeof ROLE_POLICIES[number], an
|
||||||
antennaLimit = 0;
|
antennaLimit = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
let webhookLimit;
|
let webhookLimit: Misskey.entities.RolePolicies['webhookLimit'] | undefined;
|
||||||
if (q_use.value === 'single') {
|
if (q_use.value === 'single') {
|
||||||
webhookLimit = 100;
|
webhookLimit = 100;
|
||||||
} else if (q_use.value === 'group') {
|
} else if (q_use.value === 'group') {
|
||||||
|
@ -296,35 +296,35 @@ const defaultPolicies = computed<Partial<Record<typeof ROLE_POLICIES[number], an
|
||||||
webhookLimit = 0;
|
webhookLimit = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
let canImportFollowing;
|
let canImportFollowing: Misskey.entities.RolePolicies['canImportFollowing'];
|
||||||
if (q_use.value === 'single') {
|
if (q_use.value === 'single') {
|
||||||
canImportFollowing = true;
|
canImportFollowing = true;
|
||||||
} else {
|
} else {
|
||||||
canImportFollowing = false;
|
canImportFollowing = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
let canImportMuting;
|
let canImportMuting: Misskey.entities.RolePolicies['canImportMuting'];
|
||||||
if (q_use.value === 'single') {
|
if (q_use.value === 'single') {
|
||||||
canImportMuting = true;
|
canImportMuting = true;
|
||||||
} else {
|
} else {
|
||||||
canImportMuting = false;
|
canImportMuting = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
let canImportBlocking;
|
let canImportBlocking: Misskey.entities.RolePolicies['canImportBlocking'];
|
||||||
if (q_use.value === 'single') {
|
if (q_use.value === 'single') {
|
||||||
canImportBlocking = true;
|
canImportBlocking = true;
|
||||||
} else {
|
} else {
|
||||||
canImportBlocking = false;
|
canImportBlocking = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
let canImportUserLists;
|
let canImportUserLists: Misskey.entities.RolePolicies['canImportUserLists'];
|
||||||
if (q_use.value === 'single') {
|
if (q_use.value === 'single') {
|
||||||
canImportUserLists = true;
|
canImportUserLists = true;
|
||||||
} else {
|
} else {
|
||||||
canImportUserLists = false;
|
canImportUserLists = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
let canImportAntennas;
|
let canImportAntennas: Misskey.entities.RolePolicies['canImportAntennas'];
|
||||||
if (q_use.value === 'single') {
|
if (q_use.value === 'single') {
|
||||||
canImportAntennas = true;
|
canImportAntennas = true;
|
||||||
} else {
|
} else {
|
||||||
|
@ -355,6 +355,7 @@ function applySettings() {
|
||||||
maintainerEmail: q_adminEmail.value === '' ? undefined : q_adminEmail.value,
|
maintainerEmail: q_adminEmail.value === '' ? undefined : q_adminEmail.value,
|
||||||
}, props.token),
|
}, props.token),
|
||||||
misskeyApi('admin/roles/update-default-policies', {
|
misskeyApi('admin/roles/update-default-policies', {
|
||||||
|
// @ts-expect-error バックエンド側の型
|
||||||
policies: defaultPolicies.value,
|
policies: defaultPolicies.value,
|
||||||
}, props.token),
|
}, props.token),
|
||||||
]).then(() => {
|
]).then(() => {
|
||||||
|
|
|
@ -66,7 +66,7 @@ SPDX-License-Identifier: AGPL-3.0-only
|
||||||
<MkCaptcha v-if="instance.enableMcaptcha" ref="mcaptcha" v-model="mCaptchaResponse" :class="$style.captcha" provider="mcaptcha" :sitekey="instance.mcaptchaSiteKey" :instanceUrl="instance.mcaptchaInstanceUrl"/>
|
<MkCaptcha v-if="instance.enableMcaptcha" ref="mcaptcha" v-model="mCaptchaResponse" :class="$style.captcha" provider="mcaptcha" :sitekey="instance.mcaptchaSiteKey" :instanceUrl="instance.mcaptchaInstanceUrl"/>
|
||||||
<MkCaptcha v-if="instance.enableRecaptcha" ref="recaptcha" v-model="reCaptchaResponse" :class="$style.captcha" provider="recaptcha" :sitekey="instance.recaptchaSiteKey"/>
|
<MkCaptcha v-if="instance.enableRecaptcha" ref="recaptcha" v-model="reCaptchaResponse" :class="$style.captcha" provider="recaptcha" :sitekey="instance.recaptchaSiteKey"/>
|
||||||
<MkCaptcha v-if="instance.enableTurnstile" ref="turnstile" v-model="turnstileResponse" :class="$style.captcha" provider="turnstile" :sitekey="instance.turnstileSiteKey"/>
|
<MkCaptcha v-if="instance.enableTurnstile" ref="turnstile" v-model="turnstileResponse" :class="$style.captcha" provider="turnstile" :sitekey="instance.turnstileSiteKey"/>
|
||||||
<MkCaptcha v-if="instance.enableTestcaptcha" ref="testcaptcha" v-model="testcaptchaResponse" :class="$style.captcha" provider="testcaptcha"/>
|
<MkCaptcha v-if="instance.enableTestcaptcha" ref="testcaptcha" v-model="testcaptchaResponse" :class="$style.captcha" provider="testcaptcha" :sitekey="null"/>
|
||||||
<MkButton type="submit" :disabled="shouldDisableSubmitting" large gradate rounded data-cy-signup-submit style="margin: 0 auto;">
|
<MkButton type="submit" :disabled="shouldDisableSubmitting" large gradate rounded data-cy-signup-submit style="margin: 0 auto;">
|
||||||
<template v-if="submitting">
|
<template v-if="submitting">
|
||||||
<MkLoading :em="true" :colored="false"/>
|
<MkLoading :em="true" :colored="false"/>
|
||||||
|
|
|
@ -22,6 +22,7 @@
|
||||||
"isolatedModules": true,
|
"isolatedModules": true,
|
||||||
"useDefineForClassFields": true,
|
"useDefineForClassFields": true,
|
||||||
"verbatimModuleSyntax": true,
|
"verbatimModuleSyntax": true,
|
||||||
|
"skipLibCheck": true,
|
||||||
"baseUrl": ".",
|
"baseUrl": ".",
|
||||||
"paths": {
|
"paths": {
|
||||||
"@/*": ["./src/*"],
|
"@/*": ["./src/*"],
|
||||||
|
@ -46,8 +47,6 @@
|
||||||
},
|
},
|
||||||
"compileOnSave": false,
|
"compileOnSave": false,
|
||||||
"include": [
|
"include": [
|
||||||
"./build.ts",
|
|
||||||
"./lib/**/*.ts",
|
|
||||||
"./src/**/*.ts",
|
"./src/**/*.ts",
|
||||||
"./src/**/*.vue",
|
"./src/**/*.vue",
|
||||||
"./test/**/*.ts",
|
"./test/**/*.ts",
|
||||||
|
@ -55,7 +54,6 @@
|
||||||
"./@types/**/*.ts"
|
"./@types/**/*.ts"
|
||||||
],
|
],
|
||||||
"exclude": [
|
"exclude": [
|
||||||
".storybook/**/*",
|
|
||||||
"./src/**/*.stories.ts"
|
"./src/**/*.stories.ts"
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
|
@ -3538,6 +3538,7 @@ type SignupRequest = {
|
||||||
'g-recaptcha-response'?: string | null;
|
'g-recaptcha-response'?: string | null;
|
||||||
'turnstile-response'?: string | null;
|
'turnstile-response'?: string | null;
|
||||||
'm-captcha-response'?: string | null;
|
'm-captcha-response'?: string | null;
|
||||||
|
'testcaptcha-response'?: string | null;
|
||||||
};
|
};
|
||||||
|
|
||||||
// @public (undocumented)
|
// @public (undocumented)
|
||||||
|
|
|
@ -269,6 +269,7 @@ export type SignupRequest = {
|
||||||
'g-recaptcha-response'?: string | null;
|
'g-recaptcha-response'?: string | null;
|
||||||
'turnstile-response'?: string | null;
|
'turnstile-response'?: string | null;
|
||||||
'm-captcha-response'?: string | null;
|
'm-captcha-response'?: string | null;
|
||||||
|
'testcaptcha-response'?: string | null;
|
||||||
};
|
};
|
||||||
|
|
||||||
export type SignupResponse = MeDetailed & {
|
export type SignupResponse = MeDetailed & {
|
||||||
|
|
484
pnpm-lock.yaml
484
pnpm-lock.yaml
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue