在前面的教程里,我们提到构建 Ghost 主题需要用到
gulp
来作为构建工具。 gulp 的工具链对于我们主题的开发和发布都起着很重要的作用,有了它我们可以更关注在主题的制作上面。这篇教程对于
gulp
本身不会做太多讲解,大家可以去它的官网获取更多的知识。
使用 yarn 来管理依赖
yarn 相比 npm
,它安装包的速度更快一些,所以我更倾向去用它来做依赖管理工具。
安装
npm install -g yarn
yarn -v
常用命令
# 全局安装
yarn global add [package]
# 安装依赖到不同环境
yarn add [package] --dev
yarn add [package] --peer
yarn add [package] --optional
# 更新依赖
yarn upgrade [package]
# 移除依赖
yarn remove [package]
安装 Gulp 工具链
全局安装 Gulp
# 安装 gulp
yarn global add gulp@latest
安装完后执行 gulp -v
,如果有问题,我们可以在主题的项目里面安装
yarn add gulp --dev
安装插件
gulp 提供了丰富的插件来满足我们不同的应用场景。我们主要用到它的一些插件来做主题的资源管理。
gulp-autoprefixer
Autoprefixer
是一个很实用的 css 后处理器,它可以自动帮我们处理浏览器的兼容性问题。使用它后,在写 css 的时候,我们没必要去针对特定的浏览器去写一些样式。
yarn add gulp-autoprefixer --dev
gulp-less
Less 是一门 css 预处理语言,我们用它来写主题的样式更方便扩展可管理。选择 Less
或 Sass
可以完全凭自己的喜好,对于我们这种小型的主题开发来说,两者的差别并不是很大。gulp-less
插件可以将我们的 less
文件编译成 css
yarn add gulp-less --dev
gulp-clean-css
这个插件是用来压缩 css 文件的,使生成环境的文件体积变得更小。
yarn add gulp-clean-css --dev
gulp-uglify
这个插件时用来压缩 js 文件的。
yarn add gulp-uglify --dev
gulp-concat
这个插件是把多个文件合并成一个文件
yarn add gulp-concat --dev
gulp-rename
这个插件是对文件重命名
yarn add gulp-rename --dev
到这里,我们需要的插件都安装好了。接下来我们就开始写 gulp
脚本了。
编写 gulpfile 文件
在我们主题的根目录下我们创建一个 gulpfile.js
文件并在文件中输入以下内容
function defaultTask(cb) {
// place code for your default task here
cb();
}
exports.default = defaultTask
在主题的根目录下执行 gulp 命令
gulp
默认任务将执行,因为任务为空,所以实际上什么都没做。
创建任务
我们要做的事情其实很简单,就是把 src
目录里面的资源压缩打包到 assets
里即可。
在开发主题的时候,我们需要监测 src
目录里文件的变化,如果有文件发生了变化就执行任务;在上生产环境时,我们手动执行一下即可。
最终的 gulpfile.js
如下:
const { src, dest, series, parallel, watch } = require('gulp');
const less = require('gulp-less');
const concat = require('gulp-concat');
const rename = require('gulp-rename');
const autoprefixer = require('gulp-autoprefixer');
const cleanCSS = require('gulp-clean-css');
const uglify = require('gulp-uglify');
//编译、合并、压缩less文件
const buildLess = (cb) => {
return src(['src/less/**/*.less'])
.pipe(concat('style.less'))
.pipe(less())
.pipe(autoprefixer())
.pipe(cleanCSS({ compatibility: 'ie8' }))
.pipe(dest('src/css'))
}
//合并压缩后的css文件
const buildCss = (cb) => {
return src(['src/css/*.css'])
.pipe(concat('style.min.css'))
.pipe(autoprefixer())
.pipe(cleanCSS({ compatibility: 'ie8' }))
.pipe(dest('assets/css'))
}
//压缩、合并js文件
const mainJs = (cb) => {
return src(['src/js/jquery.min.js', 'src/js/main.js'])
.pipe(uglify())
.pipe(concat('index.js'))
.pipe(rename({ suffix: '.min' }))
.pipe(dest('assets/js'))
}
//文件监听
const auto = (cb) => {
watch('src/assets/less/**/*.less', series(buildLess, buildCss))
watch('src/assets/css/*.css', buildCss)
watch('src/assets/js/**/*.js', mainJs)
}
//生产环境构建
exports.build = series(buildLess, buildCss, mainJs)
//开发环境构建
exports.dev = auto
任务讲解
gulp4
把任务分为了公开任务和私有任务。公开任务使用 exports
导出,可以通过 gulp
命令直接调用。
这里我们公开了两个任务:build
和 dev
,分别对应生产环境和开发环境
gulp build
gulp dev
私有任务被设计在内部使用,通常可以用 series()
和 parallel()
来组合使用。我们实现了 buildLess
、buildCss
、mainJs
和 auto
这几个私有任务。
buildLess
任务做的事情是把 src/less
文件夹下所有的 less
文件合并为一个 style.less
文件,然后转换成同名的 css 文件,使用 autoprefixer
后处理器,最终压缩并生成到 src/css
文件夹中。
buildCss
任务做的事情是把 src/css
文件夹下所有的 css
文件合并为一个 style.min.css
文件,使用 autoprefixer
后处理器,最终压缩并生成到 assets/css
文件夹中。
mainJs
任务同上,做的事情都不复杂。auto
任务实现了文件的监听,当我们修改了代码后,会自动构建对应的任务,方便我们实时去预览效果。
构建任务
我们可以先把任务中需要的文件都新建好。 注意:前面我们在 assets/css
里建了一个 main.css
,我们把它移到 src/css
里。 然后清空 assets
文件夹
执行 gulp build
后就可以生成生产环境的资源。最终在 assets
里面有一个 css/style.min.css
文件和一个 js/index.min.js
文件
到这里,我们使用 gulp
来管理主题的资源就完成了。最后别忘了,到 default.hbs
里引入文件。
<!DOCTYPE html>
<html lang="{{@site.lang}}">
<head>
{{!-- Document Settings --}}
<meta charset="utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
{{!-- Base Meta --}}
<title>{{meta_title}}</title>
<meta name="HandheldFriendly" content="True" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
{{!-- Styles'n'Scripts --}}
<link rel="stylesheet" type="text/css" href="{{asset "css/style.min.css"}}" />
{{!-- This tag outputs SEO meta+structured data and other important settings --}}
{{ghost_head}}
</head>
<body class="{{body_class}}">
<div class="site-wrapper">
{{!-- All the main content gets inserted here, index.hbs, post.hbs, etc --}}
{{{body}}}
</div>
<script src="{{asset 'js/index.min.js'}}"></script>
{{ghost_foot}}
</body>
</html>
示例代码:https://github.com/KINGMJ/maple-test/tree/features/tutorials-7