feat(docs): document add changelog page (#3596)

* feat(docs): document add changelog page

- Add changelog and markdown component for changelog.md
- Add changelog page
- Add some locale for change log
- Fix a bug that caused ToC not working

* Add minimal width to changelog selector

* Add width to changelog selector

* fix selector width issue
This commit is contained in:
jeremywu
2021-09-24 01:19:18 +08:00
committed by GitHub
parent ae5c119665
commit 9408e7eb76
16 changed files with 300 additions and 30 deletions

View File

@@ -0,0 +1,5 @@
{
"published-by": "Published by",
"open-link": "Open link",
"select-version": "Select a version"
}

View File

@@ -0,0 +1,4 @@
{
"edit-on-github": "Edit this page on GitHub",
"edit-on-crowdin": "Edit this page on Crowdin"
}

View File

@@ -20,7 +20,11 @@
{ "text": "i18n", "link": "/guide/i18n" },
{ "text": "Migration", "link": "/guide/migration" },
{ "text": "Theming", "link": "/guide/theming" },
{ "text": "Built-in Transitions", "link": "/guide/transitions" }
{ "text": "Built-in Transitions", "link": "/guide/transitions" },
{
"text": "Changelog",
"link": "/guide/changelog"
}
]
}
}

View File

@@ -1,15 +1,24 @@
;(() => {
const supportedLangs = window.supportedLangs
let userPreferredLang = localStorage.getItem('preferred_lang')
const userPreferredLang =
localStorage.getItem('preferred_lang') || navigator.language
if (!userPreferredLang) {
const systemLang = navigator.language
localStorage.setItem('preferred_lang', systemLang)
userPreferredLang = systemLang
}
if (
supportedLangs.includes(userPreferredLang) &&
!location.pathname.startsWith(`/${userPreferredLang}`)
) {
location.pathname = [`/${userPreferredLang}`]
const toPath = [`/${userPreferredLang}`]
.concat(location.pathname.split('/').slice(2))
.join('/')
location.pathname = toPath.endsWith('.html')
? toPath
: toPath.endsWith('/')
? toPath
: toPath.concat('/')
}
})()

View File

@@ -0,0 +1,33 @@
<script lang="ts" setup>
import { computed } from 'vue'
import marked from 'marked'
const props = defineProps({
content: String,
})
const attr = 'rel="noreferrer noopenner" target="_blank"'
const parsed = computed(() => {
// Note this is relatively arbitrary so that this could be buggy.
return marked(props.content)
.replace(
/#([0-9]+) by/g,
`<a href="https://github.com/element-plus/element-plus/pull/$1" ${attr}>#$1</a> by`
)
.replace(
/@([A-Za-z0-9_-]+)/g,
`<a href="https://github.com/$1" ${attr}>@$1</a>`
)
})
</script>
<template>
<div class="markdown-wrapper" v-html="parsed" />
</template>
<style>
.markdown-wrapper h3 {
margin-top: 1rem;
}
</style>

View File

@@ -22,7 +22,7 @@ useActiveSidebarLinks(container, marker)
<a class="toc-link" :href="link">{{ text }}</a>
<ul v-if="children">
<li
v-for="{ childLink, childText } in children"
v-for="{ link: childLink, text: childText } in children"
:key="childLink"
class="toc-item"
>

View File

@@ -0,0 +1,118 @@
<script setup lang="ts">
import { onMounted, ref } from 'vue'
import axios from 'axios'
import VPLink from '../common/vp-link.vue'
import VPMarkdown from '../common/vp-markdown.vue'
import { useLang } from '../../composables/lang'
import { useLocale } from '../../composables/locale'
import changelogLocale from '../../../i18n/component/changelog.json'
const loading = ref(true)
const releases = ref([])
const currentRelease = ref()
const changelog = useLocale(changelogLocale)
const lang = useLang()
const onVersionChange = (val) => {
const _releases = releases.value
currentRelease.value = _releases[_releases.findIndex((r) => r.name === val)]
}
onMounted(async () => {
try {
const { data } = await axios.get(
'https://api.github.com/repos/element-plus/element-plus/releases'
)
releases.value = data
currentRelease.value = data[0]
} catch (e) {
releases.value = []
currentRelease.value = undefined
// do something
} finally {
loading.value = false
}
})
</script>
<template>
<div class="changelogs">
<ClientOnly>
<ElSkeleton :loading="loading">
<div class="changelog-versions">
<p>{{ changelog['select-version'] }}:</p>
<ElSelect
:model-value="currentRelease.name"
:placeholder="changelog['select-version']"
style="min-width: 200px"
@change="onVersionChange"
>
<ElOption
v-for="release in releases"
:key="release.id"
:value="release.name"
>
{{ release.name }}
</ElOption>
</ElSelect>
</div>
<ElCard v-if="currentRelease">
<template #header>
<div class="changelog-header">
<div class="changelog-meta">
<p class="changelog-by">
{{ changelog['published-by'] }}
<strong>{{ currentRelease.author.login }}</strong>
</p>
<p class="changelog-date">
{{
new Date(currentRelease.published_at).toLocaleString(lang)
}}
</p>
</div>
<div class="operators">
<VPLink :href="currentRelease.html_url">
{{ changelog['open-link'] }}
</VPLink>
</div>
</div>
</template>
<div>
<VPMarkdown :content="currentRelease.body" />
</div>
</ElCard>
</ElSkeleton>
</ClientOnly>
</div>
</template>
<style lang="scss" scoped>
.changelog-versions {
display: flex;
align-items: center;
justfy-content: space-between;
margin-bottom: 1rem;
p {
margin-right: 2rem;
}
}
.changelog-header {
display: flex;
align-items: flex-start;
justfy-content: space-between;
.changelog-meta {
display: flex;
flex: 1;
flex-direction: column;
p {
margin: 0;
}
}
.link-item {
line-height: 1.7;
}
}
</style>

