说来惭愧,也不记得有几次立flag要把博客坚持下去的,看看上一篇的时间,一拖又是这么久了。
为了不至于彻底沦落成上班摸鱼,下班看剧的MADAO(并非在说长谷川先生),还是想去舒适区外面逛逛。自动化部署并不是什么难事,记得以前网上就可以找到一堆TravisCI的教程。不过记得去年暑假时候使用Docker封装了博客环境,以便能在新系统上使用(Ubuntu 16.04 => 18.04),同时也是为了防止博客插件以及npm的更新引起问题。
容器内构建环境
关于Docker容器的储存结构以及基本介绍,之前貌似有一篇文章已经说了一些了,这里不再赘述。
通过镜像构建容器很简单,docker run imagename
即可,由于是博客,可以把本地的blog目录挂在进去,并映射里面的端口,即加上-v /Blog:/Blog
和-p 4000:4000
,其他设置自己怎么喜欢怎么来。
个人是直接从Docker Hub官方仓库中的ubuntu:16.04镜像来启动容器的,可以使用docker pull
,也可以使用docker run
命令来启动容器。
然后是安装一些必要的软件:
首先安装必要的环境,然后安装npm的包管理工具nvm,然后配置git账号,并安装特定版本的node,在安装之前先确认之前可以运行的时候的node版本即可。剩下的就是安装hexo和gulp(博客资源压缩工具,优化用)。
为了hexo能够直接deploy,配置免密登录密钥并添加到github中。
拷贝/root/.ssh/id_rsa.pub
文件中内容到github的SSH-KEY中即可。
然后删掉博客中的node_modules/
文件夹和db.json
文件,重新安装。
之后便可以正常在本地访问博客了。
构建镜像
容器直接构建
在之前环境配置好之后,退出容器,将该容器打包成镜像。
可加参数有-a authorname
添加作者信息,-m message
添加说明文字,如:
后面添加容器ID或者容器名都可以,然后添加你要上传到DockerHub的仓库名以及版本标签(TAG如果为空,默认为latest)
通过Dockerfile构建
将之前的指令写入Dockerfile文件,然后建立镜像即可。
|
|
其中MAINTAINER
是作者名字,FROM
是使用的镜像来源,然后安装环境,和之前一样。最后使用Docker build
命令构建镜像。
需要说一点的是,通过Dockerfile构建的镜像不能直接使用ssh-keygen
命令生成免密密钥,因为每次构建镜像时都会执行一次生成指令,如果之后版本需要修改,Dockerfile中需要加入其他指令,那么原来可以免密的镜像,生成后会变的无法登陆。最明显的就是使用ssh的方式的hexo deploy和github 仓库的访问,故而将已经可以免密的.ssh/
文件夹直接拷贝进来。
|
|
使用-t
指令是指定之后要上传到Docker Hub的镜像仓库名。
然后等待一会,会显示构建完成,使用docker images
便可以查看之前直接在容器中构建的镜像和使用Dockerfile构建的镜像。通常使用Dockerfile构建镜像体积会更小,因为Docker的分层存储方式,由于在容器内通常会做很多多余的无用指令,所以直接commit构建的体积很容易变得臃肿。
之后就是上传镜像:
|
|
Docker自动化部署
其实在镜像制作完成后,即可以使用镜像启动容器,然后使用博客环境了。上传镜像之后,可以在不同电脑上使用该博客环境,也不会有环境冲突的问题。但是每次都要挂载本地目录到容器中(因为博客目录体积较大,直接放入容器中体积太大,而且博客会更新,容器不能保存,只能重新制作镜像,使得效率低下)。也许是觉得在不同电脑上都要下载镜像启动容器显得麻烦,或者觉得每次都要手动generate、push和deploy显得麻烦,便开始打算使用Docker自动化部署。
首先去DockerHub创建一个仓库用来自动化部署,仓库创建需要绑定github账号,然后将博客的源文件仓库链接至该镜像仓库,如下图所示。
不过也不一定要链接至博客源文件仓库,可以新建一个仓库,将Dockerfile上传至该仓库,每次push该仓库触发博客自动更新也可以。直接使用博客源文件仓库则是每次写好文章push上去便直接触发更新了。
然后在本地的博客源文件(或新仓库)添加一个Dockerfile记录要自动更新的指令。
|
|
然后git add .
以及使用commit
和push
上传至git仓库即可触发。
其中,ADD
一个变化的值,保证之后的构建不使用缓存,不然即使仓库更新了,容器里的仓库也不会更新。
其实不用每次git clone
,git的优点就是差异性存储,所以可以之前依然可以使用缓存,节省时间,将后续操作设置成不使用缓存。
|
|
另一种方式,直接将当前仓库中的文件添加到容器中:
|
|
这种方式,每次修改文件后都将整个文件夹添加到容器中,文件夹比较大的话会花比较多的时间。另一方面,因为Docker层层有缓存,所以第一种方式也只有第一次较慢。
最后观察触发是否成功以及最后输出结果是否在预期内。
上述涉及到ADD
和COPY
区别,COPY只是简单的复制,ADD支持下载URL,并支持解压,并具有判断其ADD
的src
功能。因此,在没有特殊需求时,尽量使用COPY提高效率,上述使用ADD .git/
是为了让Docker Daemon判断git仓库是否更新了,如果更新了,则不使用缓存,这样,后续的git pull
才能真正获取更新并最终更新到网站上。
此外,还可以添加
.dockerignore
文件来忽略一些容器中你不用的文件以提高速度。容器加载时会默认将当前目录下所有文件打包传给Docker Daemon,比如就是node_modules
文件夹。没有写的太细,长篇累牍容易给看客压力,
step by step
操作一番,不填坑也不会有印象,也并不会达到对容器熟悉的效果。因为容器的方便性,我曾不断向人安利,但也许是推荐的对象不适合,用的人貌似不多,记得以前也答应过人把Docker封装环境的详细过程写写,现在算是应诺了,希望还能帮人节省一点时间。