一文搭建自己博客/文档系统:搭建,自动编译和部署,域名,HTTPS,备案等
<blockquote><p>本文纯原创,搭建后的博客/文档网站可以参考: Java 全栈知识体系。如需转载请说明原处。</p>
</blockquote>
<h1 id="文章内容目录">文章内容目录</h1>
<ul>
<li>第一部分 - 博客/文档系统的搭建
<ul>
<li>博客/文档搭建前言
<ul>
<li>有哪些选择</li>
<li>我做了哪些尝试
<ul>
<li>自己写:我用java手写了一个系统</li>
<li>Docisify等工具</li>
<li>博客园等平台</li>
</ul>
</li>
<li>为什么现在用vuepress</li>
</ul>
</li>
<li>博客/文档工具vuepress介绍
<ul>
<li>vuepress是如何工作的?</li>
<li>vuepress 一些特性</li>
<li>vuepress 插件架构</li>
</ul>
</li>
<li>博客/文档基础搭建
<ul>
<li>brew安装或者更新</li>
<li>更新node和npm</li>
<li>配置vuepress工作目录</li>
<li>添加配置和内容</li>
</ul>
</li>
<li>文档搭建插件和配置
<ul>
<li>添加文档附加样式配置: 主题</li>
<li>添加返回最上插件</li>
<li>添加图片缩放插件</li>
<li>添加评论插件</li>
<li>添加Vuepress文档的导出</li>
<li>添加svg label标签</li>
<li>添加百度统计</li>
<li>添加Copy自动加版权信息</li>
<li>添加SEO优化</li>
<li>添加百度站点自动推送</li>
<li>添加Sitemap信息</li>
<li>添加代码拷贝</li>
<li>更多插件配置</li>
</ul>
</li>
<li>博客/文档稍完整配置清单</li>
<li>vuepress 其它参考资源</li>
</ul>
</li>
<li>第二部分 - 博客/文档的自动编译
<ul>
<li>Travis CI
<ul>
<li>Github 启用插件</li>
<li>配置插件</li>
<li>添加.travis.yml</li>
<li>触发编译</li>
<li>查看最后提交编译状况</li>
<li>生成build 状态svg</li>
</ul>
</li>
</ul>
</li>
<li>第三部分 - 博客/文档的自动部署
<ul>
<li>文档编译和部署流程</li>
<li>搭建
<ul>
<li>安装NodeJS</li>
<li>清理原有部分服务</li>
<li>安装Nginx和配置</li>
<li>部署项目</li>
</ul>
</li>
</ul>
</li>
<li>第四部分 - 博客/文档的域名,HTTPS,备案
<ul>
<li>申请域名</li>
<li>https</li>
<li>备案</li>
<li>服务器资源选择</li>
</ul>
</li>
</ul>
<h1 id="第一部分---博客文档系统的搭建">第一部分 - 博客/文档系统的搭建</h1>
<blockquote>
<p>搭建博客有很多选择,平台性的比如: 知名的CSDN, 博客园, 知乎,简书等;自己搭建比如 Hexo, Gitbook, Docisify等等。我有一颗不安分的心,每种我都用过...但是最后的最后我还是选择了将博客逐移至自己搭建的vuepress。 @pdai</p>
</blockquote>
<h2 id="博客文档搭建前言">博客/文档搭建前言</h2>
<h3 id="有哪些选择">有哪些选择</h3>
<p>搭建博客有很多选择,平台性的比如: 知名的CSDN, 博客园, 知乎,简书等;自己搭建比如 Hexo, Gitbook, Docisify等等。</p>
<h3 id="我做了哪些尝试">我做了哪些尝试</h3>
<ul>
<li>自己写:我用java手写了一个系统</li>
<li>Docisify等工具</li>
<li>博客园等平台</li>
</ul>
<h4 id="自己写我用java手写了一个系统">自己写:我用java手写了一个系统</h4>
<blockquote>
<p>以下系统由我独立设计,开发和运维(总计四万多行代码吧), 这里只展示博客文档部分。以下图片是我在之前博客园写文章截图的:</p>
</blockquote>
<ul>
<li>markdown编辑</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-choose-1.png" alt="" loading="lazy"></p>
<ul>
<li>文章清单</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-choose-2.png" alt="" loading="lazy"></p>
<ul>
<li>支持导出各种形式</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-choose-3.png" alt="" loading="lazy"></p>
<ul>
<li>支持共享给其它虚拟组织</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-choose-4.png" alt="" loading="lazy"></p>
<p>等等。</p>
<h4 id="docisify等工具">Docisify等工具</h4>
<blockquote>
<p>之前用搭建过基于K8S的完整的平台,写了系列的文章总结。用的工具就是用的Docisify。</p>
</blockquote>
<p>效果如下:</p>
<p><img src="https://www.pdai.tech/_images/blog/blog-choose-5.png" alt="" loading="lazy"></p>
<h4 id="博客园等平台">博客园等平台</h4>
<p>支持自定义样式,自定义js权限,这表明自由控制程度会很高(这点看CSDN就略保守了);但是网站长期没有更新,主页样式感觉停留在十年前;客户端程序,略有点low;</p>
<p>效果如下:</p>
<p><img src="https://www.pdai.tech/_images/blog/blog-choose-6.png" alt="" loading="lazy"></p>
<p>具体可以看我写的这篇:【博客园配置】博客园自定义配置有哪些骚操作</p>
<h3 id="为什么现在用vuepress">为什么现在用vuepress</h3>
<p>类似博客/文档工具比对vuepress可以看出其优势:以下内容摘自: Vuepress官网</p>
<ul>
<li>Nuxt</li>
</ul>
<p>VuePress 能做的事情,Nuxt 理论上确实能够胜任,但 Nuxt 是为构建应用程序而生的,而 VuePress 则专注在以内容为中心的静态网站上,同时提供了一些为技术文档定制的开箱即用的特性。</p>
<ul>
<li>Docsify / Docute</li>
</ul>
<p>这两个项目同样都是基于 Vue,然而它们都是完全的运行时驱动,因此对 SEO 不够友好。如果你并不关注 SEO,同时也不想安装大量依赖,它们仍然是非常好的选择!</p>
<ul>
<li>Hexo</li>
</ul>
<p>Hexo 一直驱动着 Vue 的文档 —— 事实上,在把我们的主站从 Hexo 迁移到 VuePress 之前,我们可能还有很长的路要走。Hexo 最大的问题在于他的主题系统太过于静态以及过度地依赖纯字符串,而我们十分希望能够好好地利用 Vue 来处理我们的布局和交互,同时,Hexo 的 Markdown 渲染的配置也不是最灵活的。</p>
<ul>
<li>GitBook</li>
</ul>
<p>我们的子项目文档一直都在使用 GitBook。GitBook 最大的问题在于当文件很多时,每次编辑后的重新加载时间长得令人无法忍受。它的默认主题导航结构也比较有限制性,并且,主题系统也不是 Vue 驱动的。GitBook 背后的团队如今也更专注于将其打造为一个商业产品而不是开源工具。</p>
<h2 id="博客文档工具vuepress介绍">博客/文档工具vuepress介绍</h2>
<p>VuePress 由两部分组成:第一部分是一个极简静态网站生成器,它包含由 Vue 驱动的<code>主题系统</code>和<code>插件 API</code>,另一个部分是为书写技术文档而优化的<code>默认主题</code>,它的诞生初衷是为了支持 Vue 及其子项目的文档需求。</p>
<p>每一个由 VuePress 生成的页面都带有预渲染好的 HTML,也因此具有非常好的加载性能和搜索引擎优化(SEO)。同时,一旦页面被加载,Vue 将接管这些静态内容,并将其转换成一个完整的单页应用(SPA),其他的页面则会只在用户浏览到的时候才按需加载。</p>
<h3 id="vuepress是如何工作的">vuepress是如何工作的?</h3>
<p>事实上,一个 VuePress 网站是一个由 Vue、Vue Router 和 webpack 驱动的单页应用。如果你以前使用过 Vue 的话,当你在开发一个自定义主题的时候,你会感受到非常熟悉的开发体验,你甚至可以使用 Vue DevTools 去调试你的自定义主题。</p>
<p>在构建时,我们会为应用创建一个服务端渲染(SSR)的版本,然后通过虚拟访问每一条路径来渲染对应的HTML。这种做法的灵感来源于 Nuxt 的 <code>nuxt generate</code> 命令,以及其他的一些项目,比如 Gatsby。</p>
<h3 id="vuepress-一些特性">vuepress 一些特性</h3>
<ul>
<li>为技术文档而优化的内置Markdown拓展</li>
<li>在Markdown文件中使用Vue组件的能力</li>
<li>Vue驱动的自定义主题系统</li>
<li>自动生成Service Worker(支持PWA)</li>
<li>Google Analytics集成</li>
<li>基于Git的"最后更新时间"</li>
<li>多语言支持</li>
<li>响应式布局</li>
<li>天然的SEO能力,对比Docsify这种前端渲染HTML要好很多</li>
</ul>
<h3 id="vuepress-插件架构">vuepress 插件架构</h3>
<p>其整体的插件架构案例: Vuepress 插件架构案例</p>
<p><img src="https://www.pdai.tech/_images/blog/blog-architecture.png" alt="" loading="lazy"></p>
<h2 id="博客文档基础搭建">博客/文档基础搭建</h2>
<blockquote>
<p>文档的搭建比较简单,主要记录流程,有些步骤你在阅读的时候如果觉得不需要, 可以直接略过。</p>
</blockquote>
<h3 id="brew安装或者更新">brew安装或者更新</h3>
<p>先卸载已安装的homebrew,命令如下:</p>
<pre><code class="language-bash">/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/uninstall)"
</code></pre>
<p>然后重新安装:</p>
<pre><code class="language-bash">/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"
</code></pre>
<p>通过该方法直接获取最新的homebrew,出现预期效果。注:上述可以修复<code>chown: /usr/local: Operation not permitted</code>这个问题。</p>
<p>如果觉得慢,需要更换 Brew 镜像源, 请看考: 更换 Brew 镜像源</p>
<h3 id="更新node和npm">更新node和npm</h3>
<blockquote>
<p>Vuepress对Node版本要求: Node.js 版本 >= 8.6。</p>
</blockquote>
<ul>
<li>方法1:手动删除/usr/local/bin 下面的node和npm文件</li>
<li>方法2:覆盖现有版本brew link --overwrite node</li>
</ul>
<p>如有需要,请参考这两篇文章:</p>
<ul>
<li>mac 用brew升级node最新版本,npm出现问题问题解决</li>
<li>brew 升级 node版本</li>
</ul>
<h3 id="配置vuepress工作目录">配置vuepress工作目录</h3>
<ul>
<li>全局安装vuepress</li>
</ul>
<pre><code class="language-bash">yarn global add vuepress
</code></pre>
<ul>
<li>创建项目并初始化目录结构</li>
</ul>
<pre><code class="language-bash"># 目录
mkdir tech-arch-doc
cd tech-arch-doc
# 初始化
yarn init -y # 或者 npm init -y
# 放markdown的文件夹
mkdir md
# package.json, 里面放的内容看后文
touch package.json
# 放vuepress相关
mkdir .vuepress
cd .vuepress
# 创建config.js, 里面放的内容看后文
touch config.js
# 放图片和CNAME
mkdir public
# 放样式的
mkdir styles
# 在里面创建放图片
cd public
mkdir _images
</code></pre>
<p>最后的结构大概是这样:(其它灰色的文件夹是编译出来的)</p>
<p><img src="https://www.pdai.tech/_images/blog/blog-struct-1.png" alt="" loading="lazy"></p>
<h3 id="添加配置和内容">添加配置和内容</h3>
<ul>
<li>添加主页面</li>
</ul>
<pre><code class="language-java">---
home: true
heroImage: /_images/index-read.gif
actionText: 快速开始 →
actionLink: /md/java/basic/java-basic-oop.md
features:
- title: 夯实基础
details: 不积跬步无以至千里, 仰望星空还需脚踏实地
- title: 构建体系
details: 告别碎片化学习,帮助你构筑你自己的知识体系
- title: 全栈开发
details: 以Java开发为背景,全栈开发,DevOps
footer: © 2017-present pdai
---
</code></pre>
<ul>
<li>config.js配置</li>
</ul>
<pre><code class="language-js">module.exports = {
port: "3000",
dest: "docs",
ga: "UA-xxxxx-1",
base: "/",
markdown: {
lineNumbers: true,
externalLinks: {
target: '_blank', rel: 'noopener noreferrer'
}
},
locales: {
"/": {
lang: "zh-CN",
title: "Java 全栈知识体系",
description: "包含: Java 基础, Java 部分源码, JVM, Spring, Spring Boot, Spring Cloud, 数据库原理, MySQL, ElasticSearch, MongoDB, Docker, k8s, CI&CD, Linux, DevOps, 分布式, 中间件, 开发工具, Git, IDE, 源码阅读,读书笔记, 开源项目..."
}
},
head: [
// ico
["link", {rel: "icon", href: `/favicon.ico`}],
// meta
["meta", {name: "robots", content: "all"}],
["meta", {name: "author", content: "pdai"}],
["meta", {name: "keywords", content: "Java 全栈知识体系, java体系, java知识体系, java框架,java详解,java学习路线,java spring, java面试, 知识体系, java技术体系, java编程, java编程指南,java开发体系, java开发,java教程,java,java数据结构, 算法, 开发基础"}],
["meta", {name: "apple-mobile-web-app-capable", content: "yes"}]
],
plugins: [
],
themeConfig: {
// repo: "realpdai/tech-arch-doc",
docsRepo: "realpdai/tech-arch-doc",
// logo: "/logo.png",
editLinks: true,
sidebarDepth:0,
locales: {
"/": {
label: "简体中文",
selectText: "Languages",
editLinkText: "在 GitHub 上编辑此页",
lastUpdated: "上次更新",
nav: [
],
sidebar: {
}
}
}
}
};
</code></pre>
<ul>
<li>package.json配置</li>
</ul>
<p>进入项目目录</p>
<pre><code class="language-json">{
"name": "tech-arch-doc",
"version": "0.0.1",
"private": true,
"scripts": {
"dev": "vuepress dev",
"build": "vuepress build"
},
"devDependencies": {
"vuepress": "^1.0.2"
}
}
</code></pre>
<ul>
<li>本地测试</li>
</ul>
<pre><code class="language-bash">vuepress dev
</code></pre>
<p>初步效果:</p>
<p><img src="https://www.pdai.tech/_images/blog/blog-try-1.png" alt="" loading="lazy"></p>
<ul>
<li>要生成静态的 HTML 文件,运行:</li>
</ul>
<blockquote>
<p>默认情况下,文件将会被生成在 .vuepress/dist,当然,你也可以通过 .vuepress/config.js 中的 dest 字段来修改,生成的文件可以部署到任意的静态文件服务器上</p>
</blockquote>
<p>请参考官网 https://vuepress.vuejs.org/zh/guide/getting-started.html#全局安装</p>
<pre><code class="language-bash">vuepress build
</code></pre>
<h2 id="文档搭建插件和配置">文档搭建插件和配置</h2>
<blockquote>
<p>这里主要介绍文档搭建除了默认加载的配置和插件之外,新增加的插件和配置。</p>
</blockquote>
<h3 id="添加文档附加样式配置-主题">添加文档附加样式配置: 主题</h3>
<blockquote>
<p>注意很多网上的例子还是基于老的版本的,甚至我用vuepress的时候,官网还没有更新过来。</p>
</blockquote>
<p>最佳配置请参考: 这里: (其它官网的配置都没有更新)</p>
<ul>
<li>index.styl - 覆盖的样式</li>
</ul>
<pre><code class="language-stylus">.custom-page-class{
/* 自定义的样式 */
}
// markdown blockquote
blockquote
font-size 1rem
color #2c3e50;
border-left .5rem solid #42b983
background-color #f3f5f7
margin 1rem 0
padding 1rem 0 1rem 1rem
& > p
margin 0
// markdown h2
h2
font-size 1.65rem
padding-bottom 1rem
border-bottom 1px solid $borderColor
</code></pre>
<ul>
<li>palette.styl - 样式配置覆盖</li>
</ul>
<pre><code class="language-stylus">// 内容的宽度
$contentWidth = 100%
// 颜色
$accentColor = #3eaf7c
$textColor = #2c3e50
$borderColor = #eaecef
$codeBgColor = #282c34
</code></pre>
<h3 id="添加返回最上插件">添加返回最上插件</h3>
<blockquote>
<p>文章很长,添加右下角一键返回顶部按钮,官网提供了 back-to-top 插件.</p>
</blockquote>
<p>安装</p>
<pre><code class="language-js">yarn add -D @vuepress/plugin-back-to-top@next
# OR npm install -D @vuepress/plugin-back-to-top@next
</code></pre>
<p>使用</p>
<pre><code class="language-js">module.exports = {
plugins: ['@vuepress/back-to-top']
}
</code></pre>
<p>插件使用你还可以参考:插件官网</p>
<h3 id="添加图片缩放插件">添加图片缩放插件</h3>
<blockquote>
<p>图片缩放可以使用@vuepress/plugin-medium-zoom插件,它基于medium-zoom 插件。</p>
</blockquote>
<pre><code class="language-bash">yarn add -D @vuepress/plugin-medium-zoom@next
# OR npm install -D @vuepress/plugin-medium-zoom@next
</code></pre>
<p>简单使用:</p>
<pre><code class="language-js">module.exports = {
plugins: ['@vuepress/medium-zoom']
}
</code></pre>
<p>自定义选项:</p>
<pre><code class="language-js">module.exports = {
plugins: {
'@vuepress/medium-zoom': {
selector: 'img.zoom-custom-imgs',
// medium-zoom options here
// See: https://github.com/francoischalifour/medium-zoom#options
options: {
margin: 16
}
}
}
}
</code></pre>
<p>效果可以点击本文中的图片查看, 具体使用你可以参考: 插件官网。</p>
<h3 id="添加评论插件">添加评论插件</h3>
<blockquote>
<p>代码托管平台遵从 OAuth 2 spec 提供了 OAuth API。Vssue 利用平台提供的 OAuth API,使得用户可以登录并发表评论。那么有哪些评论插件可以使用?这里使用Vssue,它比较新,可能知道的人还不多。@pdai</p>
</blockquote>
<p><strong>Vssue</strong> , <strong>Gitalk</strong> 和 <strong>Gitment</strong>,为何选择Vssue:</p>
<ul>
<li><strong>Vssue</strong> 支持 Github、Gitlab 和 Bitbucket,并且很容易扩展到其它平台。<strong>Gitment</strong> 和 <strong>Gitalk</strong> 仅支持 Github。</li>
<li><strong>Vssue</strong> 可以发表、编辑、删除评论。<strong>Gitment</strong> 和 <strong>Gitalk</strong> 仅能发表评论。</li>
<li><strong>Vssue</strong> 是基于 Vue.js 开发的,可以集成到 Vue 项目中,并且提供了一个 VuePress 插件。 <strong>Gitment</strong> 基于原生JS,而 <strong>Gitalk</strong> 基于 Preact。</li>
</ul>
<p>下面是 Vssue 的简要工作过程:</p>
<p><img src="https://www.pdai.tech/_images/blog/how-vssue-works-zh.png" alt="" loading="lazy"></p>
<p>用户在平台的授权页面允许 Vssue 接入后,平台会带有 <code>code</code> 或 <code>token</code> 重定向回 Vssue 的页面(如果是 <code>code</code> ,Vssue 则会根据 <code>code</code> 向平台请求 <code>token</code>)。</p>
<p>Vssue 获取 <code>token</code> 后,会将 <code>token</code> 存储在 localstorage 中,于是用户就成功使用平台的帐号“登录”到了 Vssue。</p>
<p>接下来, Vssue 就可以获取用户的基本信息、获取当前页面的评论,用户也可以发表评论了。</p>
<p>添加如下配置:具体参考Vssue 官网教程</p>
<pre><code class="language-js">plugins: {
'@vssue/vuepress-plugin-vssue': {
// 设置 `platform` 而不是 `api`
platform: 'github',
// 其他的 Vssue 配置
owner: 'OWNER_OF_REPO',
repo: 'NAME_OF_REPO',
clientId: 'YOUR_CLIENT_ID',
clientSecret: 'YOUR_CLIENT_SECRET',
},
},
</code></pre>
<p>效果如下:</p>
<p><img src="https://www.pdai.tech/_images/blog/blog-comments-1.png" alt="blog-comments" loading="lazy"></p>
<h3 id="添加vuepress文档的导出">添加Vuepress文档的导出</h3>
<blockquote>
<p>导出页面只在我本地开放,线上功能我暂时关闭了。</p>
</blockquote>
<p>自己写了文档PDF的导出功能(Page, Group, Current是我导出功能里的<code>代号</code>): Page = Group1+...GroupN, Group = Current1+...CurrentN</p>
<ul>
<li>当前页面导出</li>
<li>Group页面导出:主要用来导出一组或者多组章节下面的所有文章。</li>
<li>Page页面导出</li>
</ul>
<p>以SpringBoot部分章节导出为例,导出效果如下:</p>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-export-1.png" alt="" loading="lazy"></p>
<h3 id="添加svg-label标签">添加svg label标签</h3>
<p>你是不是常看到别人的项目中加了<img src="https://img.shields.io/badge/pdai-full%20stack-blue">这种标签?这种标签主要基于svg,主要有两种:</p>
<ul>
<li>比如Travis CI 提供的: 本网站Build结果</li>
<li>这个网站还可以定制:定制icon svg</li>
</ul>
<p>添加后效果(状态为自动获取):</p>
<img src="https://travis-ci.com/realpdai/tech-arch-doc.svg?branch=master">
<img src="https://img.shields.io/github/license/realpdai/tech-arch-doc">
<img src="https://img.shields.io/badge/pdai-full%20stack-blue">
<h3 id="添加百度统计">添加百度统计</h3>
<ul>
<li>百度统计主要辅助我分析页面访问量,直接去: 百度统计官网</li>
</ul>
<blockquote>
<p>注意百度统计添加, 考虑在每个页面点击时作记录,在enhanceApp.js中拦截router:</p>
</blockquote>
<pre><code class="language-js">export default ({router}) => {
router.beforeEach((to, from, next) => {
// @pdai: 对每个页面点击添加百度统计
if(typeof _hmt!='undefined'){
if (to.path) {
_hmt.push(['_trackPageview', to.fullPath]);
}
}
// continue
next();
})
};
</code></pre>
<p>百度统计里某个页面效果如下:</p>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-tongji-1.png" alt="" loading="lazy"></p>
<h3 id="添加copy自动加版权信息">添加Copy自动加版权信息</h3>
<blockquote>
<p>复制你网站时,禁用复制或者添加版权信息等。</p>
</blockquote>
<p>安装</p>
<pre><code class="language-bash">npm install vuepress-plugin-copyright
</code></pre>
<p>配置</p>
<pre><code class="language-js">// .vuepress/config.js
module.exports = {
plugins: [
[
'copyright',
{
noCopy: true, // 选中的文字将无法被复制
minLength: 100, // 如果长度超过 100 个字符
},
],
],
}
</code></pre>
<p>效果, 拷贝本页面会自动添加:</p>
<pre><code class="language-html">著作权归 xxxx 所有。
链接:https://www.pdai.tech/md/about/blog/blog-build-vuepress.html
</code></pre>
<p>更多请参考插件:vuepress-plugin-sitemap</p>
<h3 id="添加seo优化">添加SEO优化</h3>
<blockquote>
<p>这里给个链接供参考,我这边自己添加的meta信息没有用它。</p>
</blockquote>
<ul>
<li>vuepress-plugin-autometa</li>
</ul>
<h3 id="添加百度站点自动推送">添加百度站点自动推送</h3>
<blockquote>
<p>主要用于向百度站点自动推送,有助于SEO。</p>
</blockquote>
<p>安装</p>
<pre><code class="language-bash">npm install -D vuepress-plugin-baidu-autopush
</code></pre>
<p>添加配置</p>
<pre><code class="language-js">module.exports = {
plugins: [
'vuepress-plugin-baidu-autopush'
]
};
</code></pre>
<p>更多请参考插件:vuepress-plugin-baidu-autopush</p>
<h3 id="添加sitemap信息">添加Sitemap信息</h3>
<blockquote>
<p>主要用于生成站点的Sitemap,有助于SEO。</p>
</blockquote>
<p>安装</p>
<pre><code class="language-bash">npm install vuepress-plugin-sitemap
</code></pre>
<p>配置</p>
<pre><code class="language-js">// .vuepress/config.js
module.exports = {
plugins: {
'sitemap': {
hostname: 'https://www.pdai.tech'
},
}
}
</code></pre>
<p>更多请参考插件:vuepress-plugin-sitemap</p>
<h3 id="添加代码拷贝">添加代码拷贝</h3>
<blockquote>
<p>在代码区,添加一个拷贝按钮,用来拷贝代码。</p>
</blockquote>
<p>安装</p>
<pre><code class="language-bash">npm install vuepress-plugin-code-copy
</code></pre>
<p>配置</p>
<pre><code class="language-js">module.exports = {
plugins: [['vuepress-plugin-code-copy', true]]
}
</code></pre>
<p>更多请参考插件:vuepress-plugin-code-copy</p>
<h3 id="更多插件配置">更多插件配置</h3>
<p>请参考 awesome-vuepress</p>
<h2 id="博客文档稍完整配置清单">博客/文档稍完整配置清单</h2>
<ul>
<li>config.js部分内容</li>
</ul>
<pre><code class="language-js">module.exports = {
port: "3000",
dest: "docs",
ga: "UA-xxxxxxxxxxx-1",
base: "/",
markdown: {
lineNumbers: true,
externalLinks: {
target: '_blank', rel: 'noopener noreferrer'
}
},
locales: {
"/": {
lang: "zh-CN",
title: "Java 全栈知识体系",
description: "包含: Java 基础, Java 部分源码, JVM, Spring, Spring Boot, Spring Cloud, 数据库原理, MySQL, ElasticSearch, MongoDB, Docker, k8s, CI&CD, Linux, DevOps, 分布式, 中间件, 开发工具, Git, IDE, 源码阅读,读书笔记, 开源项目..."
}
},
head: [
// ico
["link", {rel: "icon", href: `/favicon.ico`}],
// meta
["meta", {name: "robots", content: "all"}],
["meta", {name: "author", content: "pdai"}],
["meta", {name: "keywords", content: "Java 全栈知识体系, java体系, java知识体系, java框架,java详解,java学习路线,java spring, java面试, 知识体系, java技术体系, java编程, java编程指南,java开发体系, java开发,java教程,java,java数据结构, 算法, 开发基础"}],
["meta", {name: "apple-mobile-web-app-capable", content: "yes"}],
// baidu statstic
["script", {src: "https://hm.baidu.com/hm.js?xxxxxxxxxxx"}]
],
plugins: [
['@vuepress/back-to-top', true],
['@vuepress/medium-zoom', {
selector: 'img',
// See: https://github.com/francoischalifour/medium-zoom#options
options: {
margin: 16
}
}],
// see: https://vssue.js.org/guide/vuepress.html#usage
['@vssue/vuepress-plugin-vssue', {
// set `platform` rather than `api`
platform: 'github',
// all other options of Vssue are allowed
owner: 'realpdai',
repo: 'tech-arch-doc-comments',
clientId: 'xxxxxxxxxxx',
clientSecret: 'xxxxxxxxxxxxxxxxxxxxxx',
}],
// see: https://vuepress.github.io/zh/plugins/copyright/#%E5%AE%89%E8%A3%85
['copyright', {
noCopy: false, // 允许复制内容
minLength: 100, // 如果长度超过 100 个字符
authorName: "https://www.pdai.tech",
// clipboardComponent: "请注明文章出处, (https://www.pdai.tech)"
}],
// see: https://github.com/ekoeryanto/vuepress-plugin-sitemap
['sitemap', {
hostname: 'https://www.pdai.tech'
}],
// see: https://github.com/IOriens/vuepress-plugin-baidu-autopush
['vuepress-plugin-baidu-autopush', {
}],
// see: https://github.com/znicholasbrown/vuepress-plugin-code-copy
[['vuepress-plugin-code-copy', true]]
// ...
],
themeConfig: {
//repo: "realpdai/tech-arch-doc",
docsRepo: "realpdai/tech-arch-doc",
//logo: "/logo.png",
editLinks: true,
sidebarDepth:0,
locales: {
"/": {
label: "简体中文",
selectText: "Languages",
editLinkText: "在 GitHub 上编辑此页",
lastUpdated: "上次更新",
nav: [
{
text: '关于', link: '/md/about/me/about-me.md'
}
],
sidebar: {
"/md/about/": genSidebar4About()
}
}
}
}
};
// About page
function genSidebar4About(){
return [
{
title: "关于",
collapsable: false,
sidebarDepth: 0,
children: [
"me/about-me.md",
"me/about-content.md",
"me/about-content-style.md",
"me/about-arch.md",
"me/about-motivation.md"
]
},
{
title: "关于 - 本文档的搭建",
collapsable: false,
sidebarDepth: 0,
children: [
"blog/blog-build-vuepress.md",
"blog/blog-build-ci.md",
"blog/blog-build-cd.md",
"blog/blog-build-ssl.md"
]
}
];
}
</code></pre>
<ul>
<li>package.json</li>
</ul>
<pre><code class="language-json">{
"name": "tech-arch-doc",
"version": "2.0.1",
"private": true,
"scripts": {
"dev": "vuepress dev",
"build": "vuepress build"
},
"devDependencies": {
"@vuepress/plugin-back-to-top": "^1.0.3",
"@vuepress/plugin-medium-zoom": "^1.0.4",
"vuepress": "^1.0.2"
},
"dependencies": {
"@vssue/api-github-v3": "^1.1.2",
"@vssue/vuepress-plugin-vssue": "^1.2.0",
"vuepress-plugin-baidu-autopush": "^1.0.1",
"vuepress-plugin-code-copy": "^1.0.4-alpha",
"vuepress-plugin-copyright": "^1.0.2",
"vuepress-plugin-sitemap": "^2.3.0"
}
}
</code></pre>
<ul>
<li>enhanceApp.js</li>
</ul>
<pre><code class="language-js">export default ({router}) => {
router.beforeEach((to, from, next) => {
// @pdai: 对每个页面点击添加百度统计
if(typeof _hmt!='undefined'){
if (to.path) {
_hmt.push(['_trackPageview', to.fullPath]);
}
}
// continue
next();
})
};
</code></pre>
<ul>
<li>index.styl</li>
</ul>
<pre><code class="language-stylus">.custom-page-class{
/* 自定义的样式 */
}
// markdown blockquote
blockquote
font-size 1rem
color #2c3e50;
border-left .5rem solid #42b983
background-color #f3f5f7
margin 1rem 0
padding 1rem 0 1rem 1rem
& > p
margin 0
// markdown h1
h1
font-size 2rem
padding-bottom 1rem
border-bottom 1px solid $borderColor
// markdown h2
h2
font-size 1.65rem
border-bottom 0px solid $borderColor
// custom block for tip
.custom-block
.custom-block-title
font-weight 600
margin-bottom -0.4rem
&.tip, &.warning, &.danger
padding .1rem 1.5rem
border-left-width .5rem
border-left-style solid
margin 1rem 0
&.tip
background-color #dfefff
border-color #428eb9
// logo
.navbar
.logo
height $navbarHeight - 1.6rem
min-width $navbarHeight - 1.6rem
margin-right 0rem
vertical-align top
</code></pre>
<ul>
<li>palette.styl</li>
</ul>
<pre><code class="language-stylus">// 内容的宽度
$contentWidth = 100%
// 颜色
$accentColor = #3eaf7c
$textColor = #2c3e50
$borderColor = #eaecef
$codeBgColor = #282c34
</code></pre>
<h2 id="vuepress-其它参考资源">vuepress 其它参考资源</h2>
<ul>
<li>VuePress 官网</li>
<li>VuePress Github</li>
<li>VuePress 社区 VuePress社区维护的生态系统</li>
<li>awesome-vuepress // 注意:vuepress插件分官方(包括官方社区)和社区两个维护,在里面都可以找到</li>
</ul>
<h1 id="第二部分---博客文档的自动编译">第二部分 - 博客/文档的自动编译</h1>
<blockquote>
<p>文档托管在Github,有几种选择: Github自带的Github Actions,或者插件Travis CI, 或者插件Circle CI。@pdai</p>
</blockquote>
<h2 id="travis-ci">Travis CI</h2>
<blockquote>
<p>注意: Travis CI有个坑爹的地方要注意: 它有travis.com和travis.org两个网站,一个是对公有项目,一个是对私有项目;然后,github是可以在公有和私有项目中切换的,于是在切换后,一些配置可能无法正确设置。</p>
</blockquote>
<h3 id="github-启用插件">Github 启用插件</h3>
<p>进入 https://github.com/marketplace/travis-ci</p>
<p><img src="https://www.pdai.tech/_images/blog/blog-ci-1.png" alt="" loading="lazy"></p>
<h3 id="配置插件">配置插件</h3>
<p><img src="https://www.pdai.tech/_images/blog/blog-ci-2.png" alt="" loading="lazy"></p>
<h3 id="添加travisyml">添加.travis.yml</h3>
<blockquote>
<p>注意: 这里只是简单做编译操作,您可以将编译的结果(静态的html文件)强制推送至当前仓库专门放编译后文件的分支;也可以在自己的服务器上安装travis-cli,在travis.com(注意不是travis.org)生成证书信息(自动生成相关环境变量),来进行自动化部署。</p>
</blockquote>
<p>这里上述两种方案都没有采用,是因为:</p>
<ul>
<li>1)travis-cli对私有项目自动添加证书信息支持不够;</li>
<li>2)同时本文档中静态资源较多,拉取编译结果较大;</li>
<li>3)github 拉较大资源速度稳定性无法保障,原因你懂的;相对来说用webhook方式已经够了。</li>
</ul>
<pre><code class="language-json">language: node_js
sudo: false
node_js:
- "12"
cache:
yarn: true
directories:
- node_modules
branches:
only:
- master
env:
global:
- GITHUB_REPO: github.com/realpdai/tech-arch-doc.git
before_install:
- export TZ=Asia/Shanghai
script:
- vuepress build
</code></pre>
<h3 id="触发编译">触发编译</h3>
<p><img src="https://www.pdai.tech/_images/blog/blog-ci-4.png" alt="" loading="lazy"></p>
<h3 id="查看最后提交编译状况">查看最后提交编译状况</h3>
<p><img src="https://www.pdai.tech/_images/blog/blog-ci-5.png" alt="" loading="lazy"></p>
<p><img src="https://www.pdai.tech/_images/blog/blog-ci-6.png" alt="" loading="lazy"></p>
<h3 id="生成build-状态svg">生成build 状态svg</h3>
<p><img src="https://www.pdai.tech/_images/blog/blog-ci-3.png" alt="" loading="lazy"></p>
<h1 id="第三部分---博客文档的自动部署">第三部分 - 博客/文档的自动部署</h1>
<blockquote>
<p>本文主要介绍 当前文档是如何在我自己的服务器自动编译部署的。@pdai</p>
</blockquote>
<h2 id="文档编译和部署流程">文档编译和部署流程</h2>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-cd-1.png" alt="" loading="lazy"></p>
<h2 id="搭建">搭建</h2>
<blockquote>
<p>之前购买了一个低配的阿里云虚拟机,系统是CentOS 7.x。</p>
</blockquote>
<h3 id="安装nodejs">安装NodeJS</h3>
<ul>
<li>添加yum源</li>
</ul>
<pre><code class="language-bash">curl -sL https://rpm.nodesource.com/setup_10.x | bash -
</code></pre>
<ul>
<li>yum install</li>
</ul>
<pre><code class="language-bash">yum install -y nodejs
</code></pre>
<p>其它方式可以参考此文 https://blog.csdn.net/bbwangj/article/details/82253785</p>
<h3 id="清理原有部分服务">清理原有部分服务</h3>
<blockquote>
<p>之前服务器上搭建过gitlab-ee,jenkins,httpd等,由于我自己的代码托管已经切换至github的私有仓库,所以现在需要清理下;不需要清理的,请略过。</p>
</blockquote>
<ul>
<li>清理gitlab-ee</li>
</ul>
<p>https://blog.csdn.net/huhuhuemail/article/details/80519433</p>
<ul>
<li>清理httpd</li>
</ul>
<p>https://www.cnblogs.com/richardcastle/p/8296166.html</p>
<h3 id="安装nginx和配置">安装Nginx和配置</h3>
<ul>
<li>安装</li>
</ul>
<p>https://www.centos.bz/2018/01/centos-7,使用yum安装nginx/</p>
<ul>
<li>
<p>配置开机自启<br>
https://www.cnblogs.com/jepson6669/p/9131217.html</p>
</li>
<li>
<p>配置nginx.conf</p>
</li>
</ul>
<p>https://www.cnblogs.com/alvin-niu/p/9502286.html</p>
<ul>
<li>配置firewalld</li>
</ul>
<p>https://blog.csdn.net/benchem/article/details/79605598</p>
<h3 id="部署项目">部署项目</h3>
<p>通过webhook触发编译并reload nginx</p>
<h1 id="第四部分---博客文档的域名https备案">第四部分 - 博客/文档的域名,HTTPS,备案</h1>
<blockquote>
<p>本文主要记录 本文档的域名,HTTPS,备案。 @pdai</p>
</blockquote>
<p>文档的域名,HTTPS,备案 这三个步骤不能反,因为存在依赖关系。</p>
<h2 id="申请域名">申请域名</h2>
<ul>
<li>申请: 万网</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-8.png" alt="" loading="lazy"></p>
<ul>
<li>申请域名</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-9.png" alt="" loading="lazy"></p>
<h2 id="https">https</h2>
<ul>
<li>阿里云上: SSL证书</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-0.png" alt="" loading="lazy"></p>
<ul>
<li>申请证书</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-1.png" alt="" loading="lazy"></p>
<ul>
<li>证书审核</li>
</ul>
<blockquote>
<p>30分钟之内就审核完成</p>
</blockquote>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-2.png" alt="" loading="lazy"></p>
<ul>
<li>证书详情</li>
</ul>
<blockquote>
<p>这个详情页面在备案的时候需要拍照上传。</p>
</blockquote>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-7.png" alt="" loading="lazy"></p>
<ul>
<li>证书下载</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-6.png" alt="" loading="lazy"></p>
<h2 id="备案">备案</h2>
<blockquote>
<p>80/443端口通过域名直接访问是需要备案的,在18年的时候我搭建过的个人网站是不要备案的。</p>
</blockquote>
<ul>
<li>备案前访问 www.pdai.tech</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-3.png" alt="" loading="lazy"></p>
<ul>
<li>进入备案</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-4.png" alt="" loading="lazy"></p>
<blockquote>
<p>期间需要手机通过阿里云人脸认证,并上传 身份证,域名和证书拍照等。</p>
</blockquote>
<ul>
<li>备案审核</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-5.png" alt="" loading="lazy"></p>
<blockquote>
<p>注意备案初审由阿里云代理的,要求: 个人网站必须命名为<code>xxxx的个人博客</code>或者<code>xxx的个人主页</code>,否则备案不通过。申请的周期大概最多是20天,申请完了之后工信部会发短信到登记到手机号,之后到8小时就可以使用了。</p>
</blockquote>
<h2 id="服务器资源选择">服务器资源选择</h2>
<blockquote>
<p>那么搭建这样的网站需要多少服务器资源呢,阿里云坑的地方是新用户首年都便宜,后面续费就贵了。</p>
</blockquote>
<ul>
<li>看下搭建需要多少资源</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-10.png" alt="" loading="lazy"></p>
<ul>
<li>看下费用</li>
</ul>
<blockquote>
<p>推荐选择1CPU,1-2G内存即可;1Core-1GB一年价格287多,选择五年也就642多;后期如有需求,可以在线<code>增加配置</code></p>
</blockquote>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-11.png" alt="" loading="lazy"></p>
<ul>
<li>关于续费,我之前选择是2CPU,4GB内存;当初一年是780,续费价格是2363;</li>
</ul>
<p><img src="https://www.pdai.tech/_images/blog/blog-ssl-ali-12.png" alt="" loading="lazy"></p>
<p>:::tip<br>
后续: 我将阿里到服务器降级到了1U 1GB,但是使用Vuepress build 编译静态页面时内存需要700MB,这将导致内存不够。我这边考虑使用swap方式,置换一些内存资源放置swap磁盘。<br>
:::</p>
<ul>
<li>Swap空间</li>
</ul>
<p>参考文章如下: https://blog.csdn.net/u010457406/article/details/83753384</p>
<p>编译前</p>
<p><img src="https://www.pdai.tech/_images/blog/about-ssl-swap-1.png" alt="" loading="lazy"></p>
<p>编译中 (内存不够会置换至swap区)</p>
<p><img src="https://www.pdai.tech/_images/blog/about-ssl-swap-2.png" alt="" loading="lazy"></p>
<h1 id="最后再看下搭建出来的效果吧">最后再看下搭建出来的效果吧</h1>
<blockquote>
<p><span style="color: rgba(255, 0, 0, 1); font-size: 25px">最全的Java后端知识体系</span><span style="color: rgba(255, 0, 0, 1); font-size: 25px"> https://www.pdai.tech</span>, <span style="color: rgba(255, 0, 0, 1); font-size: 25px">每天更新中...</span>。</p>
</blockquote>
</div>
<div id="MySignature" role="contentinfo">
更多文章请参考 (https://pdai.tech)<br><br>
来源:https://www.cnblogs.com/pengdai/p/11818863.html
頁:
[1]