View File

@@ -1,30 +1,55 @@
import { computed } from 'vue'
import { useData } from 'vitepress'
import { createGitHubUrl } from '../utils'
import { useLang } from '../composables/lang'
import { useLocale } from '../composables/locale'
import { defaultLang } from '../constant'
import { createGitHubUrl, createCrowdinUrl } from '../utils'
import editLinkLocale from '../../i18n/component/edit-link.json'
export function useEditLink() {
const { page, theme, frontmatter } = useData()
const lang = useLang()
const editLink = useLocale(editLinkLocale)
const canEditSource = computed(() => {
return lang.value === defaultLang
})
const url = computed(() => {
const {
repo,
docsDir = '',
docsBranch = 'dev',
docsRepo = repo,
editLinks,
} = theme.value
const showEditLink =
frontmatter.value.editLink != null
? frontmatter.value.editLink
: editLinks
const { relativePath } = page.value
if (!showEditLink || !relativePath || !repo) {
return null
if (canEditSource.value) {
const {
repo,
docsDir = '',
docsBranch = 'dev',
docsRepo = repo,
editLinks,
} = theme.value
const showEditLink =
frontmatter.value.editLink != null
? frontmatter.value.editLink
: editLinks
const { relativePath } = page.value
if (!showEditLink || !relativePath || !repo) {
return null
}
return createGitHubUrl(
docsRepo,
docsDir,
docsBranch,
relativePath,
'',
''
)
}
return createGitHubUrl(docsRepo, docsDir, docsBranch, relativePath, '', '')
return createCrowdinUrl(lang.value)
})
const text = computed(() => {
return theme.value.editLinkText || 'Edit this page'
return canEditSource.value
? editLink.value['edit-on-github']
: editLink.value['edit-on-crowdin']
})
return {
url,
text,

View File

@@ -0,0 +1,9 @@
import { computed } from 'vue'
import { useLang } from './lang'
export const useLocale = (
localeJson: Record<string, Record<string, string>>
) => {
const lang = useLang()
return computed(() => localeJson[lang.value])
}

View File

@@ -6,6 +6,7 @@ import './styles/app.scss'
import VPApp from './components/vp-app.vue'
import VPDemo from './components/vp-demo.vue'
import Changelog from './components/globals/vp-changelog.vue'
import MainColor from './components/globals/main-color.vue'
import NeutralColor from './components/globals/neutral-color.vue'
import SecondaryColors from './components/globals/secondary-colors.vue'
@@ -19,4 +20,5 @@ export const globals = [
['NeutralColor', NeutralColor],
['SecondaryColors', SecondaryColors],
['IconList', IconList],
['Changelog', Changelog],
]

View File

@@ -0,0 +1,3 @@
.hero-content {
padding: 55px 40px 0;
}

View File

@@ -4,6 +4,7 @@ import {
endingSlashRE,
isExternal,
} from 'vitepress/dist/client/theme-default/utils'
import type { Route } from 'vitepress'
export * from 'vitepress/dist/client/theme-default/utils'
@@ -56,3 +57,15 @@ export function createGitHubUrl(
}
export const isServer = typeof window === 'undefined'
export function createCrowdinUrl(targetLang: string) {
let translateLang = ''
// for zh-CN zh-HK zh-TW, maybe later we will have cases like Chinese lang
// for now we just keep it as simple as possible.
if (targetLang.startsWith('zh-')) {
translateLang = targetLang.split('-').join('').toLocaleLowerCase()
} else {
translateLang = targetLang.split('-').shift().toLocaleLowerCase()
}
return `https://crowdin.com/translate/element-plus/all/en-${translateLang}`
}

View File

@@ -0,0 +1,18 @@
---
title: 'Changelog'
---
<style scoped lang="scss">
@at-root .hero-content {
padding: 32px;
}
</style>
# Changelog
Element Plus team uses **weekly** release strategy under normal circumstance, but critical bug fixes would require hotfix so the actual release number **could be** more than 1 per week.
On this page you can only see the latest 30 records of our [changelog](https://github.com/element-plus/element-plus/blob/dev/CHANGELOG.en-US.md).
<Changelog />

View File

@@ -16,7 +16,7 @@
class="input-with-select"
>
<template #prepend>
<el-select v-model="select" placeholder="Select">
<el-select v-model="select" placeholder="Select" style="width: 110px">
<el-option label="Restaurant" value="1"></el-option>
<el-option label="Order No." value="2"></el-option>
<el-option label="Tel" value="3"></el-option>
@@ -44,9 +44,6 @@ export default defineComponent({
</script>
<style>
.el-select .el-input {
width: 110px;
}
.input-with-select .el-input-group__prepend {
background-color: #fff;
}

View File

@@ -8,7 +8,9 @@
},
"dependencies": {
"@vueuse/core": "^6.4.0",
"axios": "^0.21.4",
"element-plus": "npm:element-plus@latest",
"marked": "^3.0.4",
"normalize.css": "^8.0.1",
"nprogress": "^0.2.0"
},

36
pnpm-lock.yaml generated
View File

@@ -185,13 +185,17 @@ importers:
specifiers:
'@crowdin/cli': ^3.6.5
'@vueuse/core': ^6.4.0
axios: ^0.21.4
element-plus: npm:element-plus@latest
marked: ^3.0.4
normalize.css: ^8.0.1
nprogress: ^0.2.0
vitepress: ^0.17.2
dependencies:
'@vueuse/core': 6.4.1_vue@3.2.6
element-plus: 1.1.0-beta.14_vue@3.2.6
axios: 0.21.4
element-plus: 1.1.0-beta.15_vue@3.2.6
marked: 3.0.4
normalize.css: 8.0.1
nprogress: 0.2.0
devDependencies:
@@ -3740,6 +3744,14 @@ packages:
resolution: {integrity: sha512-zg7Hz2k5lI8kb7U32998pRRFin7zJlkfezGJjUc2heaD4Pw2wObakCDVzkKztTm/Ln7eiVvYsjqak0Ed4LkMDA==}
dev: true
/axios/0.21.4:
resolution: {integrity: sha512-ut5vewkiu8jjGBdqpM44XxjuCjq9LAKeHVmoVfHVzy8eHgxxq8SbAVQNovDA8mVi05kP0Ea/n/UzcSHcTJQfNg==}
dependencies:
follow-redirects: 1.14.4
transitivePeerDependencies:
- debug
dev: false
/babel-helper-vue-jsx-merge-props/2.0.3:
resolution: {integrity: sha512-gsLiKK7Qrb7zYJNgiXKpXblxbV5ffSwR0f5whkPAaBAR4fhi6bwRZxX9wBlIc5M/v8CCkXUbXZL4N/nSE97cqg==}
dev: true
@@ -5117,17 +5129,17 @@ packages:
resolution: {integrity: sha512-2jtSwgyiRzybHRxrc2nKI+39wH3AwQgn+sogQ+q814gv8hIFwrcZbV07Ea9f8AmK0ufPVZUvvAG1uZJ+obV4Jw==}
dev: true
/element-plus/1.1.0-beta.14_vue@3.2.6:
resolution: {integrity: sha512-LtAKw33mGhKfLhEhhDvY2rCwFvhc/fBusFetwxh/fuDIHwkA7gR9J+ygcMUX+OLcCUc8IZDhVH6umUaM7fK1Hw==}
/element-plus/1.1.0-beta.15_vue@3.2.6:
resolution: {integrity: sha512-VK0gFtMqeGdR3/Y/Jm49X15oo8QZbmWOwPVEgWYgrWgUk3NeRo4GYed3BXQdZW5EOOlaGMuho9scgefX+Ys+oA==}
peerDependencies:
vue: ^3.2.0
dependencies:
'@element-plus/icons': 0.0.11
'@popperjs/core': 2.10.1
'@vueuse/core': 6.1.0_vue@3.2.6
async-validator: 3.4.0
dayjs: 1.10.6
lodash: 4.17.21
memoize-one: 5.2.1
normalize-wheel: 1.0.1
resize-observer-polyfill: 1.5.1
vue: 3.2.6
@@ -5954,6 +5966,16 @@ packages:
readable-stream: 2.3.7
dev: true
/follow-redirects/1.14.4:
resolution: {integrity: sha512-zwGkiSXC1MUJG/qmeIFH2HBJx9u0V46QGUe3YR1fXG8bXQxq7fLj0RjLZQ5nubr9qNJUZrH+xUcwXEoXNpfS+g==}
engines: {node: '>=4.0'}
peerDependencies:
debug: '*'
peerDependenciesMeta:
debug:
optional: true
dev: false
/for-in/1.0.2:
resolution: {integrity: sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=}
engines: {node: '>=0.10.0'}
@@ -8257,6 +8279,12 @@ packages:
uc.micro: 1.0.6
dev: true
/marked/3.0.4:
resolution: {integrity: sha512-jBo8AOayNaEcvBhNobg6/BLhdsK3NvnKWJg33MAAPbvTWiG4QBn9gpW1+7RssrKu4K1dKlN+0goVQwV41xEfOA==}
engines: {node: '>= 12'}
hasBin: true
dev: false
/matchdep/2.0.0:
resolution: {integrity: sha1-xvNINKDY28OzfCfui7yyfHd1WC4=}
engines: {node: '>= 0.10.0'}