Skip to content

Commit 6dd6fcf

Browse files
enhance(frontend): サーバー情報・お問い合わせページを改修 (#14198)
* improve(frontend): サーバー情報・お問い合わせページを改修 (#238) * Revert "Revert "enhance(frontend): add contact page" (#208)" (This reverts commit 5a329a0.) * improve(frontend): サーバー情報・お問い合わせページを改修 (cherry picked from commit e72758d) * fix * Update Changelog * tweak * lint * 既存の翻訳を使用するように --------- Co-authored-by: taiy <[email protected]>
1 parent 31e82fc commit 6dd6fcf

File tree

7 files changed

+250
-220
lines changed

7 files changed

+250
-220
lines changed

CHANGELOG.md

+2
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,8 @@
1616
- Enhance: 非ログイン時のハイライトTLのデザインを改善
1717
- Enhance: フロントエンドのアクセシビリティ改善
1818
(Based on https://github.com/taiyme/misskey/pull/226)
19+
- Enhance: サーバー情報ページ・お問い合わせページを改善
20+
(Cherry-picked from https://github.com/taiyme/misskey/pull/238)
1921
- Fix: `/about#federation` ページなどで各インスタンスのチャートが表示されなくなっていた問題を修正
2022
- Fix: ユーザーページの追加情報のラベルを投稿者のサーバーの絵文字で表示する (#13968)
2123
- Fix: リバーシの対局を正しく共有できないことがある問題を修正

packages/frontend/src/components/MkMenu.vue

+1
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@ SPDX-License-Identifier: AGPL-3.0-only
5454
:class="['_button', $style.item]"
5555
:href="item.href"
5656
:target="item.target"
57+
:rel="item.target === '_blank' ? 'noopener noreferrer' : undefined"
5758
:download="item.download"
5859
@click.passive="close(true)"
5960
@mouseenter.passive="onItemMouseEnter"

packages/frontend/src/components/MkVisitorDashboard.vue

+4-7
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ SPDX-License-Identifier: AGPL-3.0-only
2323
</div>
2424
<div class="_gaps_s" :class="$style.mainActions">
2525
<MkButton :class="$style.mainAction" full rounded gradate data-cy-signup style="margin-right: 12px;" @click="signup()">{{ i18n.ts.joinThisServer }}</MkButton>
26-
<MkButton :class="$style.mainAction" full rounded @click="exploreOtherServers()">{{ i18n.ts.exploreOtherServers }}</MkButton>
26+
<MkButton :class="$style.mainAction" full rounded link to="https://misskey-hub.net/servers/">{{ i18n.ts.exploreOtherServers }}</MkButton>
2727
<MkButton :class="$style.mainAction" full rounded data-cy-signin @click="signin()">{{ i18n.ts.login }}</MkButton>
2828
</div>
2929
</div>
@@ -65,7 +65,8 @@ import { i18n } from '@/i18n.js';
6565
import { instance } from '@/instance.js';
6666
import MkNumber from '@/components/MkNumber.vue';
6767
import XActiveUsersChart from '@/components/MkVisitorDashboard.ActiveUsersChart.vue';
68-
import { openInstanceMenu } from '@/ui/_common_/common';
68+
import { openInstanceMenu } from '@/ui/_common_/common.js';
69+
import type { MenuItem } from '@/types/menu.js';
6970

7071
const stats = ref<Misskey.entities.StatsResponse | null>(null);
7172

@@ -89,13 +90,9 @@ function signup() {
8990
});
9091
}
9192

92-
function showMenu(ev) {
93+
function showMenu(ev: MouseEvent) {
9394
openInstanceMenu(ev);
9495
}
95-
96-
function exploreOtherServers() {
97-
window.open('https://misskey-hub.net/servers/', '_blank', 'noopener');
98-
}
9996
</script>
10097

10198
<style lang="scss" module>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,205 @@
1+
<!--
2+
SPDX-FileCopyrightText: syuilo and misskey-project
3+
SPDX-License-Identifier: AGPL-3.0-only
4+
-->
5+
6+
<template>
7+
<div class="_gaps_m">
8+
<div :class="$style.banner" :style="{ backgroundImage: `url(${ instance.bannerUrl })` }">
9+
<div style="overflow: clip;">
10+
<img :src="instance.iconUrl ?? instance.faviconUrl ?? '/favicon.ico'" alt="" :class="$style.bannerIcon"/>
11+
<div :class="$style.bannerName">
12+
<b>{{ instance.name ?? host }}</b>
13+
</div>
14+
</div>
15+
</div>
16+
17+
<MkKeyValue>
18+
<template #key>{{ i18n.ts.description }}</template>
19+
<template #value><div v-html="instance.description"></div></template>
20+
</MkKeyValue>
21+
22+
<FormSection>
23+
<div class="_gaps_m">
24+
<MkKeyValue :copy="version">
25+
<template #key>Misskey</template>
26+
<template #value>{{ version }}</template>
27+
</MkKeyValue>
28+
<div v-html="i18n.tsx.poweredByMisskeyDescription({ name: instance.name ?? host })">
29+
</div>
30+
<FormLink to="/about-misskey">
31+
<template #icon><i class="ti ti-info-circle"></i></template>
32+
{{ i18n.ts.aboutMisskey }}
33+
</FormLink>
34+
<FormLink v-if="instance.repositoryUrl || instance.providesTarball" :to="instance.repositoryUrl || `/tarball/misskey-${version}.tar.gz`" external>
35+
<template #icon><i class="ti ti-code"></i></template>
36+
{{ i18n.ts.sourceCode }}
37+
</FormLink>
38+
<MkInfo v-else warn>
39+
{{ i18n.ts.sourceCodeIsNotYetProvided }}
40+
</MkInfo>
41+
</div>
42+
</FormSection>
43+
44+
<FormSection>
45+
<div class="_gaps_m">
46+
<FormSplit>
47+
<MkKeyValue :copy="instance.maintainerName">
48+
<template #key>{{ i18n.ts.administrator }}</template>
49+
<template #value>
50+
<template v-if="instance.maintainerName">{{ instance.maintainerName }}</template>
51+
<span v-else style="opacity: 0.7;">({{ i18n.ts.none }})</span>
52+
</template>
53+
</MkKeyValue>
54+
<MkKeyValue :copy="instance.maintainerEmail">
55+
<template #key>{{ i18n.ts.contact }}</template>
56+
<template #value>
57+
<template v-if="instance.maintainerEmail">{{ instance.maintainerEmail }}</template>
58+
<span v-else style="opacity: 0.7;">({{ i18n.ts.none }})</span>
59+
</template>
60+
</MkKeyValue>
61+
<MkKeyValue>
62+
<template #key>{{ i18n.ts.inquiry }}</template>
63+
<template #value>
64+
<MkLink v-if="instance.inquiryUrl" :url="instance.inquiryUrl" target="_blank">{{ instance.inquiryUrl }}</MkLink>
65+
<span v-else style="opacity: 0.7;">({{ i18n.ts.none }})</span>
66+
</template>
67+
</MkKeyValue>
68+
</FormSplit>
69+
<div class="_gaps_s">
70+
<FormLink v-if="instance.impressumUrl" :to="instance.impressumUrl" external>
71+
<template #icon><i class="ti ti-user-shield"></i></template>
72+
<template #default>{{ i18n.ts.impressum }}</template>
73+
</FormLink>
74+
<MkFolder v-if="instance.serverRules.length > 0">
75+
<template #icon><i class="ti ti-checkup-list"></i></template>
76+
<template #label>{{ i18n.ts.serverRules }}</template>
77+
<ol class="_gaps_s" :class="$style.rules">
78+
<li v-for="item in instance.serverRules" :key="item" :class="$style.rule">
79+
<div :class="$style.ruleText" v-html="item"></div>
80+
</li>
81+
</ol>
82+
</MkFolder>
83+
<FormLink v-if="instance.tosUrl" :to="instance.tosUrl" external>
84+
<template #icon><i class="ti ti-license"></i></template>
85+
<template #default>{{ i18n.ts.termsOfService }}</template>
86+
</FormLink>
87+
<FormLink v-if="instance.privacyPolicyUrl" :to="instance.privacyPolicyUrl" external>
88+
<template #icon><i class="ti ti-shield-lock"></i></template>
89+
<template #default>{{ i18n.ts.privacyPolicy }}</template>
90+
</FormLink>
91+
<FormLink v-if="instance.feedbackUrl" :to="instance.feedbackUrl" external>
92+
<template #icon><i class="ti ti-message"></i></template>
93+
<template #default>{{ i18n.ts.feedback }}</template>
94+
</FormLink>
95+
</div>
96+
</div>
97+
</FormSection>
98+
99+
<FormSuspense v-slot="{ result: stats }" :p="initStats">
100+
<FormSection>
101+
<template #label>{{ i18n.ts.statistics }}</template>
102+
<FormSplit>
103+
<MkKeyValue>
104+
<template #key>{{ i18n.ts.users }}</template>
105+
<template #value>{{ number(stats.originalUsersCount) }}</template>
106+
</MkKeyValue>
107+
<MkKeyValue>
108+
<template #key>{{ i18n.ts.notes }}</template>
109+
<template #value>{{ number(stats.originalNotesCount) }}</template>
110+
</MkKeyValue>
111+
</FormSplit>
112+
</FormSection>
113+
</FormSuspense>
114+
115+
<FormSection>
116+
<template #label>Well-known resources</template>
117+
<div class="_gaps_s">
118+
<FormLink to="/.well-known/host-meta" external>host-meta</FormLink>
119+
<FormLink to="/.well-known/host-meta.json" external>host-meta.json</FormLink>
120+
<FormLink to="/.well-known/nodeinfo" external>nodeinfo</FormLink>
121+
<FormLink to="/robots.txt" external>robots.txt</FormLink>
122+
<FormLink to="/manifest.json" external>manifest.json</FormLink>
123+
</div>
124+
</FormSection>
125+
</div>
126+
</template>
127+
128+
<script lang="ts" setup>
129+
import { host, version } from '@/config.js';
130+
import { i18n } from '@/i18n.js';
131+
import { instance } from '@/instance.js';
132+
import number from '@/filters/number.js';
133+
import { misskeyApi } from '@/scripts/misskey-api.js';
134+
import FormLink from '@/components/form/link.vue';
135+
import FormSection from '@/components/form/section.vue';
136+
import FormSplit from '@/components/form/split.vue';
137+
import FormSuspense from '@/components/form/suspense.vue';
138+
import MkFolder from '@/components/MkFolder.vue';
139+
import MkKeyValue from '@/components/MkKeyValue.vue';
140+
import MkLink from '@/components/MkLink.vue';
141+
142+
const initStats = () => misskeyApi('stats', {});
143+
</script>
144+
145+
<style lang="scss" module>
146+
.banner {
147+
text-align: center;
148+
border-radius: 10px;
149+
overflow: clip;
150+
background-color: var(--panel);
151+
background-size: cover;
152+
background-position: center center;
153+
}
154+
155+
.bannerIcon {
156+
display: block;
157+
margin: 16px auto 0 auto;
158+
height: 64px;
159+
border-radius: 8px;
160+
}
161+
162+
.bannerName {
163+
display: block;
164+
padding: 16px;
165+
color: #fff;
166+
text-shadow: 0 0 8px #000;
167+
background: linear-gradient(transparent, rgba(0, 0, 0, 0.7));
168+
}
169+
170+
.rules {
171+
counter-reset: item;
172+
list-style: none;
173+
padding: 0;
174+
margin: 0;
175+
}
176+
177+
.rule {
178+
display: flex;
179+
gap: 8px;
180+
word-break: break-word;
181+
182+
&::before {
183+
flex-shrink: 0;
184+
display: flex;
185+
position: sticky;
186+
top: calc(var(--stickyTop, 0px) + 8px);
187+
counter-increment: item;
188+
content: counter(item);
189+
width: 32px;
190+
height: 32px;
191+
line-height: 32px;
192+
background-color: var(--accentedBg);
193+
color: var(--accent);
194+
font-size: 13px;
195+
font-weight: bold;
196+
align-items: center;
197+
justify-content: center;
198+
border-radius: 999px;
199+
}
200+
}
201+
202+
.ruleText {
203+
padding-top: 6px;
204+
}
205+
</style>

0 commit comments

Comments
 (0)