使用 flow.ci 快速发布你的项目文档
软件研发的协作过程中,文档是必不可少的一环,有需求文档、接口文档、使用文档等等。当开始写文档时,首先会遇到两个问题:
- team members 之间如何协作?
- 文档 OK 后如何分发,去哪里看?如何更新?
很早的时候采用 word+ppt 做文档,然后放到共享服务器(ftp,samba)上,这种方式会有文档锁定和覆盖的问题,几个人的小团队还可以,大不了更新的时喊一嗓子:“我要更新文档了,大家都不要占用某某文件(使用windows共享文档的童鞋应该很熟悉)”。更新完了还要再喊一嗓子。除此之外,由于 word 文件格式(word文件其实是个压缩包,由很多 xml 和其他文件构成)太过于复杂,即便是借助 git 或者 svn 做版本控制,一旦产生冲突,很难通过肉眼合并和解决冲突。
那么如何解决上述问题呢?这篇文章我用 gitbook + flow.ci 进行文档的发布、集成和部署,希望给有需求的同学一些参考。
如何进行文档协作 & 版本控制 (git+markdown)
开发团队使用 git 或 svn 作为协作和版本控制工具已经是很成熟的方案了,当然也可以用于文档,只是word文档本身天然不太适合版本控制,markdown 是一种轻量级的标记语言, 学习简单,上手容易(具体语法参考 http://wowubuntu.com/markdown/) , 配合 git 几乎能做到完美的文档版本控制 。
如何发布文档 (gitbook+nginx)
最好的方式是把文档发布为 web 网站,这样无需安装任何工具即可查看文档,更新时只需更新网站即可。在这里,用 gitbook 将 markdown 文件快速生成为网站。
什么是 gitbook 呢?官网上是这么介绍的:
GitBook is a modern publishing toolchain. Making both writing and collaboration easy.
简单来说就是将 markdown 文档转换成 html、pdf、epub 等多种格式,很多开源软件和书籍都是用 gitbook 发布的,
如:Elasticsearch 权威指南、 Docker — 从入门到实践 等。
如果将 markdown 文档生成静态 html 部署到服务器(nginx)上,不仅可以通过浏览器查看,而且一旦更新server,所有人看到的都是最新的文档。
如何将文档进行持续集成 & 部署 (flow.ci)
CI(Continuous Integration)意为 “持续整合”,指代码的持续测试及与其他代码修改的整合与归并。
CD(Continuous Deployment)意为 “持续部署”,指代码与其补丁的持续部署于整个代码库。
拿文档来看,持续部署就是内容的持续测试、与必要修改的归并及部署。在此,部署意为发布。举例来说,“部署文档”是指输出文件被复制于web服务器为人阅览。
关于持续集成、持续部署不是一两句话能说清的,用于实现 持续集成、持续部署的工具链也五花八门,比如:最常见的 jenkins 、TravisCI 等,使用起来配置过于复杂。这篇文章里我将使用自家的持续集成服务 —— flow.ci 来进行文档的集成和部署,仅供参考。
建一个git repo存储文档
首先,建一个git repo存储文档,此处以 flow.ci官方文档 docs.flow.ci 为例, git repo 为
git@github.com:FIRHQ/flow.ci.git
目前 flow.ci 支持 github、bitbucket、国内的coding 和 私有部署的Gitlab。只要文档放在以上代码仓库的 git repo 都可以使用 flow.ci 进行集成. 如何在 flow.ci 创建项目可以 参考文档.
在 flow.ci 上创建 flow
接着,在 flow.ci 上建一个flow,语言模板选用 nodejs(使用 gitbook 需要用到node环境)。
同时删除掉 Cache、Install、Test等 step,这几个 step 是为 nodejs 项目提供的,我们此处只需要 nodejs 运行时环境及 npm 工具。
添加自定义脚本step
删除完之后添加自定义脚本step, 如何添加自定义脚本step可参考文档。 此处要添加两个自定义脚本,一个用于安装gitbook,一个用于编译文档并发布。
安装 gitbook 的自定义脚本 step 内容

flow_cmd "npm install gitbook-cli -g" --echo --retry --assert
此处的 flow_cmd 是 flow.ci 提供的一个函数,如果执行命令失败会进行重试
生成静态文件 && 部署 的自定义脚本step 内容

if [ "$FLOW_GIT_BRANCH" == "gitbook" ]; then # 只部署 gitbook分支
source get_commits_from_last.sh
bash -x ./deploy.sh
fi;
$FLOW_GIT_BRANCH是一个环境变量,用来存储当前的git分支get_commits_from_last.sh会获取上次发布的日期以及git commit iddeploy.sh会调用gitbook命令编译markdown文档,并在首页head里面添加本次commit id号以及时间戳,并发布到服务器,脚本会为文末放出- 由于
deploy.sh会将gitbook生成的静态文件使用scp的方式copy到服务器, 所以 服务器必须添加 rsa key 信任 , rsa-key可以在项目的设置页找到,将其添加倒对应user的~/.ssh/authorized_keys中即可
添加邮件通知的step,文档部署成功后触发
Email Sender插件需要三个参数,分别是邮件接受者、邮件主题、邮件内容模板,如下:

总结
至此,使用 flow.ci 快速发布文档的步骤已经全部完成。flow.ci 不只是持续集成,持续部署的工具,也帮助我们用自动化的视角审视手头繁琐的工作,将更多的时间用在新鲜事物上。
有任何疑问发邮件到 my@fir.im,分享你的观点:)
附上所有 step 中涉及的脚本:
- get_commits_from_last.sh
#!/usr/bin/env bash
# usage: sh get_commits_from_last.sh
# 会export 2个环境变量:
# DEPLOY_DIFF 与上次部署的时间差
# DEPLOY_LOG 与上次部署的变化
set -e
STAGE="docs"
URL="${STAGE}.flow.ci"
HTML=`eval curl -sS ${URL}` # 获取首页html
# 从首页html中提取上次 部署的ID 和 部署时间
LAST_ID=`echo $HTML | awk 'match($0, /-[0-9a-f]{7}/) { print substr( $0, RSTART+1, RLENGTH-1 )}'`
LAST_TIME=`echo $HTML | awk 'match($0, /[0-9]{4}-[0-9]{2}-[0-9]{2}T[0-9]{2}:[0-9]{2}:[0-9]{2}/) { print substr( $0, RSTART, RLENGTH )}'`"Z"
FMT="%Y-%m-%dT%H:%M:%SZ"
currDate=`date -u +"$FMT"`
if [[ `uname` == 'Darwin' ]]; then
ts=$(date -j -f "$FMT" "${currDate}" "+%s")
ts2=$(date -j -f "$FMT" "${LAST_TIME}" "+%s")
else
ts=$(date --date="${currDate}" +"%s")
ts2=$(date --date="${LAST_TIME}" +"%s")
fi
(( diff=(ts-ts2)/60 ))
export DEPLOY_DIFF=$diff
echo "Last $1 version : $LAST_ID @ ${LAST_TIME} (${DEPLOY_DIFF} minutes ago)"
echo "-----------------------------------------"
export DEPLOY_LOG=`git log --oneline $LAST_ID..HEAD`
echo "${DEPLOY_LOG}"
- deploy.sh
#!/bin/bash
set -e
# VARS
DEPLOY_TIME=`date +%Y%m%d%H%M%S`
REMOTE_DIR="/var/www/flow-doc"
RELEASE_DIR="${REMOTE_DIR}/release"
DEPLOY_DIR="${RELEASE_DIR}/${DEPLOY_TIME}"
LATEST_DIR="${REMOTE_DIR}/latest"
TARGET=prod
USER=deploy # 需添加 rsa key 信任
HOST="此处修改为server的ip"
PORT=22 # ssh端口
# 使用gitbook 生成静态文件
gitbook build docs dist
# 获取当前时间
FMT="%Y-%m-%dT%H:%M:%SZ"
currDate=`date -u +"$FMT"`
if [[ `uname` == 'Darwin' ]]; then
ts=$(date -j -f "$FMT" "${currDate}" "+%s")
else
ts=$(date --date="${currDate}" +"%s")
fi
# 获取当前分支
branch=$(git rev-parse --abbrev-ref HEAD)
if [ -n "$FLOW_GIT_BRANCH" ] ; then
branch=$FLOW_GIT_BRANCH
fi
# 获取commit log
commit=$(git rev-parse --short HEAD)
# 将本次部署的时间和COMMIT ID 嵌入倒首页html中
sed -i '/author/a\ \<meta name="version" content="production|COMMIT-TAG"\>' ./dist/index.html
sed -i '/author/a\ \<meta http-equiv="last-modified" content="UPDATE-TIME"\>' ./dist/index.html
sed -i "s/COMMIT-TAG/${branch}-${commit}/g" ./dist/index.html
sed -i "s/UPDATE-TIME/${currDate}/g" ./dist/index.html
# 开始部署
echo "########## Deploy to ${TARGET} ##########"
ssh ${USER}@${HOST} -p ${PORT} "mkdir -p ${DEPLOY_DIR}"
ssh ${USER}@${HOST} -p ${PORT} "rm -rfv ${LATEST_DIR}"
scp -P ${PORT} -rv ./dist/* ${USER}@${HOST}:${DEPLOY_DIR}
ssh ${USER}@${HOST} -p ${PORT} bash -x <<EOF
ln -s ${DEPLOY_DIR} ${LATEST_DIR}
exit
EOF
echo "########## Deploy $HOST success ##########"
exit 0
使用 flow.ci 快速发布你的项目文档的更多相关文章
- 使用 Github Pages 发布你的项目文档
导读 你可能比较熟悉如何用 Github Pages 来分享你的工作,又或许你看过一堂教你建立你的第一个 Github Pages 网站的教程.近期 Github Pages 的改进使得从不同的数据源 ...
- 使用gitlab runner 进行CI(四):使用Gitlab Page托管项目文档
目录 1.什么是Gitlab Pages 2.开启Gitlab Pages 3.基本过程 4.托管markdown文档 4.1 安装sphinx等依赖 4.2 配置项目的sphinx配置 4.3 编写 ...
- 随时发布:REST API文档的代码仓库中的持续集成与协作
本文主要内容:API文档提供了预测客户成功的关键路径:在代码附近的文档上进行协作可以更好地检查代码和文档文件,提高自动化效率,并专门针对文档进行质量测试:提供通用文档框架,标准,自动化和工具,以提高团 ...
- MkDocs项目文档生成器
简介 安装 我的配置 Chocolatey 简介 - Windows的包管理器 官方网址 安装 注意事项 Python 简介 安装 Pip 简介-Python的包管理器 升级 MkDocs的安装 使用 ...
- vuepress+gitee 构建在线项目文档
目录 快速入门 在现有vue项目中安装本地开发依赖vuepress 在现有vue项目根目录下创建docs目录 创建并配置文档首页内容 运行,查看效果 可能会出现vue和vue-server-rende ...
- 使用Mkdocs构建你的项目文档
使用Mkdocs构建你的项目文档 环境搭建 安装必需软件 作者是在windows下安装的,如果是linux或mac用户,官网有更详细的安装说明. windows 10 x64 当然还有广大的windo ...
- 通过VuePress管理项目文档(一)
VuePress 相关链接 完整的Vue组件代码以及完整的文档,仅适用于个人参考学习: 文档预览地址:预览链接 使用VuePress编辑文档的代码访问:组件文档 完整代码:组件代码 Vue组件开发 这 ...
- Java-Maven-Runoob:Maven 项目文档
ylbtech-Java-Maven-Runoob:Maven 项目文档 1.返回顶部 1. Maven 项目文档 本章节我们主要学习如何创建 Maven 项目文档. 比如我们在 C:/MVN 目录下 ...
- 使用 Hexo 创建项目文档网站
当我们发布一个开源项目的时候,最重要的事情之一就是要创建项目文档.对使用项目的用户来说,文档是非常有必要的,通常我们可以使用下面这些方式来创建文档: GitHub Wiki:在 Github 上我们可 ...
随机推荐
- PHP 判断几秒前,几分钟,几小时前
PHP 对于时间的过了多久的判断,几秒前,几分钟前,几小时前,$time = strtotime("2017-01-15 14:42:00"); $time = strtotime ...
- Mysql 常用引擎的特点及选择使用策略
Mysql 常用引擎的特点及选择使用策略 Mysql数据库常用存储引擎 Mysql数据库是一款开源的数据库,支持多种存储引擎的选择,比如目前最常用的存储引擎有:MyISAM,InnoDB,Memory ...
- tableview的reloadData应注意
http://blog.csdn.net/ouyangtianhan/article/details/7835041 http://stackoverflow.com/questions/160715 ...
- Delphi 数据类型的说明
简单类型包括实数类型(Real) 和有序类型(Ordinal),有序类型又包括整数类型,字符类型,布尔类型,枚举类型和子界类型等. 数据类型 范围 ...
- Java层与Jni层的数组传递(转)
源:Java层与Jni层的数组传递 Android开发中,经常会在Java代码与Jni层之间传递数组(byte[]),一个典型的应用是Java层把需要发送给客户端的数据流传递到Jni层,由Jni层的S ...
- 使用idea建立gradle+SSM项目
目录: 一.创建一个gradle项目 二 .在gradle中创建SSM项目 一 .创建一个gradle项目 第一步: 第二步:选择gradle,并选中web,然后点击Next进入下一步 第三步:此 ...
- mongodb学习(三) 安装和基本CRUD
菜鸟啊...先吐槽一下自己 发现mongodb已经升级到2.6标准版了. 服务端最新安装方法: http://www.cnblogs.com/lzrabbit/p/3682510.html 一 准备 ...
- NOIP前刷水行动
2016.11.15 BZOJ1009:DP+矩阵乘法+KMP BZOJ1898:矩阵乘法 BZOJ4101:贪心,考虑我们往右边撞的时候,我们会向左边冲 ,于是枚举答案点利用一个指针计算即可! 20 ...
- Bomb(hdu 3555)
题意:给定一个闭区间,求区间内有多少数中含"49" /* dp[i][j]表示i位数以j为最高位位中的所有不符合数的个数. 然后把数字拆分,乱搞即可. */ #include< ...
- Rest Project Performace Pressure Test
首次调整基线和配置修改 机器配置为 CPU: Intel(R) Xeon(R) CPU E5-2630 v2 @ 2.6GHz 24core 内存: 128G JDK Ver: 1.7.0_80 To ...