diff --git a/.eslintrc.json b/.eslintrc.json index 57bd13b4a0..2cf72c2756 100644 --- a/.eslintrc.json +++ b/.eslintrc.json @@ -1,17 +1,4 @@ { "extends": "hexo", - "root": true, - "rules": { - "one-var": 0, - "operator-linebreak": [ - 2, - "after" - ], - "comma-spacing": [ - 2, - { - "after": true - } - ] - } + "root": true } diff --git a/lib/box/index.js b/lib/box/index.js index edd6459556..faf7ace4db 100644 --- a/lib/box/index.js +++ b/lib/box/index.js @@ -14,9 +14,12 @@ const defaultPattern = new Pattern(() => ({})); function Box(ctx, base, options) { Reflect.apply(EventEmitter, this, []); - this.options = Object.assign({ - persistent: true - }, options); + this.options = Object.assign( + { + persistent: true + }, + options + ); if (!base.endsWith(sep)) { base += sep; @@ -44,7 +47,8 @@ function getHash(path) { const src = fs.createReadStream(path); const hasher = new HashStream(); - src.pipe(hasher) + src + .pipe(hasher) .on('finish', () => { resolve(hasher.read().toString('hex')); }) @@ -69,15 +73,23 @@ Box.prototype._createFileClass = function() { options = {}; } - return ctx.render.render({ - path: this.source - }, options).asCallback(callback); + return ctx.render + .render( + { + path: this.source + }, + options + ) + .asCallback(callback); }; _File.prototype.renderSync = function(options) { - return ctx.render.renderSync({ - path: this.source - }, options); + return ctx.render.renderSync( + { + path: this.source + }, + options + ); }; return _File; @@ -105,16 +117,24 @@ Box.prototype._readDir = function(base, fn, prefix = '') { return Promise.resolve('Ignoring dir.'); } - return fs.readdir(base).map(path => fs.stat(join(base, path)).then(stats => { - if (stats.isDirectory()) { - return this._readDir(join(base, path), fn, `${prefix + path}/`); - } - - return this._checkFileStatus(prefix + path).then(file => fn(file).thenReturn(file)); - })).catch(err => { - if (err.cause && err.cause.code === 'ENOENT') return; - throw err; - }).reduce((files, item) => files.concat(item), []); + return fs + .readdir(base) + .map(path => + fs.stat(join(base, path)).then(stats => { + if (stats.isDirectory()) { + return this._readDir(join(base, path), fn, `${prefix + path}/`); + } + + return this._checkFileStatus(prefix + path).then(file => + fn(file).thenReturn(file) + ); + }) + ) + .catch(err => { + if (err.cause && err.cause.code === 'ENOENT') return; + throw err; + }) + .reduce((files, item) => files.concat(item), []); }; Box.prototype._checkFileStatus = function(path) { @@ -135,19 +155,34 @@ Box.prototype._checkFileStatus = function(path) { Box.prototype.process = function(callback) { const { base, Cache, context: ctx } = this; - return fs.stat(base).then(stats => { - if (!stats.isDirectory()) return; - - // Check existing files in cache - const relativeBase = escapeBackslash(base.substring(ctx.base_dir.length)); - const cacheFiles = Cache.filter(item => item._id.startsWith(relativeBase)).map(item => item._id.substring(relativeBase.length)); - - // Read files from directory - return this._readDir(base, file => this._processFile(file.type, file.path)).map(file => file.path).then(files => // Handle deleted files - Promise.filter(cacheFiles, path => !files.includes(path)).map(path => this._processFile(File.TYPE_DELETE, path))); - }).catch(err => { - if (err.cause && err.cause.code !== 'ENOENT') throw err; - }).asCallback(callback); + return fs + .stat(base) + .then(stats => { + if (!stats.isDirectory()) return; + + // Check existing files in cache + const relativeBase = escapeBackslash(base.substring(ctx.base_dir.length)); + const cacheFiles = Cache.filter(item => + item._id.startsWith(relativeBase) + ).map(item => item._id.substring(relativeBase.length)); + + // Read files from directory + return this._readDir(base, file => + this._processFile(file.type, file.path) + ) + .map(file => file.path) + .then(( + files // Handle deleted files + ) => + Promise.filter(cacheFiles, path => !files.includes(path)).map(path => + this._processFile(File.TYPE_DELETE, path) + ) + ); + }) + .catch(err => { + if (err.cause && err.cause.code !== 'ENOENT') throw err; + }) + .asCallback(callback); }; Box.prototype.load = Box.prototype.process; @@ -166,38 +201,49 @@ Box.prototype._processFile = function(type, path) { path }); - return Promise.reduce(this.processors, (count, processor) => { - const params = processor.pattern.match(path); - if (!params) return count; - - const file = new File({ - source: join(base, path), - path, - params, - type - }); - - return Reflect.apply(Promise.method(processor.process), ctx, [file]) - .thenReturn(count + 1); - }, 0).then(count => { - if (count) { - ctx.log.debug('Processed: %s', chalk.magenta(path)); - } - - this.emit('processAfter', { - type, - path - }); - }).catch(err => { - ctx.log.error({err}, 'Process failed: %s', chalk.magenta(path)); - }).finally(() => { - this._processingFiles[path] = false; - }).thenReturn(path); + return Promise.reduce( + this.processors, + (count, processor) => { + const params = processor.pattern.match(path); + if (!params) return count; + + const file = new File({ + source: join(base, path), + path, + params, + type + }); + + return Reflect.apply(Promise.method(processor.process), ctx, [ + file + ]).thenReturn(count + 1); + }, + 0 + ) + .then(count => { + if (count) { + ctx.log.debug('Processed: %s', chalk.magenta(path)); + } + + this.emit('processAfter', { + type, + path + }); + }) + .catch(err => { + ctx.log.error({ err }, 'Process failed: %s', chalk.magenta(path)); + }) + .finally(() => { + this._processingFiles[path] = false; + }) + .thenReturn(path); }; Box.prototype.watch = function(callback) { if (this.isWatching()) { - return Promise.reject(new Error('Watcher has already started.')).asCallback(callback); + return Promise.reject(new Error('Watcher has already started.')).asCallback( + callback + ); } const { base } = this; @@ -206,28 +252,35 @@ Box.prototype.watch = function(callback) { return escapeBackslash(path.substring(base.length)); } - return this.process().then(() => fs.watch(base, this.options)).then(watcher => { - this.watcher = watcher; - - watcher.on('add', path => { - this._processFile(File.TYPE_CREATE, getPath(path)); - }); - - watcher.on('change', path => { - this._processFile(File.TYPE_UPDATE, getPath(path)); - }); - - watcher.on('unlink', path => { - this._processFile(File.TYPE_DELETE, getPath(path)); - }); - - watcher.on('addDir', path => { - let prefix = getPath(path); - if (prefix) prefix += '/'; - - this._readDir(path, file => this._processFile(file.type, file.path), prefix); - }); - }).asCallback(callback); + return this.process() + .then(() => fs.watch(base, this.options)) + .then(watcher => { + this.watcher = watcher; + + watcher.on('add', path => { + this._processFile(File.TYPE_CREATE, getPath(path)); + }); + + watcher.on('change', path => { + this._processFile(File.TYPE_UPDATE, getPath(path)); + }); + + watcher.on('unlink', path => { + this._processFile(File.TYPE_DELETE, getPath(path)); + }); + + watcher.on('addDir', path => { + let prefix = getPath(path); + if (prefix) prefix += '/'; + + this._readDir( + path, + file => this._processFile(file.type, file.path), + prefix + ); + }); + }) + .asCallback(callback); }; Box.prototype.unwatch = function() { diff --git a/lib/extend/console.js b/lib/extend/console.js index fd72b4d60f..bcbdc6ec4f 100644 --- a/lib/extend/console.js +++ b/lib/extend/console.js @@ -25,10 +25,12 @@ Console.prototype.register = function(name, desc, options, fn) { if (typeof options === 'function') { fn = options; - if (typeof desc === 'object') { // name, options, fn + if (typeof desc === 'object') { + // name, options, fn options = desc; desc = ''; - } else { // name, desc, fn + } else { + // name, desc, fn options = {}; } } else { @@ -52,7 +54,7 @@ Console.prototype.register = function(name, desc, options, fn) { fn = Promise.method(fn); } - const c = this.store[name.toLowerCase()] = fn; + const c = (this.store[name.toLowerCase()] = fn); c.options = options; c.desc = desc; diff --git a/lib/extend/filter.js b/lib/extend/filter.js index 962a5431dc..1d229f5f59 100644 --- a/lib/extend/filter.js +++ b/lib/extend/filter.js @@ -30,7 +30,7 @@ Filter.prototype.register = function(type, fn, priority) { type = typeAlias[type] || type; priority = priority == null ? 10 : priority; - const store = this.store[type] = this.store[type] || []; + const store = (this.store[type] = this.store[type] || []); fn.priority = priority; store.push(fn); @@ -57,10 +57,12 @@ Filter.prototype.exec = function(type, data, options = {}) { args.unshift(data); - return Promise.each(filters, filter => Reflect.apply(Promise.method(filter), ctx, args).then(result => { - args[0] = result == null ? args[0] : result; - return args[0]; - })).then(() => args[0]); + return Promise.each(filters, filter => + Reflect.apply(Promise.method(filter), ctx, args).then(result => { + args[0] = result == null ? args[0] : result; + return args[0]; + }) + ).then(() => args[0]); }; Filter.prototype.execSync = function(type, data, options = {}) { diff --git a/lib/extend/tag.js b/lib/extend/tag.js index df66add124..7135b7325a 100644 --- a/lib/extend/tag.js +++ b/lib/extend/tag.js @@ -17,7 +17,7 @@ Tag.prototype.register = function(name, fn, options) { if (typeof fn !== 'function') throw new TypeError('fn must be a function'); if (options == null || typeof options === 'boolean') { - options = {ends: options}; + options = { ends: options }; } let tag; @@ -66,20 +66,23 @@ function getContext(lines, errLine, location, type) { colorize(' === (line number probably different from source) ===') ]; - Array.prototype.push.apply(message, + Array.prototype.push.apply( + message, // get LINES_OF_CONTEXT lines surrounding `errLine` - getContextLineNums(1, lines.length, errLine, LINES_OF_CONTEXT) - .map(function(lnNum) { - const line = ' ' + lnNum + ' | ' + lines[lnNum - 1]; - if (lnNum === errLine) { - return colorize.bold(line); - } - - return colorize(line); - }) + getContextLineNums(1, lines.length, errLine, LINES_OF_CONTEXT).map(function( + lnNum + ) { + const line = ' ' + lnNum + ' | ' + lines[lnNum - 1]; + if (lnNum === errLine) { + return colorize.bold(line); + } + + return colorize(line); + }) + ); + message.push( + colorize(' ===== Context Dump Ends =====') ); - message.push(colorize( - ' ===== Context Dump Ends =====')); return message; } @@ -104,7 +107,12 @@ function formatNunjucksError(err, input) { e.line = errLine; e.location = splited[0]; e.type = splited[1].trim(); - e.message = getContext(input.split(/\r?\n/), errLine, e.location, e.type).join('\n'); + e.message = getContext( + input.split(/\r?\n/), + errLine, + e.location, + e.type + ).join('\n'); return e; } @@ -120,7 +128,9 @@ Tag.prototype.render = function(str, options, callback) { str = str.replace(/
[\s\S]*?<\/code><\/pre>/gm, escapeContent); - return Promise.fromCallback(cb => { this.env.renderString(str, options, cb); }) + return Promise.fromCallback(cb => { + this.env.renderString(str, options, cb); + }) .catch(err => Promise.reject(formatNunjucksError(err, str))) .then(result => result.replace(rPlaceholder, (_, index) => cache[index])); }; @@ -145,9 +155,16 @@ NunjucksTag.prototype._parseArgs = (parser, nodes, lexer) => { let argitem = ''; while ((token = parser.nextToken(true))) { - if (token.type === lexer.TOKEN_WHITESPACE || token.type === lexer.TOKEN_BLOCK_END) { + if ( + token.type === lexer.TOKEN_WHITESPACE || + token.type === lexer.TOKEN_BLOCK_END + ) { if (argitem !== '') { - const argnode = new nodes.Literal(tag.lineno, tag.colno, argitem.trim()); + const argnode = new nodes.Literal( + tag.lineno, + tag.colno, + argitem.trim() + ); argarray.addChild(argnode); argitem = ''; } diff --git a/lib/hexo/default_config.js b/lib/hexo/default_config.js index 710e764586..9f72dbdea1 100644 --- a/lib/hexo/default_config.js +++ b/lib/hexo/default_config.js @@ -59,4 +59,3 @@ module.exports = { // Category & Tag meta_generator: true }; - diff --git a/lib/hexo/index.js b/lib/hexo/index.js index d98c187e6f..4aceb60da1 100644 --- a/lib/hexo/index.js +++ b/lib/hexo/index.js @@ -94,8 +94,9 @@ function Hexo(base = process.cwd(), args = {}) { const mcp = multiConfigPath(this); - this.config_path = args.config ? mcp(base, args.config, args.output) : - join(base, '_config.yml'); + this.config_path = args.config + ? mcp(base, args.config, args.output) + : join(base, '_config.yml'); registerModels(this); @@ -115,7 +116,7 @@ Hexo.prototype._bindLocals = function() { const query = {}; if (!this.config.future) { - query.date = {$lte: Date.now()}; + query.date = { $lte: Date.now() }; } if (!this._showDrafts()) { @@ -129,7 +130,7 @@ Hexo.prototype._bindLocals = function() { const query = {}; if (!this.config.future) { - query.date = {$lte: Date.now()}; + query.date = { $lte: Date.now() }; } return db.model('Page').find(query); @@ -152,7 +153,10 @@ Hexo.prototype._bindLocals = function() { Hexo.prototype.init = function() { this.log.debug('Hexo version: %s', chalk.magenta(this.version)); - this.log.debug('Working directory: %s', chalk.magenta(tildify(this.base_dir))); + this.log.debug( + 'Working directory: %s', + chalk.magenta(tildify(this.base_dir)) + ); // Load internal plugins require('../plugins/console')(this); @@ -164,14 +168,19 @@ Hexo.prototype.init = function() { require('../plugins/tag')(this); // Load config - return Promise.each([ - 'update_package', // Update package.json - 'load_config', // Load config - 'load_plugins' // Load external plugins & scripts - ], name => require(`./${name}`)(this)).then(() => this.execFilter('after_init', null, {context: this})).then(() => { - // Ready to go! - this.emit('ready'); - }); + return Promise.each( + [ + 'update_package', // Update package.json + 'load_config', // Load config + 'load_plugins' // Load external plugins & scripts + ], + name => require(`./${name}`)(this) + ) + .then(() => this.execFilter('after_init', null, { context: this })) + .then(() => { + // Ready to go! + this.emit('ready'); + }); }; Hexo.prototype.call = function(name, args, callback) { @@ -209,28 +218,31 @@ Hexo.prototype.resolvePlugin = function(name) { }; Hexo.prototype.loadPlugin = function(path, callback) { - return fs.readFile(path).then(script => { - // Based on: https://github.com/joyent/node/blob/v0.10.33/src/node.js#L516 - const module = new Module(path); - module.filename = path; - module.paths = Module._nodeModulePaths(path); - - function require(path) { - return module.require(path); - } + return fs + .readFile(path) + .then(script => { + // Based on: https://github.com/joyent/node/blob/v0.10.33/src/node.js#L516 + const module = new Module(path); + module.filename = path; + module.paths = Module._nodeModulePaths(path); + + function require(path) { + return module.require(path); + } - require.resolve = request => Module._resolveFilename(request, module); + require.resolve = request => Module._resolveFilename(request, module); - require.main = process.mainModule; - require.extensions = Module._extensions; - require.cache = Module._cache; + require.main = process.mainModule; + require.extensions = Module._extensions; + require.cache = Module._cache; - script = `(function(exports, require, module, __filename, __dirname, hexo){${script}});`; + script = `(function(exports, require, module, __filename, __dirname, hexo){${script}});`; - const fn = vm.runInThisContext(script, path); + const fn = vm.runInThisContext(script, path); - return fn(module.exports, require, module, path, dirname(path), this); - }).asCallback(callback); + return fn(module.exports, require, module, path, dirname(path), this); + }) + .asCallback(callback); }; Hexo.prototype._showDrafts = function() { @@ -239,32 +251,32 @@ Hexo.prototype._showDrafts = function() { }; Hexo.prototype.load = function(callback) { - return loadDatabase(this).then(() => { - this.log.info('Start processing'); - - return Promise.all([ - this.source.process(), - this.theme.process() - ]); - }).then(() => this._generate({cache: true})).asCallback(callback); + return loadDatabase(this) + .then(() => { + this.log.info('Start processing'); + + return Promise.all([this.source.process(), this.theme.process()]); + }) + .then(() => this._generate({ cache: true })) + .asCallback(callback); }; Hexo.prototype.watch = function(callback) { - this._watchBox = debounce(() => this._generate({cache: false}), 100); + this._watchBox = debounce(() => this._generate({ cache: false }), 100); - return loadDatabase(this).then(() => { - this.log.info('Start processing'); + return loadDatabase(this) + .then(() => { + this.log.info('Start processing'); - return Promise.all([ - this.source.watch(), - this.theme.watch() - ]); - }).then(() => { - this.source.on('processAfter', this._watchBox); - this.theme.on('processAfter', this._watchBox); + return Promise.all([this.source.watch(), this.theme.watch()]); + }) + .then(() => { + this.source.on('processAfter', this._watchBox); + this.theme.on('processAfter', this._watchBox); - return this._generate({cache: false}); - }).asCallback(callback); + return this._generate({ cache: false }); + }) + .asCallback(callback); }; Hexo.prototype.unwatch = function() { @@ -295,7 +307,12 @@ Hexo.prototype._generateLocals = function() { } Locals.prototype.config = config; - Locals.prototype.theme = Object.assign({}, config, theme.config, config.theme_config); + Locals.prototype.theme = Object.assign( + {}, + config, + theme.config, + config.theme_config + ); Locals.prototype._ = _; Locals.prototype.layout = 'layout'; Locals.prototype.env = this.env; @@ -326,9 +343,12 @@ Hexo.prototype._runGenerators = function() { const routeCache = new WeakMap(); -const unique = array => array.filter((item, index, self) => self.indexOf(item) === index); +const unique = array => + array.filter((item, index, self) => self.indexOf(item) === index); -const castArray = obj => { return Array.isArray(obj) ? obj : [obj]; }; +const castArray = obj => { + return Array.isArray(obj) ? obj : [obj]; +}; const createLoadThemeRoute = function(generatorResult, locals, ctx) { const { log, theme } = ctx; @@ -338,7 +358,8 @@ const createLoadThemeRoute = function(generatorResult, locals, ctx) { const layoutLength = layout.length; return () => { - if (useCache && routeCache.has(generatorResult)) return routeCache.get(generatorResult); + if (useCache && routeCache.has(generatorResult)) + return routeCache.get(generatorResult); for (let i = 0; i < layoutLength; i++) { const name = layout[i]; @@ -346,11 +367,14 @@ const createLoadThemeRoute = function(generatorResult, locals, ctx) { if (view) { log.debug(`Rendering HTML ${name}: ${chalk.magenta(path)}`); - return view.render(locals).tap(result => { - routeCache.set(generatorResult, result); - }).tapCatch(err => { - log.error({ err }, `Render HTML failed: ${chalk.magenta(path)}`); - }); + return view + .render(locals) + .tap(result => { + routeCache.set(generatorResult, result); + }) + .tapCatch(err => { + log.error({ err }, `Render HTML failed: ${chalk.magenta(path)}`); + }); } } @@ -364,29 +388,36 @@ Hexo.prototype._routerReflesh = function(runningGenerators, useCache) { const Locals = this._generateLocals(); Locals.prototype.cache = useCache; - return runningGenerators.map(generatorResult => { - if (typeof generatorResult !== 'object' || generatorResult.path == null) return undefined; + return runningGenerators + .map(generatorResult => { + if (typeof generatorResult !== 'object' || generatorResult.path == null) + return undefined; - // add Route - const path = route.format(generatorResult.path); - const { data, layout } = generatorResult; + // add Route + const path = route.format(generatorResult.path); + const { data, layout } = generatorResult; - if (!layout) { - route.set(path, data); - return path; - } - - return this.execFilter('template_locals', new Locals(path, data), {context: this}) - .then(locals => { route.set(path, createLoadThemeRoute(generatorResult, locals, this)); }) - .thenReturn(path); - }).then(newRouteList => { - // Remove old routes - const removed = routeList.filter(item => !newRouteList.includes(item)); + if (!layout) { + route.set(path, data); + return path; + } - for (let i = 0, len = removed.length; i < len; i++) { - route.remove(removed[i]); - } - }); + return this.execFilter('template_locals', new Locals(path, data), { + context: this + }) + .then(locals => { + route.set(path, createLoadThemeRoute(generatorResult, locals, this)); + }) + .thenReturn(path); + }) + .then(newRouteList => { + // Remove old routes + const removed = routeList.filter(item => !newRouteList.includes(item)); + + for (let i = 0, len = removed.length; i < len; i++) { + route.remove(removed[i]); + } + }); }; Hexo.prototype._generate = function(options = {}) { @@ -399,13 +430,17 @@ Hexo.prototype._generate = function(options = {}) { this.emit('generateBefore'); // Run before_generate filters - return this.execFilter('before_generate', this.locals.get('data'), {context: this}) - .then(() => this._routerReflesh(this._runGenerators(), useCache)).then(() => { + return this.execFilter('before_generate', this.locals.get('data'), { + context: this + }) + .then(() => this._routerReflesh(this._runGenerators(), useCache)) + .then(() => { this.emit('generateAfter'); // Run after_generate filters - return this.execFilter('after_generate', null, {context: this}); - }).finally(() => { + return this.execFilter('after_generate', null, { context: this }); + }) + .finally(() => { this._isGenerating = false; }); }; @@ -413,13 +448,13 @@ Hexo.prototype._generate = function(options = {}) { Hexo.prototype.exit = function(err) { if (err) { this.log.fatal( - {err}, - 'Something\'s wrong. Maybe you can find the solution here: %s', + { err }, + "Something's wrong. Maybe you can find the solution here: %s", chalk.underline('https://hexo.io/docs/troubleshooting.html') ); } - return this.execFilter('before_exit', null, {context: this}).then(() => { + return this.execFilter('before_exit', null, { context: this }).then(() => { this.emit('exit', err); }); }; diff --git a/lib/hexo/load_config.js b/lib/hexo/load_config.js index 6d9d3f890b..fead9661e9 100644 --- a/lib/hexo/load_config.js +++ b/lib/hexo/load_config.js @@ -14,35 +14,39 @@ module.exports = ctx => { const baseDir = ctx.base_dir; let configPath = ctx.config_path; - return fs.exists(configPath).then(exist => { - return exist ? configPath : findConfigPath(configPath); - }).then(path => { - if (!path) return; - - configPath = path; - return ctx.render.render({path}); - }).then(config => { - if (!config || typeof config !== 'object') return; - - ctx.log.debug('Config loaded: %s', chalk.magenta(tildify(configPath))); - - config = merge(ctx.config, config); - ctx.config_path = configPath; - - config.root = config.root.replace(/\/*$/, '/'); - config.url = config.url.replace(/\/+$/, ''); - - ctx.public_dir = resolve(baseDir, config.public_dir) + sep; - ctx.source_dir = resolve(baseDir, config.source_dir) + sep; - ctx.source = new Source(ctx); - - if (!config.theme) return; - - config.theme = config.theme.toString(); - ctx.theme_dir = join(baseDir, 'themes', config.theme) + sep; - ctx.theme_script_dir = join(ctx.theme_dir, 'scripts') + sep; - ctx.theme = new Theme(ctx); - }); + return fs + .exists(configPath) + .then(exist => { + return exist ? configPath : findConfigPath(configPath); + }) + .then(path => { + if (!path) return; + + configPath = path; + return ctx.render.render({ path }); + }) + .then(config => { + if (!config || typeof config !== 'object') return; + + ctx.log.debug('Config loaded: %s', chalk.magenta(tildify(configPath))); + + config = merge(ctx.config, config); + ctx.config_path = configPath; + + config.root = config.root.replace(/\/*$/, '/'); + config.url = config.url.replace(/\/+$/, ''); + + ctx.public_dir = resolve(baseDir, config.public_dir) + sep; + ctx.source_dir = resolve(baseDir, config.source_dir) + sep; + ctx.source = new Source(ctx); + + if (!config.theme) return; + + config.theme = config.theme.toString(); + ctx.theme_dir = join(baseDir, 'themes', config.theme) + sep; + ctx.theme_script_dir = join(ctx.theme_dir, 'scripts') + sep; + ctx.theme = new Theme(ctx); + }); }; function findConfigPath(path) { diff --git a/lib/hexo/load_database.js b/lib/hexo/load_database.js index b3d59a036e..037e4eefc5 100644 --- a/lib/hexo/load_database.js +++ b/lib/hexo/load_database.js @@ -10,15 +10,19 @@ module.exports = ctx => { const { path } = db.options; const { log } = ctx; - return fs.exists(path).then(exist => { - if (!exist) return; + return fs + .exists(path) + .then(exist => { + if (!exist) return; - log.debug('Loading database.'); - return db.load(); - }).then(() => { - ctx._dbLoaded = true; - }).catch(() => { - log.error('Database load failed. Deleting database.'); - return fs.unlink(path); - }); + log.debug('Loading database.'); + return db.load(); + }) + .then(() => { + ctx._dbLoaded = true; + }) + .catch(() => { + log.error('Database load failed. Deleting database.'); + return fs.unlink(path); + }); }; diff --git a/lib/hexo/load_plugins.js b/lib/hexo/load_plugins.js index d6e2c6105c..80b1cb5709 100644 --- a/lib/hexo/load_plugins.js +++ b/lib/hexo/load_plugins.js @@ -13,34 +13,39 @@ module.exports = ctx => { function loadModuleList(ctx) { if (ctx.config && Array.isArray(ctx.config.plugins)) { - return Promise.resolve(ctx.config.plugins).filter(item => typeof item === 'string'); + return Promise.resolve(ctx.config.plugins).filter( + item => typeof item === 'string' + ); } const packagePath = join(ctx.base_dir, 'package.json'); // Make sure package.json exists - return fs.exists(packagePath).then(exist => { - if (!exist) return []; - - // Read package.json and find dependencies - return fs.readFile(packagePath).then(content => { - const json = JSON.parse(content); - const deps = Object.keys(json.dependencies || {}); - const devDeps = Object.keys(json.devDependencies || {}); - - return deps.concat(devDeps); + return fs + .exists(packagePath) + .then(exist => { + if (!exist) return []; + + // Read package.json and find dependencies + return fs.readFile(packagePath).then(content => { + const json = JSON.parse(content); + const deps = Object.keys(json.dependencies || {}); + const devDeps = Object.keys(json.devDependencies || {}); + + return deps.concat(devDeps); + }); + }) + .filter(name => { + // Ignore plugins whose name is not started with "hexo-" + if (!/^hexo-|^@[^/]+\/hexo-/.test(name)) return false; + + // Ignore typescript definition file that is started with "@types/" + if (/^@types\//.test(name)) return false; + + // Make sure the plugin exists + const path = ctx.resolvePlugin(name); + return fs.exists(path); }); - }).filter(name => { - // Ignore plugins whose name is not started with "hexo-" - if (!/^hexo-|^@[^/]+\/hexo-/.test(name)) return false; - - // Ignore typescript definition file that is started with "@types/" - if (/^@types\//.test(name)) return false; - - // Make sure the plugin exists - const path = ctx.resolvePlugin(name); - return fs.exists(path); - }); } function loadModules(ctx) { @@ -48,11 +53,14 @@ function loadModules(ctx) { const path = ctx.resolvePlugin(name); // Load plugins - return ctx.loadPlugin(path).then(() => { - ctx.log.debug('Plugin loaded: %s', chalk.magenta(name)); - }).catch(err => { - ctx.log.error({err}, 'Plugin load failed: %s', chalk.magenta(name)); - }); + return ctx + .loadPlugin(path) + .then(() => { + ctx.log.debug('Plugin loaded: %s', chalk.magenta(name)); + }) + .catch(err => { + ctx.log.error({ err }, 'Plugin load failed: %s', chalk.magenta(name)); + }); }); } @@ -63,18 +71,21 @@ function loadScripts(ctx) { return chalk.magenta(path.substring(baseDirLength)); } - return Promise.filter([ - ctx.theme_script_dir, - ctx.script_dir - ], scriptDir => { // Ignore the directory if it does not exist + return Promise.filter([ctx.theme_script_dir, ctx.script_dir], scriptDir => { + // Ignore the directory if it does not exist return scriptDir ? fs.exists(scriptDir) : false; - }).map(scriptDir => fs.listDir(scriptDir).map(name => { - const path = join(scriptDir, name); - - return ctx.loadPlugin(path).then(() => { - ctx.log.debug('Script loaded: %s', displayPath(path)); - }).catch(err => { - ctx.log.error({err}, 'Script load failed: %s', displayPath(path)); - }); - })); + }).map(scriptDir => + fs.listDir(scriptDir).map(name => { + const path = join(scriptDir, name); + + return ctx + .loadPlugin(path) + .then(() => { + ctx.log.debug('Script loaded: %s', displayPath(path)); + }) + .catch(err => { + ctx.log.error({ err }, 'Script load failed: %s', displayPath(path)); + }); + }) + ); } diff --git a/lib/hexo/multi_config_path.js b/lib/hexo/multi_config_path.js index afc3b40b00..6924616e81 100644 --- a/lib/hexo/multi_config_path.js +++ b/lib/hexo/multi_config_path.js @@ -5,73 +5,76 @@ const fs = require('hexo-fs'); const merge = require('lodash/merge'); const yml = require('js-yaml'); -module.exports = ctx => function multiConfigPath(base, configPaths, outputDir) { - const { log } = ctx; - const defaultPath = join(base, '_config.yml'); - - if (!configPaths) { - log.w('No config file entered.'); - return join(base, '_config.yml'); - } - - let paths; - // determine if comma or space separated - if (configPaths.includes(',')) { - paths = configPaths.replace(' ', '').split(','); - } else { - // only one config - let configPath = isAbsolute(configPaths) ? configPaths : resolve(base, configPaths); - - if (!fs.existsSync(configPath)) { - log.w(`Config file ${configPaths} not found, using default.`); - configPath = defaultPath; +module.exports = ctx => + function multiConfigPath(base, configPaths, outputDir) { + const { log } = ctx; + const defaultPath = join(base, '_config.yml'); + + if (!configPaths) { + log.w('No config file entered.'); + return join(base, '_config.yml'); } - return configPath; - } - - const numPaths = paths.length; + let paths; + // determine if comma or space separated + if (configPaths.includes(',')) { + paths = configPaths.replace(' ', '').split(','); + } else { + // only one config + let configPath = isAbsolute(configPaths) + ? configPaths + : resolve(base, configPaths); - // combine files - const combinedConfig = {}; - let count = 0; - for (let i = 0; i < numPaths; i++) { - const configPath = isAbsolute(paths[i]) ? paths[i] : join(base, paths[i]); + if (!fs.existsSync(configPath)) { + log.w(`Config file ${configPaths} not found, using default.`); + configPath = defaultPath; + } - if (!fs.existsSync(configPath)) { - log.w(`Config file ${paths[i]} not found.`); - continue; + return configPath; } - // files read synchronously to ensure proper overwrite order - const file = fs.readFileSync(configPath); - const ext = extname(paths[i]).toLowerCase(); - - if (ext === '.yml') { - merge(combinedConfig, yml.load(file)); - count++; - } else if (ext === '.json') { - merge(combinedConfig, yml.safeLoad(file, {json: true})); - count++; - } else { - log.w(`Config file ${paths[i]} not supported type.`); + const numPaths = paths.length; + + // combine files + const combinedConfig = {}; + let count = 0; + for (let i = 0; i < numPaths; i++) { + const configPath = isAbsolute(paths[i]) ? paths[i] : join(base, paths[i]); + + if (!fs.existsSync(configPath)) { + log.w(`Config file ${paths[i]} not found.`); + continue; + } + + // files read synchronously to ensure proper overwrite order + const file = fs.readFileSync(configPath); + const ext = extname(paths[i]).toLowerCase(); + + if (ext === '.yml') { + merge(combinedConfig, yml.load(file)); + count++; + } else if (ext === '.json') { + merge(combinedConfig, yml.safeLoad(file, { json: true })); + count++; + } else { + log.w(`Config file ${paths[i]} not supported type.`); + } } - } - if (count === 0) { - log.e('No config files found. Using _config.yml.'); - return defaultPath; - } + if (count === 0) { + log.e('No config files found. Using _config.yml.'); + return defaultPath; + } - log.i('Config based on', count, 'files'); + log.i('Config based on', count, 'files'); - const multiconfigRoot = outputDir || base; - const outputPath = join(multiconfigRoot, '_multiconfig.yml'); + const multiconfigRoot = outputDir || base; + const outputPath = join(multiconfigRoot, '_multiconfig.yml'); - log.d(`Writing _multiconfig.yml to ${outputPath}`); + log.d(`Writing _multiconfig.yml to ${outputPath}`); - fs.writeFileSync(outputPath, yml.dump(combinedConfig)); + fs.writeFileSync(outputPath, yml.dump(combinedConfig)); - // write file and return path - return outputPath; -}; + // write file and return path + return outputPath; + }; diff --git a/lib/hexo/post.js b/lib/hexo/post.js index de2ded5b14..8e4ce09e85 100644 --- a/lib/hexo/post.js +++ b/lib/hexo/post.js @@ -24,7 +24,9 @@ const _escapeContent = (cache, str) => { PostRenderCache.prototype.escapeContent = function(str) { const rEscapeContent = / ]*)>([\s\S]*?)<\/escape>/g; - return str.replace(rEscapeContent, (_, content) => _escapeContent(this.cache, content)); + return str.replace(rEscapeContent, (_, content) => + _escapeContent(this.cache, content) + ); }; PostRenderCache.prototype.loadContent = function(str) { @@ -39,7 +41,8 @@ PostRenderCache.prototype.escapeAllSwigTags = function(str) { const rSwigFullBlock = /\{% *(.+?)(?: *| +.*)%\}[\s\S]+?\{% *end\1 *%\}/g; const escape = _str => _escapeContent(this.cache, _str); - return str.replace(rSwigFullBlock, escape) + return str + .replace(rSwigFullBlock, escape) .replace(rSwigBlock, escape) .replace(rSwigComment, '') .replace(rSwigVar, escape); @@ -58,7 +61,9 @@ Post.prototype.create = function(data, replace, callback) { const ctx = this.context; const { config } = ctx; - data.slug = slugize((data.slug || data.title).toString(), {transform: config.filename_case}); + data.slug = slugize((data.slug || data.title).toString(), { + transform: config.filename_case + }); data.layout = (data.layout || config.default_layout).toLowerCase(); data.date = data.date ? moment(data.date) : moment(); @@ -69,18 +74,22 @@ Post.prototype.create = function(data, replace, callback) { context: ctx }), this._renderScaffold(data) - ]).spread((path, content) => { - const result = { path, content }; - - return Promise.all([ - // Write content to file - fs.writeFile(path, content), - // Create asset folder - createAssetFolder(path, config.post_asset_folder) - ]).then(() => { - ctx.emit('new', result); - }).thenReturn(result); - }).asCallback(callback); + ]) + .spread((path, content) => { + const result = { path, content }; + + return Promise.all([ + // Write content to file + fs.writeFile(path, content), + // Create asset folder + createAssetFolder(path, config.post_asset_folder) + ]) + .then(() => { + ctx.emit('new', result); + }) + .thenReturn(result); + }) + .asCallback(callback); }; function prepareFrontMatter(data) { @@ -112,42 +121,46 @@ Post.prototype._renderScaffold = function(data) { const { tag } = this.context.extend; let yfmSplit; - return this._getScaffold(data.layout).then(scaffold => { - const frontMatter = prepareFrontMatter(clone(data)); - yfmSplit = yfm.split(scaffold); - - return tag.render(yfmSplit.data, frontMatter); - }).then(frontMatter => { - const { separator } = yfmSplit; - const jsonMode = separator[0] === ';'; - - // Parse front-matter - const obj = jsonMode ? JSON.parse(`{${frontMatter}}`) : yaml.load(frontMatter); - - // Add data which are not in the front-matter - for (const key of Object.keys(data)) { - if (!preservedKeys.includes(key) && obj[key] == null) { - obj[key] = data[key]; + return this._getScaffold(data.layout) + .then(scaffold => { + const frontMatter = prepareFrontMatter(clone(data)); + yfmSplit = yfm.split(scaffold); + + return tag.render(yfmSplit.data, frontMatter); + }) + .then(frontMatter => { + const { separator } = yfmSplit; + const jsonMode = separator[0] === ';'; + + // Parse front-matter + const obj = jsonMode + ? JSON.parse(`{${frontMatter}}`) + : yaml.load(frontMatter); + + // Add data which are not in the front-matter + for (const key of Object.keys(data)) { + if (!preservedKeys.includes(key) && obj[key] == null) { + obj[key] = data[key]; + } } - } - let content = ''; - // Prepend the separator - if (yfmSplit.prefixSeparator) content += `${separator}\n`; + let content = ''; + // Prepend the separator + if (yfmSplit.prefixSeparator) content += `${separator}\n`; - content += yfm.stringify(obj, { - mode: jsonMode ? 'json' : '' - }); + content += yfm.stringify(obj, { + mode: jsonMode ? 'json' : '' + }); - // Concat content - content += yfmSplit.content; + // Concat content + content += yfmSplit.content; - if (data.content) { - content += `\n${data.content}`; - } + if (data.content) { + content += `\n${data.content}`; + } - return content; - }); + return content; + }); }; function createAssetFolder(path, assetFolder) { @@ -175,7 +188,9 @@ Post.prototype.publish = function(data, replace, callback) { const ctx = this.context; const { config } = ctx; const draftDir = join(ctx.source_dir, '_drafts'); - const slug = data.slug = slugize(data.slug.toString(), {transform: config.filename_case}); + const slug = (data.slug = slugize(data.slug.toString(), { + transform: config.filename_case + })); const regex = new RegExp(`^${escapeRegExp(slug)}(?:[^\\/\\\\]+)`); let src = ''; const result = {}; @@ -183,38 +198,48 @@ Post.prototype.publish = function(data, replace, callback) { data.layout = (data.layout || config.default_layout).toLowerCase(); // Find the draft - return fs.listDir(draftDir).then(list => { - return list.find(item => regex.test(item)); - }).then(item => { - if (!item) throw new Error(`Draft "${slug}" does not exist.`); - - // Read the content - src = join(draftDir, item); - return fs.readFile(src); - }).then(content => { - // Create post - assignIn(data, yfm(content)); - data.content = data._content; - delete data._content; - - return this.create(data, replace).then(post => { - result.path = post.path; - result.content = post.content; - }); - }).then(() => // Remove the original draft file - fs.unlink(src)).then(() => { - if (!config.post_asset_folder) return; - - // Copy assets - const assetSrc = removeExtname(src); - const assetDest = removeExtname(result.path); - - return fs.exists(assetSrc).then(exist => { - if (!exist) return; - - return fs.copyDir(assetSrc, assetDest).then(() => fs.rmdir(assetSrc)); - }); - }).thenReturn(result).asCallback(callback); + return fs + .listDir(draftDir) + .then(list => { + return list.find(item => regex.test(item)); + }) + .then(item => { + if (!item) throw new Error(`Draft "${slug}" does not exist.`); + + // Read the content + src = join(draftDir, item); + return fs.readFile(src); + }) + .then(content => { + // Create post + assignIn(data, yfm(content)); + data.content = data._content; + delete data._content; + + return this.create(data, replace).then(post => { + result.path = post.path; + result.content = post.content; + }); + }) + .then(() => + // Remove the original draft file + fs.unlink(src) + ) + .then(() => { + if (!config.post_asset_folder) return; + + // Copy assets + const assetSrc = removeExtname(src); + const assetDest = removeExtname(result.path); + + return fs.exists(assetSrc).then(exist => { + if (!exist) return; + + return fs.copyDir(assetSrc, assetDest).then(() => fs.rmdir(assetSrc)); + }); + }) + .thenReturn(result) + .asCallback(callback); }; Post.prototype.render = function(source, data = {}, callback) { @@ -231,61 +256,73 @@ Post.prototype.render = function(source, data = {}, callback) { // Read content from files promise = fs.readFile(source); } else { - return Promise.reject(new Error('No input file or string!')).asCallback(callback); + return Promise.reject(new Error('No input file or string!')).asCallback( + callback + ); } const isSwig = ext === 'swig'; // disable Nunjucks when the renderer spcify that. - const disableNunjucks = ext && ctx.render.renderer.get(ext) && !!ctx.render.renderer.get(ext).disableNunjucks; + const disableNunjucks = + ext && + ctx.render.renderer.get(ext) && + !!ctx.render.renderer.get(ext).disableNunjucks; const cacheObj = new PostRenderCache(); - return promise.then(content => { - data.content = content; - - // Run "before_post_render" filters - return ctx.execFilter('before_post_render', data, {context: ctx}); - }).then(() => { - data.content = cacheObj.escapeContent(data.content); - - if (isSwig) { - // Render with Nunjucks if this is a swig file - return tag.render(data.content, data); - } - - // Escape all Swig tags - if (!disableNunjucks) { - data.content = cacheObj.escapeAllSwigTags(data.content); - } - - const options = data.markdown || {}; - if (!config.highlight.enable) options.highlight = null; + return promise + .then(content => { + data.content = content; - ctx.log.debug('Rendering post: %s', chalk.magenta(source)); - // Render with markdown or other renderer - return ctx.render.render({ - text: data.content, - path: source, - engine: data.engine, - toString: true, - onRenderEnd(content) { - // Replace cache data with real contents - data.content = cacheObj.loadContent(content); + // Run "before_post_render" filters + return ctx.execFilter('before_post_render', data, { context: ctx }); + }) + .then(() => { + data.content = cacheObj.escapeContent(data.content); - // Return content after replace the placeholders - if (disableNunjucks) return data.content; - - // Render with Nunjucks + if (isSwig) { + // Render with Nunjucks if this is a swig file return tag.render(data.content, data); } - }, options); - }).then(content => { - data.content = content; - // Run "after_post_render" filters - return ctx.execFilter('after_post_render', data, {context: ctx}); - }).asCallback(callback); + // Escape all Swig tags + if (!disableNunjucks) { + data.content = cacheObj.escapeAllSwigTags(data.content); + } + + const options = data.markdown || {}; + if (!config.highlight.enable) options.highlight = null; + + ctx.log.debug('Rendering post: %s', chalk.magenta(source)); + // Render with markdown or other renderer + return ctx.render.render( + { + text: data.content, + path: source, + engine: data.engine, + toString: true, + onRenderEnd(content) { + // Replace cache data with real contents + data.content = cacheObj.loadContent(content); + + // Return content after replace the placeholders + if (disableNunjucks) return data.content; + + // Render with Nunjucks + return tag.render(data.content, data); + } + }, + options + ); + }) + .then(content => { + data.content = content; + + // Run "after_post_render" filters + return ctx.execFilter('after_post_render', data, { context: ctx }); + }) + .asCallback(callback); }; module.exports = Post; diff --git a/lib/hexo/render.js b/lib/hexo/render.js index 40029d46e0..e10e922c06 100644 --- a/lib/hexo/render.js +++ b/lib/hexo/render.js @@ -51,27 +51,31 @@ Render.prototype.render = function(data, options, callback) { if (!data.path) return reject(new TypeError('No input file or string!')); fs.readFile(data.path).then(resolve, reject); - }).then(text => { - data.text = text; - ext = data.engine || getExtname(data.path); - if (!ext || !this.isRenderable(ext)) return text; - - const renderer = this.getRenderer(ext); - return Reflect.apply(renderer, ctx, [data, options]); - }).then(result => { - result = toString(result, data); - if (data.onRenderEnd) { - return data.onRenderEnd(result); - } - - return result; - }).then(result => { - const output = this.getOutput(ext) || ext; - return ctx.execFilter(`after_render:${output}`, result, { - context: ctx, - args: [data] - }); - }).asCallback(callback); + }) + .then(text => { + data.text = text; + ext = data.engine || getExtname(data.path); + if (!ext || !this.isRenderable(ext)) return text; + + const renderer = this.getRenderer(ext); + return Reflect.apply(renderer, ctx, [data, options]); + }) + .then(result => { + result = toString(result, data); + if (data.onRenderEnd) { + return data.onRenderEnd(result); + } + + return result; + }) + .then(result => { + const output = this.getOutput(ext) || ext; + return ctx.execFilter(`after_render:${output}`, result, { + context: ctx, + args: [data] + }); + }) + .asCallback(callback); }; Render.prototype.renderSync = function(data, options) { @@ -112,7 +116,11 @@ Render.prototype.renderSync = function(data, options) { }; function toString(result, options) { - if (!Object.prototype.hasOwnProperty.call(options, 'toString') || typeof result === 'string') return result; + if ( + !Object.prototype.hasOwnProperty.call(options, 'toString') || + typeof result === 'string' + ) + return result; if (typeof options.toString === 'function') { return options.toString(result); diff --git a/lib/hexo/router.js b/lib/hexo/router.js index 54ccf47481..c3c424be65 100644 --- a/lib/hexo/router.js +++ b/lib/hexo/router.js @@ -98,7 +98,7 @@ Router.prototype.remove = function(path) { }; function RouteStream(data) { - Reflect.apply(Readable, this, [{objectMode: true}]); + Reflect.apply(Readable, this, [{ objectMode: true }]); this._data = data.data; this._ended = false; @@ -120,32 +120,34 @@ RouteStream.prototype._read = function() { if (this._ended) return false; this._ended = true; - data().then(data => { - if (data instanceof Stream && data.readable) { - data.on('data', d => { - this.push(d); - }); - - data.on('end', () => { + data() + .then(data => { + if (data instanceof Stream && data.readable) { + data.on('data', d => { + this.push(d); + }); + + data.on('end', () => { + this.push(null); + }); + + data.on('error', err => { + this.emit('error', err); + }); + } else if (data instanceof Buffer || typeof data === 'string') { + this.push(data); this.push(null); - }); - - data.on('error', err => { - this.emit('error', err); - }); - } else if (data instanceof Buffer || typeof data === 'string') { - this.push(data); - this.push(null); - } else if (typeof data === 'object') { - this.push(JSON.stringify(data)); - this.push(null); - } else { + } else if (typeof data === 'object') { + this.push(JSON.stringify(data)); + this.push(null); + } else { + this.push(null); + } + }) + .catch(err => { + this.emit('error', err); this.push(null); - } - }).catch(err => { - this.emit('error', err); - this.push(null); - }); + }); }; module.exports = Router; diff --git a/lib/hexo/scaffold.js b/lib/hexo/scaffold.js index 5a9acdb888..2ed45678dd 100644 --- a/lib/hexo/scaffold.js +++ b/lib/hexo/scaffold.js @@ -22,16 +22,19 @@ Scaffold.prototype.defaults = { Scaffold.prototype._listDir = function() { const { scaffoldDir } = this; - return fs.exists(scaffoldDir).then(exist => { - if (!exist) return []; + return fs + .exists(scaffoldDir) + .then(exist => { + if (!exist) return []; - return fs.listDir(scaffoldDir, { - ignoreFilesRegex: /^_|\/_/ - }); - }).map(item => ({ - name: item.substring(0, item.length - extname(item).length), - path: join(scaffoldDir, item) - })); + return fs.listDir(scaffoldDir, { + ignoreFilesRegex: /^_|\/_/ + }); + }) + .map(item => ({ + name: item.substring(0, item.length - extname(item).length), + path: join(scaffoldDir, item) + })); }; Scaffold.prototype._getScaffold = function(name) { @@ -39,32 +42,38 @@ Scaffold.prototype._getScaffold = function(name) { }; Scaffold.prototype.get = function(name, callback) { - return this._getScaffold(name).then(item => { - if (item) { - return fs.readFile(item.path); - } + return this._getScaffold(name) + .then(item => { + if (item) { + return fs.readFile(item.path); + } - return this.defaults[name]; - }).asCallback(callback); + return this.defaults[name]; + }) + .asCallback(callback); }; Scaffold.prototype.set = function(name, content, callback) { const { scaffoldDir } = this; - return this._getScaffold(name).then(item => { - let path = item ? item.path : join(scaffoldDir, name); - if (!extname(path)) path += '.md'; + return this._getScaffold(name) + .then(item => { + let path = item ? item.path : join(scaffoldDir, name); + if (!extname(path)) path += '.md'; - return fs.writeFile(path, content); - }).asCallback(callback); + return fs.writeFile(path, content); + }) + .asCallback(callback); }; Scaffold.prototype.remove = function(name, callback) { - return this._getScaffold(name).then(item => { - if (!item) return; + return this._getScaffold(name) + .then(item => { + if (!item) return; - return fs.unlink(item.path); - }).asCallback(callback); + return fs.unlink(item.path); + }) + .asCallback(callback); }; module.exports = Scaffold; diff --git a/lib/models/asset.js b/lib/models/asset.js index 30320d9417..ee9865a74f 100644 --- a/lib/models/asset.js +++ b/lib/models/asset.js @@ -5,10 +5,10 @@ const { join } = require('path'); module.exports = ctx => { const Asset = new Schema({ - _id: {type: String, required: true}, - path: {type: String, required: true}, - modified: {type: Boolean, default: true}, - renderable: {type: Boolean, default: true} + _id: { type: String, required: true }, + path: { type: String, required: true }, + modified: { type: Boolean, default: true }, + renderable: { type: Boolean, default: true } }); Asset.virtual('source').get(function() { diff --git a/lib/models/cache.js b/lib/models/cache.js index 1e3c9cd39d..00e9bb34ce 100644 --- a/lib/models/cache.js +++ b/lib/models/cache.js @@ -5,9 +5,9 @@ const Promise = require('bluebird'); module.exports = ctx => { const Cache = new Schema({ - _id: {type: String, required: true}, - hash: {type: String, default: ''}, - modified: {type: Number, default: Date.now} + _id: { type: String, required: true }, + hash: { type: String, default: '' }, + modified: { type: Number, default: Date.now } }); Cache.static('compareFile', function(id, hashFn, statFn) { @@ -16,52 +16,58 @@ module.exports = ctx => { // If cache does not exist, then it must be a new file. We have to get both // file hash and stats. if (!cache) { - return Promise.all([hashFn(id), statFn(id)]).spread((hash, stats) => this.insert({ - _id: id, - hash, - modified: stats.mtime - })).thenReturn({ - type: 'create' - }); + return Promise.all([hashFn(id), statFn(id)]) + .spread((hash, stats) => + this.insert({ + _id: id, + hash, + modified: stats.mtime + }) + ) + .thenReturn({ + type: 'create' + }); } let mtime; // Get file stats - return statFn(id).then(stats => { - mtime = stats.mtime; + return statFn(id) + .then(stats => { + mtime = stats.mtime; - // Skip the file if the modified time is unchanged - if (cache.modified === mtime) { - return { - type: 'skip' - }; - } + // Skip the file if the modified time is unchanged + if (cache.modified === mtime) { + return { + type: 'skip' + }; + } - // Get file hash - return hashFn(id); - }).then(result => { - // If the result is an object, skip the following steps because it's an - // unchanged file - if (typeof result === 'object') return result; + // Get file hash + return hashFn(id); + }) + .then(result => { + // If the result is an object, skip the following steps because it's an + // unchanged file + if (typeof result === 'object') return result; - const hash = result; + const hash = result; - // Skip the file if the hash is unchanged - if (cache.hash === hash) { - return { - type: 'skip' - }; - } + // Skip the file if the hash is unchanged + if (cache.hash === hash) { + return { + type: 'skip' + }; + } - // Update cache info - cache.hash = hash; - cache.modified = mtime; + // Update cache info + cache.hash = hash; + cache.modified = mtime; - return cache.save().thenReturn({ - type: 'update' + return cache.save().thenReturn({ + type: 'update' + }); }); - }); }); return Cache; diff --git a/lib/models/category.js b/lib/models/category.js index a025b5316a..ea6d3023b9 100644 --- a/lib/models/category.js +++ b/lib/models/category.js @@ -5,8 +5,8 @@ const { slugize } = require('hexo-util'); module.exports = ctx => { const Category = new Schema({ - name: {type: String, required: true}, - parent: {type: Schema.Types.CUID, ref: 'Category'} + name: { type: String, required: true }, + parent: { type: Schema.Types.CUID, ref: 'Category' } }); Category.virtual('slug').get(function() { @@ -24,7 +24,7 @@ module.exports = ctx => { const map = ctx.config.category_map || {}; name = map[name] || name; - str += slugize(name, {transform: ctx.config.filename_case}); + str += slugize(name, { transform: ctx.config.filename_case }); return str; }); @@ -44,10 +44,12 @@ module.exports = ctx => { Category.virtual('posts').get(function() { const PostCategory = ctx.model('PostCategory'); - const ids = PostCategory.find({category_id: this._id}).map(item => item.post_id); + const ids = PostCategory.find({ category_id: this._id }).map( + item => item.post_id + ); return ctx.locals.get('posts').find({ - _id: {$in: ids} + _id: { $in: ids } }); }); @@ -61,10 +63,13 @@ module.exports = ctx => { if (!name) return; const Category = ctx.model('Category'); - const cat = Category.findOne({ - name, - parent: parent || {$exists: false} - }, {lean: true}); + const cat = Category.findOne( + { + name, + parent: parent || { $exists: false } + }, + { lean: true } + ); if (cat) { throw new Error(`Category \`${name}\` has already existed!`); @@ -74,7 +79,7 @@ module.exports = ctx => { // Remove PostCategory references Category.pre('remove', data => { const PostCategory = ctx.model('PostCategory'); - return PostCategory.remove({category_id: data._id}); + return PostCategory.remove({ category_id: data._id }); }); return Category; diff --git a/lib/models/data.js b/lib/models/data.js index c4eaccd126..20b2466c3d 100644 --- a/lib/models/data.js +++ b/lib/models/data.js @@ -4,7 +4,7 @@ const { Schema } = require('warehouse'); module.exports = ctx => { const Data = new Schema({ - _id: {type: String, required: true}, + _id: { type: String, required: true }, data: Object }); diff --git a/lib/models/page.js b/lib/models/page.js index f946abb25d..de8e6c3da9 100644 --- a/lib/models/page.js +++ b/lib/models/page.js @@ -7,7 +7,7 @@ const moment = require('moment'); module.exports = ctx => { const Page = new Schema({ - title: {type: String, default: ''}, + title: { type: String, default: '' }, date: { type: Moment, default: moment, @@ -20,15 +20,15 @@ module.exports = ctx => { language: ctx.config.languages, timezone: ctx.config.timezone }, - comments: {type: Boolean, default: true}, - layout: {type: String, default: 'page'}, - _content: {type: String, default: ''}, - source: {type: String, required: true}, - path: {type: String, required: true}, - raw: {type: String, default: ''}, - content: {type: String}, - excerpt: {type: String}, - more: {type: String} + comments: { type: Boolean, default: true }, + layout: { type: String, default: 'page' }, + _content: { type: String, default: '' }, + source: { type: String, required: true }, + path: { type: String, required: true }, + raw: { type: String, default: '' }, + content: { type: String }, + excerpt: { type: String }, + more: { type: String } }); Page.virtual('permalink').get(function() { diff --git a/lib/models/post.js b/lib/models/post.js index 27fc275a0d..e7f7c22a95 100644 --- a/lib/models/post.js +++ b/lib/models/post.js @@ -17,7 +17,7 @@ function removeEmptyTag(tags) { module.exports = ctx => { const Post = new Schema({ id: String, - title: {type: String, default: ''}, + title: { type: String, default: '' }, date: { type: Moment, default: moment, @@ -30,22 +30,22 @@ module.exports = ctx => { language: ctx.config.languages, timezone: ctx.config.timezone }, - comments: {type: Boolean, default: true}, - layout: {type: String, default: 'post'}, - _content: {type: String, default: ''}, - source: {type: String, required: true}, - slug: {type: String, required: true}, + comments: { type: Boolean, default: true }, + layout: { type: String, default: 'post' }, + _content: { type: String, default: '' }, + source: { type: String, required: true }, + slug: { type: String, required: true }, photos: [String], - link: {type: String, default: ''}, - raw: {type: String, default: ''}, - published: {type: Boolean, default: true}, - content: {type: String}, - excerpt: {type: String}, - more: {type: String} + link: { type: String, default: '' }, + raw: { type: String, default: '' }, + published: { type: Boolean, default: true }, + content: { type: String }, + excerpt: { type: String }, + more: { type: String } }); Post.virtual('path').get(function() { - const path = ctx.execFilterSync('post_permalink', this, {context: ctx}); + const path = ctx.execFilterSync('post_permalink', this, { context: ctx }); return typeof path === 'string' ? path : ''; }); @@ -70,9 +70,11 @@ module.exports = ctx => { const PostTag = ctx.model('PostTag'); const Tag = ctx.model('Tag'); - const ids = PostTag.find({post_id: this._id}, {lean: true}).map(item => item.tag_id); + const ids = PostTag.find({ post_id: this._id }, { lean: true }).map( + item => item.tag_id + ); - return Tag.find({_id: {$in: ids}}); + return Tag.find({ _id: { $in: ids } }); }); Post.method('setTags', function(tags) { @@ -81,60 +83,74 @@ module.exports = ctx => { const PostTag = ctx.model('PostTag'); const Tag = ctx.model('Tag'); const id = this._id; - const existed = PostTag.find({post_id: id}, {lean: true}).map(pickID); + const existed = PostTag.find({ post_id: id }, { lean: true }).map(pickID); return Promise.map(tags, tag => { // Find the tag by name - const data = Tag.findOne({name: tag}, {lean: true}); + const data = Tag.findOne({ name: tag }, { lean: true }); if (data) return data; // Insert the tag if not exist - return Tag.insert({name: tag}).catch(err => { + return Tag.insert({ name: tag }).catch(err => { // Try to find the tag again. Throw the error if not found - const data = Tag.findOne({name: tag}, {lean: true}); + const data = Tag.findOne({ name: tag }, { lean: true }); if (data) return data; throw err; }); - }).map(tag => { - // Find the reference - const ref = PostTag.findOne({post_id: id, tag_id: tag._id}, {lean: true}); - if (ref) return ref; - - // Insert the reference if not exist - return PostTag.insert({ - post_id: id, - tag_id: tag._id - }); - }).then(tags => { - // Remove old tags - const deleted = existed.filter(item => !tags.map(pickID).includes(item)); - return deleted; - }).map(tag => PostTag.removeById(tag)); + }) + .map(tag => { + // Find the reference + const ref = PostTag.findOne( + { post_id: id, tag_id: tag._id }, + { lean: true } + ); + if (ref) return ref; + + // Insert the reference if not exist + return PostTag.insert({ + post_id: id, + tag_id: tag._id + }); + }) + .then(tags => { + // Remove old tags + const deleted = existed.filter( + item => !tags.map(pickID).includes(item) + ); + return deleted; + }) + .map(tag => PostTag.removeById(tag)); }); Post.virtual('categories').get(function() { const PostCategory = ctx.model('PostCategory'); const Category = ctx.model('Category'); - const ids = PostCategory.find({post_id: this._id}, {lean: true}).map(item => item.category_id); + const ids = PostCategory.find({ post_id: this._id }, { lean: true }).map( + item => item.category_id + ); - return Category.find({_id: {$in: ids}}); + return Category.find({ _id: { $in: ids } }); }); Post.method('setCategories', function(cats) { // Remove empty categories, preserving hierarchies - cats = cats.filter(cat => { - return Array.isArray(cat) || (cat != null && cat !== ''); - }).map(cat => { - return Array.isArray(cat) ? removeEmptyTag(cat) : `${cat}`; - }); + cats = cats + .filter(cat => { + return Array.isArray(cat) || (cat != null && cat !== ''); + }) + .map(cat => { + return Array.isArray(cat) ? removeEmptyTag(cat) : `${cat}`; + }); const PostCategory = ctx.model('PostCategory'); const Category = ctx.model('Category'); const id = this._id; const allIds = []; - const existed = PostCategory.find({post_id: id}, {lean: true}).map(pickID); + const existed = PostCategory.find({ post_id: id }, { lean: true }).map( + pickID + ); const hasHierarchy = cats.filter(Array.isArray).length > 0; // Add a hierarchy of categories @@ -145,10 +161,13 @@ module.exports = ctx => { // MUST USE "Promise.each". return Promise.each(catHierarchy, (cat, i) => { // Find the category by name - const data = Category.findOne({ - name: cat, - parent: i ? parentIds[i - 1] : {$exists: false} - }, {lean: true}); + const data = Category.findOne( + { + name: cat, + parent: i ? parentIds[i - 1] : { $exists: false } + }, + { lean: true } + ); if (data) { allIds.push(data._id); @@ -157,57 +176,72 @@ module.exports = ctx => { } // Insert the category if not exist - const obj = {name: cat}; + const obj = { name: cat }; if (i) obj.parent = parentIds[i - 1]; - return Category.insert(obj).catch(err => { - // Try to find the category again. Throw the error if not found - const data = Category.findOne({ - name: cat, - parent: i ? parentIds[i - 1] : {$exists: false} - }, {lean: true}); - - if (data) return data; - throw err; - }).then(data => { - allIds.push(data._id); - parentIds.push(data._id); - return data; - }); + return Category.insert(obj) + .catch(err => { + // Try to find the category again. Throw the error if not found + const data = Category.findOne( + { + name: cat, + parent: i ? parentIds[i - 1] : { $exists: false } + }, + { lean: true } + ); + + if (data) return data; + throw err; + }) + .then(data => { + allIds.push(data._id); + parentIds.push(data._id); + return data; + }); }); }; - return (hasHierarchy ? Promise.each(cats, addHierarchy) : Promise.resolve(addHierarchy(cats)) - ).then(() => allIds).map(catId => { - // Find the reference - const ref = PostCategory.findOne({post_id: id, category_id: catId}, {lean: true}); - if (ref) return ref; - - // Insert the reference if not exist - return PostCategory.insert({ - post_id: id, - category_id: catId - }); - }).then(postCats => // Remove old categories - existed.filter(item => !postCats.map(pickID).includes(item))).map(cat => PostCategory.removeById(cat)); + return (hasHierarchy + ? Promise.each(cats, addHierarchy) + : Promise.resolve(addHierarchy(cats)) + ) + .then(() => allIds) + .map(catId => { + // Find the reference + const ref = PostCategory.findOne( + { post_id: id, category_id: catId }, + { lean: true } + ); + if (ref) return ref; + + // Insert the reference if not exist + return PostCategory.insert({ + post_id: id, + category_id: catId + }); + }) + .then(( + postCats // Remove old categories + ) => existed.filter(item => !postCats.map(pickID).includes(item))) + .map(cat => PostCategory.removeById(cat)); }); // Remove PostTag references Post.pre('remove', data => { const PostTag = ctx.model('PostTag'); - return PostTag.remove({post_id: data._id}); + return PostTag.remove({ post_id: data._id }); }); // Remove PostCategory references Post.pre('remove', data => { const PostCategory = ctx.model('PostCategory'); - return PostCategory.remove({post_id: data._id}); + return PostCategory.remove({ post_id: data._id }); }); // Remove assets Post.pre('remove', data => { const PostAsset = ctx.model('PostAsset'); - return PostAsset.remove({post: data._id}); + return PostAsset.remove({ post: data._id }); }); return Post; diff --git a/lib/models/post_asset.js b/lib/models/post_asset.js index 316178e53e..6f690b6b28 100644 --- a/lib/models/post_asset.js +++ b/lib/models/post_asset.js @@ -5,11 +5,11 @@ const { join } = require('path'); module.exports = ctx => { const PostAsset = new Schema({ - _id: {type: String, required: true}, - slug: {type: String, required: true}, - modified: {type: Boolean, default: true}, - post: {type: Schema.Types.CUID, ref: 'Post'}, - renderable: {type: Boolean, default: true} + _id: { type: String, required: true }, + slug: { type: String, required: true }, + modified: { type: Boolean, default: true }, + post: { type: Schema.Types.CUID, ref: 'Post' }, + renderable: { type: Boolean, default: true } }); PostAsset.virtual('path').get(function() { diff --git a/lib/models/post_category.js b/lib/models/post_category.js index fa28d33880..1fcd86aa44 100644 --- a/lib/models/post_category.js +++ b/lib/models/post_category.js @@ -4,8 +4,8 @@ const { Schema } = require('warehouse'); module.exports = ctx => { const PostCategory = new Schema({ - post_id: {type: Schema.Types.CUID, ref: 'Post'}, - category_id: {type: Schema.Types.CUID, ref: 'Category'} + post_id: { type: Schema.Types.CUID, ref: 'Post' }, + category_id: { type: Schema.Types.CUID, ref: 'Category' } }); return PostCategory; diff --git a/lib/models/post_tag.js b/lib/models/post_tag.js index fac9ef98b0..322a16c0ec 100644 --- a/lib/models/post_tag.js +++ b/lib/models/post_tag.js @@ -4,8 +4,8 @@ const { Schema } = require('warehouse'); module.exports = ctx => { const PostTag = new Schema({ - post_id: {type: Schema.Types.CUID, ref: 'Post'}, - tag_id: {type: Schema.Types.CUID, ref: 'Tag'} + post_id: { type: Schema.Types.CUID, ref: 'Post' }, + tag_id: { type: Schema.Types.CUID, ref: 'Tag' } }); return PostTag; diff --git a/lib/models/tag.js b/lib/models/tag.js index 22491f1fd9..afefb6f236 100644 --- a/lib/models/tag.js +++ b/lib/models/tag.js @@ -6,7 +6,7 @@ const { hasOwnProperty: hasOwn } = Object.prototype; module.exports = ctx => { const Tag = new Schema({ - name: {type: String, required: true} + name: { type: String, required: true } }); Tag.virtual('slug').get(function() { @@ -18,7 +18,7 @@ module.exports = ctx => { name = map[name] || name; } - return slugize(name, {transform: ctx.config.filename_case}); + return slugize(name, { transform: ctx.config.filename_case }); }); Tag.virtual('path').get(function() { @@ -35,10 +35,10 @@ module.exports = ctx => { Tag.virtual('posts').get(function() { const PostTag = ctx.model('PostTag'); - const ids = PostTag.find({tag_id: this._id}).map(item => item.post_id); + const ids = PostTag.find({ tag_id: this._id }).map(item => item.post_id); return ctx.locals.get('posts').find({ - _id: {$in: ids} + _id: { $in: ids } }); }); @@ -52,7 +52,7 @@ module.exports = ctx => { if (!name) return; const Tag = ctx.model('Tag'); - const tag = Tag.findOne({name}, {lean: true}); + const tag = Tag.findOne({ name }, { lean: true }); if (tag) { throw new Error(`Tag \`${name}\` has already existed!`); @@ -62,7 +62,7 @@ module.exports = ctx => { // Remove PostTag references Tag.pre('remove', data => { const PostTag = ctx.model('PostTag'); - return PostTag.remove({tag_id: data._id}); + return PostTag.remove({ tag_id: data._id }); }); return Tag; diff --git a/lib/plugins/console/clean.js b/lib/plugins/console/clean.js index ab6895f165..4914025155 100644 --- a/lib/plugins/console/clean.js +++ b/lib/plugins/console/clean.js @@ -7,7 +7,7 @@ function cleanConsole(args) { return Promise.all([ deleteDatabase(this), deletePublicDir(this), - this.execFilter('after_clean', null, {context: this}) + this.execFilter('after_clean', null, { context: this }) ]); } diff --git a/lib/plugins/console/config.js b/lib/plugins/console/config.js index a8b1828dc4..4e1af71513 100644 --- a/lib/plugins/console/config.js +++ b/lib/plugins/console/config.js @@ -23,18 +23,22 @@ function configConsole(args) { const configPath = this.config_path; const ext = extname(configPath); - return fs.exists(configPath).then(exist => { - if (!exist) return {}; - return this.render.render({path: configPath}); - }).then(config => { - if (!config) config = {}; - - setProperty(config, key, castValue(value)); - - const result = ext === '.json' ? JSON.stringify(config) : yaml.dump(config); - - return fs.writeFile(configPath, result); - }); + return fs + .exists(configPath) + .then(exist => { + if (!exist) return {}; + return this.render.render({ path: configPath }); + }) + .then(config => { + if (!config) config = {}; + + setProperty(config, key, castValue(value)); + + const result = + ext === '.json' ? JSON.stringify(config) : yaml.dump(config); + + return fs.writeFile(configPath, result); + }); } function getProperty(obj, key) { diff --git a/lib/plugins/console/deploy.js b/lib/plugins/console/deploy.js index 433f0f272f..4f553b4c19 100644 --- a/lib/plugins/console/deploy.js +++ b/lib/plugins/console/deploy.js @@ -13,10 +13,13 @@ function deployConsole(args) { if (!config) { let help = ''; - help += 'You should configure deployment settings in _config.yml first!\n\n'; + help += + 'You should configure deployment settings in _config.yml first!\n\n'; help += 'Available deployer plugins:\n'; help += ` ${Object.keys(deployers).join(', ')}\n\n`; - help += `For more help, you can check the online docs: ${chalk.underline('https://hexo.io/')}`; + help += `For more help, you can check the online docs: ${chalk.underline( + 'https://hexo.io/' + )}`; console.log(help); return; @@ -35,29 +38,34 @@ function deployConsole(args) { this.call('generate', args).then(resolve, reject); }); } - }).then(() => { - this.emit('deployBefore'); + }) + .then(() => { + this.emit('deployBefore'); - if (!Array.isArray(config)) config = [config]; - return config; - }).each(item => { - if (!item.type) return; + if (!Array.isArray(config)) config = [config]; + return config; + }) + .each(item => { + if (!item.type) return; - const { type } = item; + const { type } = item; - if (!deployers[type]) { - this.log.error('Deployer not found: %s', chalk.magenta(type)); - return; - } + if (!deployers[type]) { + this.log.error('Deployer not found: %s', chalk.magenta(type)); + return; + } - this.log.info('Deploying: %s', chalk.magenta(type)); + this.log.info('Deploying: %s', chalk.magenta(type)); - return Reflect.apply(deployers[type], this, [assignIn({}, item, args)]).then(() => { - this.log.info('Deploy done: %s', chalk.magenta(type)); + return Reflect.apply(deployers[type], this, [ + assignIn({}, item, args) + ]).then(() => { + this.log.info('Deploy done: %s', chalk.magenta(type)); + }); + }) + .then(() => { + this.emit('deployAfter'); }); - }).then(() => { - this.emit('deployAfter'); - }); } module.exports = deployConsole; diff --git a/lib/plugins/console/generate.js b/lib/plugins/console/generate.js index ff7e9440cd..c14b76aa17 100644 --- a/lib/plugins/console/generate.js +++ b/lib/plugins/console/generate.js @@ -28,57 +28,69 @@ function generateConsole(args = {}) { const dest = join(publicDir, path); - return fs.exists(dest).then(exist => { - if (force || !exist) return writeFile(path, true); - if (route.isModified(path)) return writeFile(path); - }).finally(() => { - // Unlock the file - generatingFiles[path] = false; - }); + return fs + .exists(dest) + .then(exist => { + if (force || !exist) return writeFile(path, true); + if (route.isModified(path)) return writeFile(path); + }) + .finally(() => { + // Unlock the file + generatingFiles[path] = false; + }); } function writeFile(path, force) { const dest = join(publicDir, path); const cacheId = `public/${path}`; - const dataStream = wrapDataStream(route.get(path), {bail}); + const dataStream = wrapDataStream(route.get(path), { bail }); const cacheStream = new CacheStream(); const hashStream = new HashStream(); // Get data => Cache data => Calculate hash - return pipeStream(dataStream, cacheStream, hashStream).then(() => { - const cache = Cache.findById(cacheId); - const hash = hashStream.read().toString('hex'); - - // Skip generating if hash is unchanged - if (!force && cache && cache.hash === hash) { - return; - } - - // Save new hash to cache - return Cache.save({ - _id: cacheId, - hash - }).then(() => // Write cache data to public folder - fs.writeFile(dest, cacheStream.getCache())).then(() => { - log.info('Generated: %s', chalk.magenta(path)); - return true; + return pipeStream(dataStream, cacheStream, hashStream) + .then(() => { + const cache = Cache.findById(cacheId); + const hash = hashStream.read().toString('hex'); + + // Skip generating if hash is unchanged + if (!force && cache && cache.hash === hash) { + return; + } + + // Save new hash to cache + return Cache.save({ + _id: cacheId, + hash + }) + .then(() => + // Write cache data to public folder + fs.writeFile(dest, cacheStream.getCache()) + ) + .then(() => { + log.info('Generated: %s', chalk.magenta(path)); + return true; + }); + }) + .finally(() => { + // Destroy cache + cacheStream.destroy(); }); - }).finally(() => { - // Destroy cache - cacheStream.destroy(); - }); } function deleteFile(path) { const dest = join(publicDir, path); - return fs.unlink(dest).then(() => { - log.info('Deleted: %s', chalk.magenta(path)); - }, err => { - // Skip ENOENT errors (file was deleted) - if (err.cause && err.cause.code === 'ENOENT') return; - throw err; - }); + return fs.unlink(dest).then( + () => { + log.info('Deleted: %s', chalk.magenta(path)); + }, + err => { + // Skip ENOENT errors (file was deleted) + if (err.cause && err.cause.code === 'ENOENT') return; + throw err; + } + ); } function wrapDataStream(dataStream, options) { @@ -106,58 +118,79 @@ function generateConsole(args = {}) { start = process.hrtime(); // Check the public folder - return fs.stat(publicDir).then(stats => { - if (!stats.isDirectory()) { - throw new Error('%s is not a directory', chalk.magenta(tildify(publicDir))); - } - }).catch(err => { - // Create public folder if not exists - if (err.cause && err.cause.code === 'ENOENT') { - return fs.mkdirs(publicDir); - } - - throw err; - }).then(() => { - const task = (fn, path) => () => fn(path); - const doTask = fn => fn(); - const routeList = route.list(); - const publicFiles = Cache.filter(item => item._id.startsWith('public/')).map(item => item._id.substring(7)); - const tasks = publicFiles.filter(path => !routeList.includes(path)) - // Clean files - .map(path => task(deleteFile, path)) - // Generate files - .concat(routeList.map(path => task(generateFile, path))); - - return Promise.all(Promise.map(tasks, doTask, { concurrency: parseFloat(concurrency || 'Infinity') })); - }).then(result => { - const interval = prettyHrtime(process.hrtime(start)); - const count = result.filter(Boolean).length; - - log.info('%d files generated in %s', count, chalk.cyan(interval)); - }); + return fs + .stat(publicDir) + .then(stats => { + if (!stats.isDirectory()) { + throw new Error( + '%s is not a directory', + chalk.magenta(tildify(publicDir)) + ); + } + }) + .catch(err => { + // Create public folder if not exists + if (err.cause && err.cause.code === 'ENOENT') { + return fs.mkdirs(publicDir); + } + + throw err; + }) + .then(() => { + const task = (fn, path) => () => fn(path); + const doTask = fn => fn(); + const routeList = route.list(); + const publicFiles = Cache.filter(item => + item._id.startsWith('public/') + ).map(item => item._id.substring(7)); + const tasks = publicFiles + .filter(path => !routeList.includes(path)) + // Clean files + .map(path => task(deleteFile, path)) + // Generate files + .concat(routeList.map(path => task(generateFile, path))); + + return Promise.all( + Promise.map(tasks, doTask, { + concurrency: parseFloat(concurrency || 'Infinity') + }) + ); + }) + .then(result => { + const interval = prettyHrtime(process.hrtime(start)); + const count = result.filter(Boolean).length; + + log.info('%d files generated in %s', count, chalk.cyan(interval)); + }); } if (args.w || args.watch) { - return this.watch().then(firstGenerate).then(() => { - log.info('Hexo is watching for file changes. Press Ctrl+C to exit.'); - - // Watch changes of the route - route.on('update', path => { - const modified = route.isModified(path); - if (!modified) return; - - generateFile(path); - }).on('remove', path => { - deleteFile(path); + return this.watch() + .then(firstGenerate) + .then(() => { + log.info('Hexo is watching for file changes. Press Ctrl+C to exit.'); + + // Watch changes of the route + route + .on('update', path => { + const modified = route.isModified(path); + if (!modified) return; + + generateFile(path); + }) + .on('remove', path => { + deleteFile(path); + }); }); - }); } - return this.load().then(firstGenerate).then(() => { - if (args.d || args.deploy) { - return this.call('deploy', args); - } - }); + return this.load() + .then(firstGenerate) + .then(() => { + if (args.d || args.deploy) { + return this.call('deploy', args); + } + }); } // Pipe a stream from one to another diff --git a/lib/plugins/console/index.js b/lib/plugins/console/index.js index 3a34b7b0fb..23ec68c7a9 100644 --- a/lib/plugins/console/index.js +++ b/lib/plugins/console/index.js @@ -3,78 +3,159 @@ module.exports = function(ctx) { const { console } = ctx.extend; - console.register('clean', 'Remove generated files and cache.', require('./clean')); + console.register( + 'clean', + 'Remove generated files and cache.', + require('./clean') + ); - console.register('config', 'Get or set configurations.', { - usage: '[name] [value]', - arguments: [ - {name: 'name', desc: 'Setting name. Leave it blank if you want to show all configurations.'}, - {name: 'value', desc: 'New value of a setting. Leave it blank if you just want to show a single configuration.'} - ] - }, require('./config')); + console.register( + 'config', + 'Get or set configurations.', + { + usage: '[name] [value]', + arguments: [ + { + name: 'name', + desc: + 'Setting name. Leave it blank if you want to show all configurations.' + }, + { + name: 'value', + desc: + 'New value of a setting. Leave it blank if you just want to show a single configuration.' + } + ] + }, + require('./config') + ); - console.register('deploy', 'Deploy your website.', { - options: [ - {name: '--setup', desc: 'Setup without deployment'}, - {name: '-g, --generate', desc: 'Generate before deployment'} - ] - }, require('./deploy')); + console.register( + 'deploy', + 'Deploy your website.', + { + options: [ + { name: '--setup', desc: 'Setup without deployment' }, + { name: '-g, --generate', desc: 'Generate before deployment' } + ] + }, + require('./deploy') + ); - console.register('generate', 'Generate static files.', { - options: [ - {name: '-d, --deploy', desc: 'Deploy after generated'}, - {name: '-f, --force', desc: 'Force regenerate'}, - {name: '-w, --watch', desc: 'Watch file changes'}, - {name: '-b, --bail', desc: 'Raise an error if any unhandled exception is thrown during generation'}, - {name: '-c, --concurrency', desc: 'Maximum number of files to be generated in parallel. Default is infinity'} - ] - }, require('./generate')); + console.register( + 'generate', + 'Generate static files.', + { + options: [ + { name: '-d, --deploy', desc: 'Deploy after generated' }, + { name: '-f, --force', desc: 'Force regenerate' }, + { name: '-w, --watch', desc: 'Watch file changes' }, + { + name: '-b, --bail', + desc: + 'Raise an error if any unhandled exception is thrown during generation' + }, + { + name: '-c, --concurrency', + desc: + 'Maximum number of files to be generated in parallel. Default is infinity' + } + ] + }, + require('./generate') + ); - console.register('list', 'List the information of the site', { - desc: 'List the information of the site.', - usage: ' ', - arguments: [ - {name: 'type', desc: 'Available types: page, post, route, tag, category'} - ] - }, require('./list')); + console.register( + 'list', + 'List the information of the site', + { + desc: 'List the information of the site.', + usage: ' ', + arguments: [ + { + name: 'type', + desc: 'Available types: page, post, route, tag, category' + } + ] + }, + require('./list') + ); - console.register('migrate', 'Migrate your site from other system to Hexo.', { - init: true, - usage: ' ', - arguments: [ - {name: 'type', desc: 'Migrator type.'} - ] - }, require('./migrate')); + console.register( + 'migrate', + 'Migrate your site from other system to Hexo.', + { + init: true, + usage: ' ', + arguments: [{ name: 'type', desc: 'Migrator type.' }] + }, + require('./migrate') + ); - console.register('new', 'Create a new post.', { - usage: '[layout] ', - arguments: [ - {name: 'layout', desc: 'Post layout. Use post, page, draft or whatever you want.'}, - {name: 'title', desc: 'Post title. Wrap it with quotations to escape.'} - ], - options: [ - {name: '-r, --replace', desc: 'Replace the current post if existed.'}, - {name: '-s, --slug', desc: 'Post slug. Customize the URL of the post.'}, - {name: '-p, --path', desc: 'Post path. Customize the path of the post.'} - ] - }, require('./new')); + console.register( + 'new', + 'Create a new post.', + { + usage: '[layout] ', + arguments: [ + { + name: 'layout', + desc: 'Post layout. Use post, page, draft or whatever you want.' + }, + { + name: 'title', + desc: 'Post title. Wrap it with quotations to escape.' + } + ], + options: [ + { name: '-r, --replace', desc: 'Replace the current post if existed.' }, + { + name: '-s, --slug', + desc: 'Post slug. Customize the URL of the post.' + }, + { + name: '-p, --path', + desc: 'Post path. Customize the path of the post.' + } + ] + }, + require('./new') + ); - console.register('publish', 'Moves a draft post from _drafts to _posts folder.', { - usage: '[layout] ', - arguments: [ - {name: 'layout', desc: 'Post layout. Use post, page, draft or whatever you want.'}, - {name: 'filename', desc: 'Draft filename. "hello-world" for example.'} - ] - }, require('./publish')); + console.register( + 'publish', + 'Moves a draft post from _drafts to _posts folder.', + { + usage: '[layout] ', + arguments: [ + { + name: 'layout', + desc: 'Post layout. Use post, page, draft or whatever you want.' + }, + { name: 'filename', desc: 'Draft filename. "hello-world" for example.' } + ] + }, + require('./publish') + ); - console.register('render', 'Render files with renderer plugins.', { - init: true, - desc: 'Render files with renderer plugins (e.g. Markdown) and save them at the specified path.', - usage: ' [file2] ...', - options: [ - {name: '--output', desc: 'Output destination. Result will be printed in the terminal if the output destination is not set.'}, - {name: '--engine', desc: 'Specify render engine'}, - {name: '--pretty', desc: 'Prettify JSON output'} - ] - }, require('./render')); + console.register( + 'render', + 'Render files with renderer plugins.', + { + init: true, + desc: + 'Render files with renderer plugins (e.g. Markdown) and save them at the specified path.', + usage: ' [file2] ...', + options: [ + { + name: '--output', + desc: + 'Output destination. Result will be printed in the terminal if the output destination is not set.' + }, + { name: '--engine', desc: 'Specify render engine' }, + { name: '--pretty', desc: 'Prettify JSON output' } + ] + }, + require('./render') + ); }; diff --git a/lib/plugins/console/list/category.js b/lib/plugins/console/list/category.js index 85b9045df2..3e52a8b0a2 100644 --- a/lib/plugins/console/list/category.js +++ b/lib/plugins/console/list/category.js @@ -7,7 +7,9 @@ const common = require('./common'); function listCategory() { const categories = this.model('Category'); - const data = categories.sort({name: 1}).map(cate => [cate.name, String(cate.length)]); + const data = categories + .sort({ name: 1 }) + .map(cate => [cate.name, String(cate.length)]); // Table header const header = ['Name', 'Posts'].map(str => chalk.underline(str)); diff --git a/lib/plugins/console/list/index.js b/lib/plugins/console/list/index.js index 4ab6fba1d0..172e688c5a 100644 --- a/lib/plugins/console/list/index.js +++ b/lib/plugins/console/list/index.js @@ -17,10 +17,12 @@ function listConsole(args) { // Display help message if user didn't input any arguments if (!type || !alias[type]) { - return this.call('help', {_: ['list']}); + return this.call('help', { _: ['list'] }); } - return this.load().then(() => Reflect.apply(store[alias[type]], this, [args])); + return this.load().then(() => + Reflect.apply(store[alias[type]], this, [args]) + ); } module.exports = listConsole; diff --git a/lib/plugins/console/list/page.js b/lib/plugins/console/list/page.js index 230853c016..8b2e298cf3 100644 --- a/lib/plugins/console/list/page.js +++ b/lib/plugins/console/list/page.js @@ -7,7 +7,7 @@ const common = require('./common'); function listPage() { const Page = this.model('Page'); - const data = Page.sort({date: 1}).map(page => { + const data = Page.sort({ date: 1 }).map(page => { const date = page.date.format('YYYY-MM-DD'); return [chalk.gray(date), page.title, chalk.magenta(page.source)]; }); diff --git a/lib/plugins/console/list/post.js b/lib/plugins/console/list/post.js index 8a4a368144..1f29b5e092 100644 --- a/lib/plugins/console/list/post.js +++ b/lib/plugins/console/list/post.js @@ -11,7 +11,7 @@ function mapName(item) { function listPost() { const Post = this.model('Post'); - const data = Post.sort({published: -1, date: 1}).map(post => { + const data = Post.sort({ published: -1, date: 1 }).map(post => { const date = post.published ? post.date.format('YYYY-MM-DD') : 'Draft'; const tags = post.tags.map(mapName); const categories = post.categories.map(mapName); @@ -26,7 +26,9 @@ function listPost() { }); // Table header - const header = ['Date', 'Title', 'Path', 'Category', 'Tags'].map(str => chalk.underline(str)); + const header = ['Date', 'Title', 'Path', 'Category', 'Tags'].map(str => + chalk.underline(str) + ); data.unshift(header); diff --git a/lib/plugins/console/list/tag.js b/lib/plugins/console/list/tag.js index f01453b679..ed3ccae9f2 100644 --- a/lib/plugins/console/list/tag.js +++ b/lib/plugins/console/list/tag.js @@ -7,7 +7,11 @@ const common = require('./common'); function listTag() { const Tag = this.model('Tag'); - const data = Tag.sort({name: 1}).map(tag => [tag.name, String(tag.length), chalk.magenta(tag.path)]); + const data = Tag.sort({ name: 1 }).map(tag => [ + tag.name, + String(tag.length), + chalk.magenta(tag.path) + ]); // Table header const header = ['Name', 'Posts', 'Path'].map(str => chalk.underline(str)); diff --git a/lib/plugins/console/migrate.js b/lib/plugins/console/migrate.js index 9592525805..d4db6f4c58 100644 --- a/lib/plugins/console/migrate.js +++ b/lib/plugins/console/migrate.js @@ -5,7 +5,7 @@ const chalk = require('chalk'); function migrateConsole(args) { // Display help message if user didn't input any arguments if (!args._.length) { - return this.call('help', {_: ['migrate']}); + return this.call('help', { _: ['migrate'] }); } const type = args._.shift(); @@ -17,7 +17,9 @@ function migrateConsole(args) { help += `${type.magenta} migrator plugin is not installed.\n\n`; help += 'Installed migrator plugins:\n'; help += ` ${Object.keys(migrators).join(', ')}\n\n`; - help += `For more help, you can check the online docs: ${chalk.underline('https://hexo.io/')}`; + help += `For more help, you can check the online docs: ${chalk.underline( + 'https://hexo.io/' + )}`; console.log(help); return; diff --git a/lib/plugins/console/new.js b/lib/plugins/console/new.js index ace8d996ec..e41020707c 100644 --- a/lib/plugins/console/new.js +++ b/lib/plugins/console/new.js @@ -20,7 +20,7 @@ const reservedKeys = { function newConsole(args) { // Display help message if user didn't input any arguments if (!args._.length) { - return this.call('help', {_: ['new']}); + return this.call('help', { _: ['new'] }); } const data = { diff --git a/lib/plugins/console/publish.js b/lib/plugins/console/publish.js index 030063e9f9..fa1d6a6aef 100644 --- a/lib/plugins/console/publish.js +++ b/lib/plugins/console/publish.js @@ -6,15 +6,20 @@ const chalk = require('chalk'); function publishConsole(args) { // Display help message if user didn't input any arguments if (!args._.length) { - return this.call('help', {_: ['publish']}); + return this.call('help', { _: ['publish'] }); } - return this.post.publish({ - slug: args._.pop(), - layout: args._.length ? args._[0] : this.config.default_layout - }, args.r || args.replace).then(post => { - this.log.info('Published: %s', chalk.magenta(tildify(post.path))); - }); + return this.post + .publish( + { + slug: args._.pop(), + layout: args._.length ? args._[0] : this.config.default_layout + }, + args.r || args.replace + ) + .then(post => { + this.log.info('Published: %s', chalk.magenta(tildify(post.path))); + }); } module.exports = publishConsole; diff --git a/lib/plugins/console/render.js b/lib/plugins/console/render.js index 937c2d1b03..51133cb4fc 100644 --- a/lib/plugins/console/render.js +++ b/lib/plugins/console/render.js @@ -9,7 +9,7 @@ const chalk = require('chalk'); function renderConsole(args) { // Display help message if user didn't input any arguments if (!args._.length) { - return this.call('help', {_: 'render'}); + return this.call('help', { _: 'render' }); } const baseDir = this.base_dir; @@ -18,26 +18,33 @@ function renderConsole(args) { const start = process.hrtime(); const { log } = this; - return this.render.render({ - path: src, - engine: args.engine - }).then(result => { - if (typeof result === 'object') { - if (args.pretty) { - result = JSON.stringify(result, null, ' '); - } else { - result = JSON.stringify(result); + return this.render + .render({ + path: src, + engine: args.engine + }) + .then(result => { + if (typeof result === 'object') { + if (args.pretty) { + result = JSON.stringify(result, null, ' '); + } else { + result = JSON.stringify(result); + } } - } - if (!output) return console.log(result); + if (!output) return console.log(result); - const dest = resolve(baseDir, output); - const interval = prettyHrtime(process.hrtime(start)); + const dest = resolve(baseDir, output); + const interval = prettyHrtime(process.hrtime(start)); - log.info('Rendered in %s: %s -> %s', chalk.cyan(interval), chalk.magenta(tildify(src)), chalk.magenta(tildify(dest))); - return fs.writeFile(dest, result); - }); + log.info( + 'Rendered in %s: %s -> %s', + chalk.cyan(interval), + chalk.magenta(tildify(src)), + chalk.magenta(tildify(dest)) + ); + return fs.writeFile(dest, result); + }); } module.exports = renderConsole; diff --git a/lib/plugins/filter/after_post_render/external_link.js b/lib/plugins/filter/after_post_render/external_link.js index 229f3a3f41..17edfe979c 100644 --- a/lib/plugins/filter/after_post_render/external_link.js +++ b/lib/plugins/filter/after_post_render/external_link.js @@ -8,25 +8,28 @@ function externalLinkFilter(data) { const siteHost = url.parse(config.url).hostname || config.url; - data.content = data.content.replace(/ /gi, (str, hrefStr, href) => { - if (/target=/gi.test(str)) return str; - - const data = url.parse(href); - // Exit if the link doesn't have protocol, which means it's a internal link - // Exit if the url has same host with config.url - if (!data.protocol || data.hostname === siteHost) return str; - - if (/rel=/gi.test(str)) { - str = str.replace(/rel="(.*?)"/gi, (relStr, rel) => { - if (!rel.includes('noopenner')) relStr = relStr.replace(rel, `${rel} noopener`); - return relStr; - }); - return str.replace(hrefStr, `${hrefStr} target="_blank"`); + data.content = data.content.replace( + / /gi, + (str, hrefStr, href) => { + if (/target=/gi.test(str)) return str; + + const data = url.parse(href); + // Exit if the link doesn't have protocol, which means it's a internal link + // Exit if the url has same host with config.url + if (!data.protocol || data.hostname === siteHost) return str; + + if (/rel=/gi.test(str)) { + str = str.replace(/rel="(.*?)"/gi, (relStr, rel) => { + if (!rel.includes('noopenner')) + relStr = relStr.replace(rel, `${rel} noopener`); + return relStr; + }); + return str.replace(hrefStr, `${hrefStr} target="_blank"`); + } + + return str.replace(hrefStr, `${hrefStr} target="_blank" rel="noopener"`); } - - return str.replace(hrefStr, `${hrefStr} target="_blank" rel="noopener"`); - }); - + ); } module.exports = externalLinkFilter; diff --git a/lib/plugins/filter/before_generate/render_post.js b/lib/plugins/filter/before_generate/render_post.js index 100450004a..4a874835fb 100644 --- a/lib/plugins/filter/before_generate/render_post.js +++ b/lib/plugins/filter/before_generate/render_post.js @@ -8,7 +8,7 @@ function renderPostFilter(data) { return Promise.map(posts, post => { post.content = post._content; - post.site = {data}; + post.site = { data }; return this.post.render(post.full_source, post).then(() => post.save()); }); diff --git a/lib/plugins/filter/before_post_render/backtick_code_block.js b/lib/plugins/filter/before_post_render/backtick_code_block.js index 06dec6739a..57d4a9b3a8 100644 --- a/lib/plugins/filter/before_post_render/backtick_code_block.js +++ b/lib/plugins/filter/before_post_render/backtick_code_block.js @@ -10,52 +10,55 @@ const rLangCaption = /([^\s]+)\s*(.+)?/; function backtickCodeBlock(data) { const config = this.config.highlight || {}; if (!config.enable) return; - data.content = data.content.replace(rBacktick, ($0, start, $2, _args, content, end) => { - const args = _args.split('=').shift(); - - const options = { - hljs: config.hljs, - autoDetect: config.auto_detect, - gutter: config.line_number, - tab: config.tab_replace - }; - - if (options.gutter) { - config.first_line_number = config.first_line_number || 'always1'; - if (config.first_line_number === 'inline') { - - // setup line number by inline - _args = _args.replace('=+', '='); - options.gutter = _args.includes('='); - - // setup fiestLineNumber; - options.firstLine = options.gutter ? _args.split('=')[1] || 1 : 0; - } - } + data.content = data.content.replace( + rBacktick, + ($0, start, $2, _args, content, end) => { + const args = _args.split('=').shift(); + + const options = { + hljs: config.hljs, + autoDetect: config.auto_detect, + gutter: config.line_number, + tab: config.tab_replace + }; + + if (options.gutter) { + config.first_line_number = config.first_line_number || 'always1'; + if (config.first_line_number === 'inline') { + // setup line number by inline + _args = _args.replace('=+', '='); + options.gutter = _args.includes('='); - if (args) { - const match = rAllOptions.exec(args) || rLangCaption.exec(args); + // setup fiestLineNumber; + options.firstLine = options.gutter ? _args.split('=')[1] || 1 : 0; + } + } + if (args) { + const match = rAllOptions.exec(args) || rLangCaption.exec(args); - if (match) { - options.lang = match[1]; + if (match) { + options.lang = match[1]; - if (match[2]) { - options.caption = `${match[2]}`; + if (match[2]) { + options.caption = `${match[2]}`; - if (match[3]) { - options.caption += `${match[4] ? match[4] : 'link'}`; + if (match[3]) { + options.caption += `${ + match[4] ? match[4] : 'link' + }`; + } } } } - } - content = highlight(stripIndent(content), options) - .replace(/{/g, '{') - .replace(/}/g, '}'); + content = highlight(stripIndent(content), options) + .replace(/{/g, '{') + .replace(/}/g, '}'); - return `${start} ${content} ${end ? '\n\n' : ''}`; - }); + return `${start}${content} ${end ? '\n\n' : ''}`; + } + ); } module.exports = backtickCodeBlock; diff --git a/lib/plugins/filter/meta_generator.js b/lib/plugins/filter/meta_generator.js index 8440b9b0fe..af23b91faa 100644 --- a/lib/plugins/filter/meta_generator.js +++ b/lib/plugins/filter/meta_generator.js @@ -2,12 +2,17 @@ function hexoMetaGeneratorInject(data) { const { config } = this; - if (!config.meta_generator || - data.match(/`; - return data.replace(/(?!<\/head>).+?<\/head>/, (str) => str.replace('', `${hexoGeneratorTag}`)); + return data.replace(/(?!<\/head>).+?<\/head>/, str => + str.replace('', `${hexoGeneratorTag}`) + ); } module.exports = hexoMetaGeneratorInject; diff --git a/lib/plugins/filter/new_post_path.js b/lib/plugins/filter/new_post_path.js index 4773c0cca1..76fd438243 100644 --- a/lib/plugins/filter/new_post_path.js +++ b/lib/plugins/filter/new_post_path.js @@ -73,12 +73,16 @@ function newPostPathFilter(data = {}, replace) { if (!reservedKeys[key]) filenameData[key] = data[key]; } - target = join(postDir, permalink.stringify( - defaults(filenameData, permalinkDefaults))); + target = join( + postDir, + permalink.stringify(defaults(filenameData, permalinkDefaults)) + ); } } } else { - return Promise.reject(new TypeError('Either data.path or data.slug is required!')); + return Promise.reject( + new TypeError('Either data.path or data.slug is required!') + ); } if (!extname(target)) { diff --git a/lib/plugins/filter/post_permalink.js b/lib/plugins/filter/post_permalink.js index 9fc519c933..ce5bea213d 100644 --- a/lib/plugins/filter/post_permalink.js +++ b/lib/plugins/filter/post_permalink.js @@ -11,7 +11,7 @@ function postPermalinkFilter(data) { id: data.id || data._id, title: data.slug, name: typeof data.slug === 'string' ? basename(data.slug) : '', - post_title: slugize(data.title, {transform: 1}), + post_title: slugize(data.title, { transform: 1 }), year: data.date.format('YYYY'), month: data.date.format('MM'), day: data.date.format('DD'), @@ -39,7 +39,11 @@ function postPermalinkFilter(data) { // Use Object.getOwnPropertyDescriptor to copy getters to avoid "Maximum call // stack size exceeded" error - Object.defineProperty(meta, key, Object.getOwnPropertyDescriptor(data, key)); + Object.defineProperty( + meta, + key, + Object.getOwnPropertyDescriptor(data, key) + ); } return permalink.stringify(defaults(meta, config.permalink_defaults)); diff --git a/lib/plugins/filter/template_locals/i18n.js b/lib/plugins/filter/template_locals/i18n.js index 7348a3d580..74b7165985 100644 --- a/lib/plugins/filter/template_locals/i18n.js +++ b/lib/plugins/filter/template_locals/i18n.js @@ -29,7 +29,10 @@ function i18nLocalsFilter(locals) { page.canonical_path = page.canonical_path || locals.path; - const languages = _([].concat(lang, i18nConfigLanguages, i18nLanguages)).compact().uniq().value(); + const languages = _([].concat(lang, i18nConfigLanguages, i18nLanguages)) + .compact() + .uniq() + .value(); locals.__ = i18n.__(languages); locals._p = i18n._p(languages); diff --git a/lib/plugins/generator/asset.js b/lib/plugins/generator/asset.js index b24ad1a3e2..d3a16a47f2 100644 --- a/lib/plugins/generator/asset.js +++ b/lib/plugins/generator/asset.js @@ -6,9 +6,11 @@ const { extname } = require('path'); const chalk = require('chalk'); const process = (name, ctx) => { - return Promise.filter(ctx.model(name).toArray(), asset => fs.exists(asset.source).tap(exist => { - if (!exist) return asset.remove(); - })).map(asset => { + return Promise.filter(ctx.model(name).toArray(), asset => + fs.exists(asset.source).tap(exist => { + if (!exist) return asset.remove(); + }) + ).map(asset => { const { source } = asset; let { path } = asset; const data = { @@ -21,12 +23,19 @@ const process = (name, ctx) => { path = `${filename}.${ctx.render.getOutput(path)}`; - data.data = () => ctx.render.render({ - path: source, - toString: true - }).catch(err => { - ctx.log.error({err}, 'Asset render failed: %s', chalk.magenta(path)); - }); + data.data = () => + ctx.render + .render({ + path: source, + toString: true + }) + .catch(err => { + ctx.log.error( + { err }, + 'Asset render failed: %s', + chalk.magenta(path) + ); + }); } else { data.data = () => fs.createReadStream(source); } @@ -36,10 +45,9 @@ const process = (name, ctx) => { }; function assetGenerator(locals) { - return Promise.all([ - process('Asset', this), - process('PostAsset', this) - ]).then(data => [].concat(...data)); + return Promise.all([process('Asset', this), process('PostAsset', this)]).then( + data => [].concat(...data) + ); } module.exports = assetGenerator; diff --git a/lib/plugins/helper/date.js b/lib/plugins/helper/date.js index 8bad844b9d..0bd54d39f6 100644 --- a/lib/plugins/helper/date.js +++ b/lib/plugins/helper/date.js @@ -55,7 +55,12 @@ function relativeDateHelper(date) { function timeTagHelper(date, format) { const { config } = this; - return ``; + return ``; } function getLanguage(ctx) { diff --git a/lib/plugins/helper/fragment_cache.js b/lib/plugins/helper/fragment_cache.js index 95c1a9a5fe..d220dc5c16 100644 --- a/lib/plugins/helper/fragment_cache.js +++ b/lib/plugins/helper/fragment_cache.js @@ -6,7 +6,7 @@ module.exports = ctx => { return function fragmentCache(id, fn) { if (this.cache && cache[id] != null) return cache[id]; - const result = cache[id] = fn(); + const result = (cache[id] = fn()); return result; }; }; diff --git a/lib/plugins/helper/gravatar.js b/lib/plugins/helper/gravatar.js index 184a1df38d..a0eb86f36a 100644 --- a/lib/plugins/helper/gravatar.js +++ b/lib/plugins/helper/gravatar.js @@ -4,12 +4,15 @@ const crypto = require('crypto'); const querystring = require('querystring'); function md5(str) { - return crypto.createHash('md5').update(str).digest('hex'); + return crypto + .createHash('md5') + .update(str) + .digest('hex'); } function gravatarHelper(email, options) { if (typeof options === 'number') { - options = {s: options}; + options = { s: options }; } let str = `https://www.gravatar.com/avatar/${md5(email.toLowerCase())}`; diff --git a/lib/plugins/helper/image_tag.js b/lib/plugins/helper/image_tag.js index 8fc8d92da9..8f67666e58 100644 --- a/lib/plugins/helper/image_tag.js +++ b/lib/plugins/helper/image_tag.js @@ -3,9 +3,12 @@ const { htmlTag } = require('hexo-util'); function imageTagHelper(path, options = {}) { - const attrs = Object.assign({ - src: this.url_for(path) - }, options); + const attrs = Object.assign( + { + src: this.url_for(path) + }, + options + ); if (attrs.class && Array.isArray(attrs.class)) { attrs.class = attrs.class.join(' '); diff --git a/lib/plugins/helper/link_to.js b/lib/plugins/helper/link_to.js index ed9605c9f6..bc89da2338 100644 --- a/lib/plugins/helper/link_to.js +++ b/lib/plugins/helper/link_to.js @@ -3,14 +3,17 @@ const { htmlTag } = require('hexo-util'); function linkToHelper(path, text, options = {}) { - if (typeof options === 'boolean') options = {external: options}; + if (typeof options === 'boolean') options = { external: options }; if (!text) text = path.replace(/^https?:\/\/|\/$/g, ''); - const attrs = Object.assign({ - href: this.url_for(path), - title: text - }, options); + const attrs = Object.assign( + { + href: this.url_for(path), + title: text + }, + options + ); if (attrs.external) { attrs.target = '_blank'; diff --git a/lib/plugins/helper/list_archives.js b/lib/plugins/helper/list_archives.js index 861e92fa15..35ba3d03ca 100644 --- a/lib/plugins/helper/list_archives.js +++ b/lib/plugins/helper/list_archives.js @@ -8,7 +8,9 @@ function listArchivesHelper(options = {}) { let { format } = options; const type = options.type || 'monthly'; const { style = 'list', transform, separator = ', ' } = options; - const showCount = Object.prototype.hasOwnProperty.call(options, 'show_count') ? options.show_count : true; + const showCount = Object.prototype.hasOwnProperty.call(options, 'show_count') + ? options.show_count + : true; const className = options.class || 'archive'; const order = options.order || -1; let result = ''; diff --git a/lib/plugins/helper/list_categories.js b/lib/plugins/helper/list_categories.js index f867ed6903..de184ef1d1 100644 --- a/lib/plugins/helper/list_categories.js +++ b/lib/plugins/helper/list_categories.js @@ -1,7 +1,10 @@ 'use strict'; function listCategoriesHelper(categories, options) { - if (!options && (!categories || !Object.prototype.hasOwnProperty.call(categories, 'length'))) { + if ( + !options && + (!categories || !Object.prototype.hasOwnProperty.call(categories, 'length')) + ) { options = categories; categories = this.site.categories; } @@ -10,13 +13,20 @@ function listCategoriesHelper(categories, options) { options = options || {}; const { style = 'list', transform, separator = ', ', suffix = '' } = options; - const showCount = Object.prototype.hasOwnProperty.call(options, 'show_count') ? options.show_count : true; + const showCount = Object.prototype.hasOwnProperty.call(options, 'show_count') + ? options.show_count + : true; const className = options.class || 'category'; const depth = options.depth ? parseInt(options.depth, 10) : 0; const orderby = options.orderby || 'name'; const order = options.order || 1; const showCurrent = options.show_current || false; - const childrenIndicator = Object.prototype.hasOwnProperty.call(options, 'children_indicator') ? options.children_indicator : false; + const childrenIndicator = Object.prototype.hasOwnProperty.call( + options, + 'children_indicator' + ) + ? options.children_indicator + : false; const prepareQuery = parent => { const query = {}; @@ -24,10 +34,13 @@ function listCategoriesHelper(categories, options) { if (parent) { query.parent = parent; } else { - query.parent = {$exists: false}; + query.parent = { $exists: false }; } - return categories.find(query).sort(orderby, order).filter(cat => cat.length); + return categories + .find(query) + .sort(orderby, order) + .filter(cat => cat.length); }; const hierarchicalList = (level, parent) => { @@ -50,14 +63,18 @@ function listCategoriesHelper(categories, options) { } // special case: category page - isCurrent = isCurrent || (this.page.base && this.page.base.startsWith(cat.path)); + isCurrent = + isCurrent || (this.page.base && this.page.base.startsWith(cat.path)); } - const additionalClassName = child && childrenIndicator ? ` ${childrenIndicator}` : ''; + const additionalClassName = + child && childrenIndicator ? ` ${childrenIndicator}` : ''; result += ``; - result += ``; + result += ``; result += transform ? transform(cat.name) : cat.name; result += ''; @@ -81,7 +98,9 @@ function listCategoriesHelper(categories, options) { prepareQuery(parent).forEach((cat, i) => { if (i || level) result += separator; - result += ``; + result += ``; result += transform ? transform(cat.name) : cat.name; if (showCount) { diff --git a/lib/plugins/helper/list_posts.js b/lib/plugins/helper/list_posts.js index 3161edd71b..66e8727d82 100644 --- a/lib/plugins/helper/list_posts.js +++ b/lib/plugins/helper/list_posts.js @@ -1,7 +1,10 @@ 'use strict'; function listPostsHelper(posts, options) { - if (!options && (!posts || !Object.prototype.hasOwnProperty.call(posts, 'length'))) { + if ( + !options && + (!posts || !Object.prototype.hasOwnProperty.call(posts, 'length')) + ) { options = posts; posts = this.site.posts; } @@ -30,7 +33,9 @@ function listPostsHelper(posts, options) { result += ` `; - result += ``; + result += ``; result += transform ? transform(title) : title; result += ''; @@ -44,7 +49,9 @@ function listPostsHelper(posts, options) { const title = post.title || post.slug; - result += ``; + result += ``; result += transform ? transform(title) : title; result += ''; }); diff --git a/lib/plugins/helper/list_tags.js b/lib/plugins/helper/list_tags.js index 881bfa506c..81c9717cef 100644 --- a/lib/plugins/helper/list_tags.js +++ b/lib/plugins/helper/list_tags.js @@ -1,7 +1,10 @@ 'use strict'; function listTagsHelper(tags, options) { - if (!options && (!tags || !Object.prototype.hasOwnProperty.call(tags, 'length'))) { + if ( + !options && + (!tags || !Object.prototype.hasOwnProperty.call(tags, 'length')) + ) { options = tags; tags = this.site.tags; } @@ -10,7 +13,9 @@ function listTagsHelper(tags, options) { options = options || {}; const { style = 'list', transform, separator = ', ', suffix = '' } = options; - const showCount = Object.prototype.hasOwnProperty.call(options, 'show_count') ? options.show_count : true; + const showCount = Object.prototype.hasOwnProperty.call(options, 'show_count') + ? options.show_count + : true; const className = options.class || 'tag'; const orderby = options.orderby || 'name'; const order = options.order || 1; @@ -31,7 +36,9 @@ function listTagsHelper(tags, options) { tags.forEach(tag => { result += ` `; - result += ``; + result += ``; result += transform ? transform(tag.name) : tag.name; result += ''; @@ -47,7 +54,9 @@ function listTagsHelper(tags, options) { tags.forEach((tag, i) => { if (i) result += separator; - result += ``; + result += ``; result += transform ? transform(tag.name) : tag.name; if (showCount) { diff --git a/lib/plugins/helper/mail_to.js b/lib/plugins/helper/mail_to.js index 5443388106..09a7bca472 100644 --- a/lib/plugins/helper/mail_to.js +++ b/lib/plugins/helper/mail_to.js @@ -7,10 +7,13 @@ function mailToHelper(path, text, options = {}) { if (Array.isArray(path)) path = path.join(','); if (!text) text = path; - const attrs = Object.assign({ - href: `mailto:${path}`, - title: text - }, options); + const attrs = Object.assign( + { + href: `mailto:${path}`, + title: text + }, + options + ); if (attrs.class && Array.isArray(attrs.class)) { attrs.class = attrs.class.join(' '); diff --git a/lib/plugins/helper/number_format.js b/lib/plugins/helper/number_format.js index 0db807eb76..bbedd0362e 100644 --- a/lib/plugins/helper/number_format.js +++ b/lib/plugins/helper/number_format.js @@ -30,7 +30,8 @@ function numberFormatHelper(num, options = {}) { const afterLast = after[precision]; const last = parseInt(after[precision - 1], 10); - afterResult = after.substr(0, precision - 1) + (afterLast < 5 ? last : last + 1); + afterResult = + after.substr(0, precision - 1) + (afterLast < 5 ? last : last + 1); } else { afterResult = after; for (let i = 0, len = precision - afterLength; i < len; i++) { diff --git a/lib/plugins/helper/open_graph.js b/lib/plugins/helper/open_graph.js index 279f1db908..eb1b358433 100644 --- a/lib/plugins/helper/open_graph.js +++ b/lib/plugins/helper/open_graph.js @@ -27,24 +27,34 @@ function og(name, content, escape) { } function openGraphHelper(options = {}) { - const { config, page } = this; const { content } = page; let images = options.image || options.images || page.photos || []; - let description = options.description || page.description || page.excerpt || content || config.description; - const keywords = page.keywords || (page.tags && page.tags.length ? page.tags : undefined) || config.keywords; + let description = + options.description || + page.description || + page.excerpt || + content || + config.description; + const keywords = + page.keywords || + (page.tags && page.tags.length ? page.tags : undefined) || + config.keywords; const title = options.title || page.title || config.title; const type = options.type || (this.is_post() ? 'article' : 'website'); const url = options.url || this.url; const siteName = options.site_name || config.title; const twitterCard = options.twitter_card || 'summary'; - const updated = options.updated !== false ? options.updated || page.updated : false; - const language = options.language || page.lang || page.language || config.language; + const updated = + options.updated !== false ? options.updated || page.updated : false; + const language = + options.language || page.lang || page.language || config.language; if (!Array.isArray(images)) images = [images]; if (description) { - description = stripHTML(description).substring(0, 200) + description = stripHTML(description) + .substring(0, 200) .trim() // Remove prefixing/trailing spaces .replace(//g, '>') @@ -64,7 +74,6 @@ function openGraphHelper(options = {}) { images.push(img[1]); } } - } let result = ''; @@ -77,9 +86,15 @@ function openGraphHelper(options = {}) { if (typeof keywords === 'string') { result += meta('keywords', keywords); } else if (keywords.length) { - result += meta('keywords', keywords.map(tag => { - return tag.name ? tag.name : tag; - }).filter(keyword => !!keyword).join()); + result += meta( + 'keywords', + keywords + .map(tag => { + return tag.name ? tag.name : tag; + }) + .filter(keyword => !!keyword) + .join() + ); } } @@ -110,7 +125,10 @@ function openGraphHelper(options = {}) { }); if (updated) { - if ((moment.isMoment(updated) || moment.isDate(updated)) && !isNaN(updated.valueOf())) { + if ( + (moment.isMoment(updated) || moment.isDate(updated)) && + !isNaN(updated.valueOf()) + ) { result += og('og:updated_time', updated.toISOString()); } } @@ -133,7 +151,10 @@ function openGraphHelper(options = {}) { } if (options.google_plus) { - result += `${htmlTag('link', {rel: 'publisher', href: options.google_plus})}\n`; + result += `${htmlTag('link', { + rel: 'publisher', + href: options.google_plus + })}\n`; } if (options.fb_admins) { diff --git a/lib/plugins/helper/paginator.js b/lib/plugins/helper/paginator.js index 622251c63a..55a9e12fe0 100644 --- a/lib/plugins/helper/paginator.js +++ b/lib/plugins/helper/paginator.js @@ -14,9 +14,17 @@ const createPageTag = (options, ctx) => { return i => { if (i === current) { - return htmlTag('span', { class: 'page-number current' }, transform ? transform(i) : i); + return htmlTag( + 'span', + { class: 'page-number current' }, + transform ? transform(i) : i + ); } - return htmlTag('a', { class: 'page-number', href: link(i) }, transform ? transform(i) : i); + return htmlTag( + 'a', + { class: 'page-number', href: link(i) }, + transform ? transform(i) : i + ); }; }; @@ -41,9 +49,12 @@ const pagenasionPartShow = (tags, options, ctx) => { } = options; const leftEnd = current <= endSize ? current - 1 : endSize; - const rightEnd = total - current <= endSize ? current + 1 : total - endSize + 1; - const leftMid = current - midSize <= endSize ? leftEnd + 1 : current - midSize; - const rightMid = current + midSize + endSize > total ? rightEnd - 1 : current + midSize; + const rightEnd = + total - current <= endSize ? current + 1 : total - endSize + 1; + const leftMid = + current - midSize <= endSize ? leftEnd + 1 : current - midSize; + const rightMid = + current + midSize + endSize > total ? rightEnd - 1 : current + midSize; const spaceHtml = htmlTag('span', { class: 'space' }, space); const pageTag = createPageTag(options, ctx); @@ -87,18 +98,21 @@ const pagenasionPartShow = (tags, options, ctx) => { }; function paginatorHelper(options = {}) { - options = Object.assign({ - base: this.page.base || '', - current: this.page.current || 0, - format: `${this.config.pagination_dir}/%d/`, - total: this.page.total || 1, - end_size: 1, - mid_size: 2, - space: '…', - next_text: 'Next', - prev_text: 'Prev', - prev_next: true - }, options); + options = Object.assign( + { + base: this.page.base || '', + current: this.page.current || 0, + format: `${this.config.pagination_dir}/%d/`, + total: this.page.total || 1, + end_size: 1, + mid_size: 2, + space: '…', + next_text: 'Next', + prev_text: 'Prev', + prev_next: true + }, + options + ); const { current, @@ -116,7 +130,13 @@ function paginatorHelper(options = {}) { // Display the link to the previous page if (prevNext && current > 1) { - tags.push(htmlTag('a', { class: 'extend prev', rel: 'prev', href: link(current - 1)}, prevText)); + tags.push( + htmlTag( + 'a', + { class: 'extend prev', rel: 'prev', href: link(current - 1) }, + prevText + ) + ); } if (options.show_all) { @@ -127,7 +147,13 @@ function paginatorHelper(options = {}) { // Display the link to the next page if (prevNext && current < total) { - tags.push(htmlTag('a', { class: 'extend next', rel: 'next', href: link(current + 1) }, nextText)); + tags.push( + htmlTag( + 'a', + { class: 'extend next', rel: 'next', href: link(current + 1) }, + nextText + ) + ); } return tags.join(''); diff --git a/lib/plugins/helper/partial.js b/lib/plugins/helper/partial.js index bc3994189c..0b4d4573b9 100644 --- a/lib/plugins/helper/partial.js +++ b/lib/plugins/helper/partial.js @@ -2,34 +2,35 @@ const { dirname, join } = require('path'); -module.exports = ctx => function partial(name, locals, options = {}) { - if (typeof name !== 'string') throw new TypeError('name must be a string!'); - - const { cache } = options; - const viewDir = this.view_dir; - const currentView = this.filename.substring(viewDir.length); - const path = join(dirname(currentView), name); - const view = ctx.theme.getView(path) || ctx.theme.getView(name); - const viewLocals = { layout: false }; - - if (!view) { - throw new Error(`Partial ${name} does not exist. (in ${currentView})`); - } - - if (options.only) { - Object.assign(viewLocals, locals); - } else { - Object.assign(viewLocals, this, locals); - } - - // Partial don't need layout - viewLocals.layout = false; - - if (cache) { - const cacheId = typeof cache === 'string' ? cache : view.path; - - return this.fragment_cache(cacheId, () => view.renderSync(viewLocals)); - } - - return view.renderSync(viewLocals); -}; +module.exports = ctx => + function partial(name, locals, options = {}) { + if (typeof name !== 'string') throw new TypeError('name must be a string!'); + + const { cache } = options; + const viewDir = this.view_dir; + const currentView = this.filename.substring(viewDir.length); + const path = join(dirname(currentView), name); + const view = ctx.theme.getView(path) || ctx.theme.getView(name); + const viewLocals = { layout: false }; + + if (!view) { + throw new Error(`Partial ${name} does not exist. (in ${currentView})`); + } + + if (options.only) { + Object.assign(viewLocals, locals); + } else { + Object.assign(viewLocals, this, locals); + } + + // Partial don't need layout + viewLocals.layout = false; + + if (cache) { + const cacheId = typeof cache === 'string' ? cache : view.path; + + return this.fragment_cache(cacheId, () => view.renderSync(viewLocals)); + } + + return view.renderSync(viewLocals); + }; diff --git a/lib/plugins/helper/render.js b/lib/plugins/helper/render.js index f71bdb2917..d7f9c5d8b0 100644 --- a/lib/plugins/helper/render.js +++ b/lib/plugins/helper/render.js @@ -1,8 +1,12 @@ 'use strict'; -module.exports = ctx => function render(text, engine, options) { - return ctx.render.renderSync({ - text, - engine - }, options); -}; +module.exports = ctx => + function render(text, engine, options) { + return ctx.render.renderSync( + { + text, + engine + }, + options + ); + }; diff --git a/lib/plugins/helper/search_form.js b/lib/plugins/helper/search_form.js index ea81c2c4c4..2ab6c413b5 100644 --- a/lib/plugins/helper/search_form.js +++ b/lib/plugins/helper/search_form.js @@ -5,7 +5,15 @@ function searchFormHelper(options = {}) { const className = options.class || 'search-form'; const { text = 'Search', button } = options; - return ``; + return ``; } module.exports = searchFormHelper; diff --git a/lib/plugins/helper/tagcloud.js b/lib/plugins/helper/tagcloud.js index 9fd5bda421..dd18572c2a 100644 --- a/lib/plugins/helper/tagcloud.js +++ b/lib/plugins/helper/tagcloud.js @@ -3,7 +3,10 @@ const Color = require('hexo-util').Color; function tagcloudHelper(tags, options) { - if (!options && (!tags || !Object.prototype.hasOwnProperty.call(tags, 'length'))) { + if ( + !options && + (!tags || !Object.prototype.hasOwnProperty.call(tags, 'length')) + ) { options = tags; tags = this.site.tags; } @@ -57,7 +60,7 @@ function tagcloudHelper(tags, options) { tags.forEach(tag => { const ratio = length ? sizes.indexOf(tag.length) / length : 0; - const size = min + ((max - min) * ratio); + const size = min + (max - min) * ratio; let style = `font-size: ${parseFloat(size.toFixed(2))}${unit};`; if (color) { @@ -66,7 +69,9 @@ function tagcloudHelper(tags, options) { } result.push( - `${transform ? transform(tag.name) : tag.name}` + `${ + transform ? transform(tag.name) : tag.name + }` ); }); diff --git a/lib/plugins/helper/toc.js b/lib/plugins/helper/toc.js index ddf4023816..81dd1f852a 100644 --- a/lib/plugins/helper/toc.js +++ b/lib/plugins/helper/toc.js @@ -7,14 +7,26 @@ function tocHelper(str, options = {}) { if (!cheerio) cheerio = require('cheerio'); const $ = cheerio.load(str); - const headingsMaxDepth = Object.prototype.hasOwnProperty.call(options, 'max_depth') ? options.max_depth : 6; - const headingsSelector = ['h1', 'h2', 'h3', 'h4', 'h5', 'h6'].slice(0, headingsMaxDepth).join(','); + const headingsMaxDepth = Object.prototype.hasOwnProperty.call( + options, + 'max_depth' + ) + ? options.max_depth + : 6; + const headingsSelector = ['h1', 'h2', 'h3', 'h4', 'h5', 'h6'] + .slice(0, headingsMaxDepth) + .join(','); const headings = $(headingsSelector); if (!headings.length) return ''; const className = options.class || 'toc'; - const listNumber = Object.prototype.hasOwnProperty.call(options, 'list_number') ? options.list_number : true; + const listNumber = Object.prototype.hasOwnProperty.call( + options, + 'list_number' + ) + ? options.list_number + : true; let result = ` `; const lastNumber = [0, 0, 0, 0, 0, 0]; let firstLevel = 0; @@ -23,9 +35,7 @@ function tocHelper(str, options = {}) { function getId(ele) { const id = $(ele).attr('id'); const $parent = $(ele).parent(); - return id || - ($parent.length < 1 ? null : - getId($parent)); + return id || ($parent.length < 1 ? null : getId($parent)); } headings.each(function() { diff --git a/lib/plugins/helper/url_for.js b/lib/plugins/helper/url_for.js index 868dd56b3c..1810465a04 100644 --- a/lib/plugins/helper/url_for.js +++ b/lib/plugins/helper/url_for.js @@ -11,9 +11,12 @@ function urlForHelper(path = '/', options) { const { root } = config; const data = url.parse(path); - options = Object.assign({ - relative: config.relative_link - }, options); + options = Object.assign( + { + relative: config.relative_link + }, + options + ); // Exit if this is an external path if (data.protocol) { diff --git a/lib/plugins/processor/asset.js b/lib/plugins/processor/asset.js index ee39ade154..1239075c93 100644 --- a/lib/plugins/processor/asset.js +++ b/lib/plugins/processor/asset.js @@ -10,7 +10,7 @@ module.exports = ctx => { function processPage(file) { const Page = ctx.model('Page'); const { path } = file; - const doc = Page.findOne({source: path}); + const doc = Page.findOne({ source: path }); const { config } = ctx; const { timezone } = config; @@ -26,10 +26,7 @@ module.exports = ctx => { return; } - return Promise.all([ - file.stat(), - file.read() - ]).spread((stats, content) => { + return Promise.all([file.stat(), file.read()]).spread((stats, content) => { const data = yfm(content); const output = ctx.render.getOutput(path); @@ -64,7 +61,10 @@ module.exports = ctx => { data.path += `.${output}`; } } else { - data.path = `${path.substring(0, path.length - extname(path).length)}.${output}`; + data.path = `${path.substring( + 0, + path.length - extname(path).length + )}.${output}`; } if (!data.layout && output !== 'html' && output !== 'htm') { @@ -73,7 +73,7 @@ module.exports = ctx => { // FIXME: Data may be inserted when reading files. Load it again to prevent // race condition. We have to solve this in warehouse. - const doc = Page.findOne({source: path}); + const doc = Page.findOne({ source: path }); if (doc) { return doc.replace(data); @@ -106,14 +106,20 @@ module.exports = ctx => { return { pattern: new Pattern(path => { - if (common.isTmpFile(path) || common.isMatch(path, ctx.config.exclude)) return; + if (common.isTmpFile(path) || common.isMatch(path, ctx.config.exclude)) + return; - if (common.isHiddenFile(path) && !common.isMatch(path, ctx.config.include)) { + if ( + common.isHiddenFile(path) && + !common.isMatch(path, ctx.config.include) + ) { return; } return { - renderable: ctx.render.isRenderable(path) && !common.isMatch(path, ctx.config.skip_render) + renderable: + ctx.render.isRenderable(path) && + !common.isMatch(path, ctx.config.skip_render) }; }), diff --git a/lib/plugins/processor/post.js b/lib/plugins/processor/post.js index 6518e504b6..62495d4583 100644 --- a/lib/plugins/processor/post.js +++ b/lib/plugins/processor/post.js @@ -24,7 +24,7 @@ module.exports = ctx => { function processPost(file) { const Post = ctx.model('Post'); const { path } = file.params; - const doc = Post.findOne({source: file.path}); + const doc = Post.findOne({ source: file.path }); const { config } = ctx; const { timezone } = config; let categories, tags; @@ -41,105 +41,112 @@ module.exports = ctx => { return; } - return Promise.all([ - file.stat(), - file.read() - ]).spread((stats, content) => { - const data = yfm(content); - const info = parseFilename(config.new_post_name, path); - const keys = Object.keys(info); - - data.source = file.path; - data.raw = content; - data.slug = info.title; - - if (file.params.published) { - if (!Object.prototype.hasOwnProperty.call(data, 'published')) data.published = true; - } else { - data.published = false; - } - - for (let i = 0, len = keys.length; i < len; i++) { - const key = keys[i]; - if (!preservedKeys[key]) data[key] = info[key]; - } - - if (data.date) { - data.date = common.toDate(data.date); - } else if (info && info.year && (info.month || info.i_month) && (info.day || info.i_day)) { - data.date = new Date( - info.year, - parseInt(info.month || info.i_month, 10) - 1, - parseInt(info.day || info.i_day, 10) - ); - } - - if (data.date) { - if (timezone) data.date = common.timezone(data.date, timezone); - } else { - data.date = stats.birthtime; - } - - data.updated = common.toDate(data.updated); - - if (data.updated) { - if (timezone) data.updated = common.timezone(data.updated, timezone); - } else { - data.updated = stats.mtime; - } - - if (data.category && !data.categories) { - data.categories = data.category; - delete data.category; - } - - if (data.tag && !data.tags) { - data.tags = data.tag; - delete data.tag; - } - - categories = data.categories || []; - tags = data.tags || []; - - if (!Array.isArray(categories)) categories = [categories]; - if (!Array.isArray(tags)) tags = [tags]; - - if (data.photo && !data.photos) { - data.photos = data.photo; - delete data.photo; - } - - if (data.photos && !Array.isArray(data.photos)) { - data.photos = [data.photos]; - } - - if (data.link && !data.title) { - data.title = data.link.replace(/^https?:\/\/|\/$/g, ''); - } - - if (!data.title) { - data.title = data.slug; - } - - if (data.permalink) { - data.slug = data.permalink; - delete data.permalink; - } - - // FIXME: Data may be inserted when reading files. Load it again to prevent - // race condition. We have to solve this in warehouse. - const doc = Post.findOne({source: file.path}); - - if (doc) { - return doc.replace(data); - } - - return Post.insert(data); - }).then(doc => Promise.all([ - doc.setCategories(categories), - doc.setTags(tags), - scanAssetDir(doc) - ])); + return Promise.all([file.stat(), file.read()]) + .spread((stats, content) => { + const data = yfm(content); + const info = parseFilename(config.new_post_name, path); + const keys = Object.keys(info); + + data.source = file.path; + data.raw = content; + data.slug = info.title; + + if (file.params.published) { + if (!Object.prototype.hasOwnProperty.call(data, 'published')) + data.published = true; + } else { + data.published = false; + } + + for (let i = 0, len = keys.length; i < len; i++) { + const key = keys[i]; + if (!preservedKeys[key]) data[key] = info[key]; + } + + if (data.date) { + data.date = common.toDate(data.date); + } else if ( + info && + info.year && + (info.month || info.i_month) && + (info.day || info.i_day) + ) { + data.date = new Date( + info.year, + parseInt(info.month || info.i_month, 10) - 1, + parseInt(info.day || info.i_day, 10) + ); + } + + if (data.date) { + if (timezone) data.date = common.timezone(data.date, timezone); + } else { + data.date = stats.birthtime; + } + + data.updated = common.toDate(data.updated); + + if (data.updated) { + if (timezone) data.updated = common.timezone(data.updated, timezone); + } else { + data.updated = stats.mtime; + } + + if (data.category && !data.categories) { + data.categories = data.category; + delete data.category; + } + + if (data.tag && !data.tags) { + data.tags = data.tag; + delete data.tag; + } + + categories = data.categories || []; + tags = data.tags || []; + + if (!Array.isArray(categories)) categories = [categories]; + if (!Array.isArray(tags)) tags = [tags]; + + if (data.photo && !data.photos) { + data.photos = data.photo; + delete data.photo; + } + + if (data.photos && !Array.isArray(data.photos)) { + data.photos = [data.photos]; + } + + if (data.link && !data.title) { + data.title = data.link.replace(/^https?:\/\/|\/$/g, ''); + } + + if (!data.title) { + data.title = data.slug; + } + + if (data.permalink) { + data.slug = data.permalink; + delete data.permalink; + } + + // FIXME: Data may be inserted when reading files. Load it again to prevent + // race condition. We have to solve this in warehouse. + const doc = Post.findOne({ source: file.path }); + + if (doc) { + return doc.replace(data); + } + + return Post.insert(data); + }) + .then(doc => + Promise.all([ + doc.setCategories(categories), + doc.setTags(tags), + scanAssetDir(doc) + ]) + ); } function scanAssetDir(post) { @@ -150,25 +157,32 @@ module.exports = ctx => { const baseDirLength = baseDir.length; const PostAsset = ctx.model('PostAsset'); - return fs.stat(assetDir).then(stats => { - if (!stats.isDirectory()) return []; - - return fs.listDir(assetDir); - }).catch(err => { - if (err.cause && err.cause.code === 'ENOENT') return []; - throw err; - }).filter(item => !common.isTmpFile(item) && !common.isHiddenFile(item)).map(item => { - const id = join(assetDir, item).substring(baseDirLength).replace(/\\/g, '/'); - const asset = PostAsset.findById(id); - if (asset) return undefined; - - return PostAsset.save({ - _id: id, - post: post._id, - slug: item, - modified: true + return fs + .stat(assetDir) + .then(stats => { + if (!stats.isDirectory()) return []; + + return fs.listDir(assetDir); + }) + .catch(err => { + if (err.cause && err.cause.code === 'ENOENT') return []; + throw err; + }) + .filter(item => !common.isTmpFile(item) && !common.isHiddenFile(item)) + .map(item => { + const id = join(assetDir, item) + .substring(baseDirLength) + .replace(/\\/g, '/'); + const asset = PostAsset.findById(id); + if (asset) return undefined; + + return PostAsset.save({ + _id: id, + post: post._id, + slug: item, + modified: true + }); }); - }); } function processAsset(file) { @@ -186,7 +200,9 @@ module.exports = ctx => { } // TODO: Better post searching - const post = Post.toArray().find(post => file.source.startsWith(post.asset_dir)); + const post = Post.toArray().find(post => + file.source.startsWith(post.asset_dir) + ); if (post != null) { return PostAsset.save({ @@ -223,7 +239,9 @@ module.exports = ctx => { if (!result || common.isHiddenFile(result.path)) return; - result.renderable = ctx.render.isRenderable(path) && !common.isMatch(path, ctx.config.skip_render); + result.renderable = + ctx.render.isRenderable(path) && + !common.isMatch(path, ctx.config.skip_render); return result; }), diff --git a/lib/plugins/renderer/swig.js b/lib/plugins/renderer/swig.js index d272df7a0c..a1afca8ee7 100644 --- a/lib/plugins/renderer/swig.js +++ b/lib/plugins/renderer/swig.js @@ -23,13 +23,23 @@ swig.setDefaults({ }); // Hack: Override for tag of Swig -swig.setTag('for', forTag.parse, (...args) => { - const compile = forTag.compile(...args).split('\n'); - - compile.splice(3, 0, ' if (!Array.isArray(__l) && typeof __l.toArray === "function") { __l = __l.toArray(); }'); - - return compile.join('\n'); -}, forTag.ends, true); +swig.setTag( + 'for', + forTag.parse, + (...args) => { + const compile = forTag.compile(...args).split('\n'); + + compile.splice( + 3, + 0, + ' if (!Array.isArray(__l) && typeof __l.toArray === "function") { __l = __l.toArray(); }' + ); + + return compile.join('\n'); + }, + forTag.ends, + true +); function swigRenderer(data, locals) { return swig.render(data.text, { @@ -38,8 +48,9 @@ function swigRenderer(data, locals) { }); } -swigRenderer.compile = (data, locals) => swig.compile(data.text, { - filename: data.path -}); +swigRenderer.compile = (data, locals) => + swig.compile(data.text, { + filename: data.path + }); module.exports = swigRenderer; diff --git a/lib/plugins/tag/asset_img.js b/lib/plugins/tag/asset_img.js index 752d0deb05..a2dc5f24a3 100644 --- a/lib/plugins/tag/asset_img.js +++ b/lib/plugins/tag/asset_img.js @@ -17,7 +17,7 @@ module.exports = ctx => { // Find image URL for (let i = 0; i < len; i++) { - const asset = PostAsset.findOne({post: this._id, slug: args[i]}); + const asset = PostAsset.findOne({ post: this._id, slug: args[i] }); if (asset) { args[i] = url.resolve('/', asset.path); return img(ctx)(args); diff --git a/lib/plugins/tag/asset_link.js b/lib/plugins/tag/asset_link.js index 8cf335c30b..47760e7437 100644 --- a/lib/plugins/tag/asset_link.js +++ b/lib/plugins/tag/asset_link.js @@ -15,7 +15,7 @@ module.exports = ctx => { const slug = args.shift(); if (!slug) return; - const asset = PostAsset.findOne({post: this._id, slug}); + const asset = PostAsset.findOne({ post: this._id, slug }); if (!asset) return; const title = args.length ? args.join(' ') : asset.slug; diff --git a/lib/plugins/tag/asset_path.js b/lib/plugins/tag/asset_path.js index 81babf2297..0d233278ca 100644 --- a/lib/plugins/tag/asset_path.js +++ b/lib/plugins/tag/asset_path.js @@ -15,7 +15,7 @@ module.exports = ctx => { const slug = args.shift(); if (!slug) return; - const asset = PostAsset.findOne({post: this._id, slug}); + const asset = PostAsset.findOne({ post: this._id, slug }); if (!asset) return; return url.resolve(ctx.config.root, asset.path); diff --git a/lib/plugins/tag/blockquote.js b/lib/plugins/tag/blockquote.js index 847727da92..8a41de03da 100644 --- a/lib/plugins/tag/blockquote.js +++ b/lib/plugins/tag/blockquote.js @@ -49,21 +49,22 @@ const parseFooter = (args, ctx) => { }; /** -* Blockquote tag -* -* Syntax: -* {% blockquote [author[, source]] [link] [source_link_title] %} -* Quote string -* {% endblockquote %} -*/ + * Blockquote tag + * + * Syntax: + * {% blockquote [author[, source]] [link] [source_link_title] %} + * Quote string + * {% endblockquote %} + */ -module.exports = ctx => function blockquoteTag(args, content) { - const footer = parseFooter(args, ctx); +module.exports = ctx => + function blockquoteTag(args, content) { + const footer = parseFooter(args, ctx); - let result = '
'; - result += ctx.render.renderSync({text: content, engine: 'markdown'}); - if (footer) result += ``; - result += ''; + let result = ''; + result += ctx.render.renderSync({ text: content, engine: 'markdown' }); + if (footer) result += ``; + result += ''; - return result; -}; + return result; + }; diff --git a/lib/plugins/tag/code.js b/lib/plugins/tag/code.js index e7cfd8a614..c4b5690391 100644 --- a/lib/plugins/tag/code.js +++ b/lib/plugins/tag/code.js @@ -24,7 +24,6 @@ const rMark = /\s*mark:([0-9,-]+)/i; */ function getHighlightOptions(config, arg) { - let lang = ''; if (rLang.test(arg)) { arg = arg.replace(rLang, (match, _lang) => { @@ -56,7 +55,8 @@ function getHighlightOptions(config, arg) { if (/-/.test(cur)) { let a = Number(cur.substr(0, cur.indexOf('-'))); let b = Number(cur.substr(cur.indexOf('-') + 1)); - if (b < a) { // switch a & b + if (b < a) { + // switch a & b const temp = a; a = b; b = temp; @@ -80,10 +80,14 @@ function getHighlightOptions(config, arg) { let caption = ''; if (rCaptionUrlTitle.test(arg)) { const match = arg.match(rCaptionUrlTitle); - caption = `${match[1]}${match[4]}`; + caption = `${match[1]}${ + match[4] + }`; } else if (rCaptionUrl.test(arg)) { const match = arg.match(rCaptionUrl); - caption = `${match[1]}link`; + caption = `${match[1]}link`; } else if (rCaption.test(arg)) { const match = arg.match(rCaption); caption = `${match[1]}`; @@ -101,29 +105,29 @@ function getHighlightOptions(config, arg) { }; } -module.exports = ctx => function codeTag(args, content) { - let arg = args.join(' '); - const config = ctx.config.highlight || {}; - let enable = config.enable; +module.exports = ctx => + function codeTag(args, content) { + let arg = args.join(' '); + const config = ctx.config.highlight || {}; + let enable = config.enable; - if (rHighlight.test(arg)) { - arg = arg.replace(rHighlight, (match, _enable) => { - enable = _enable === 'true'; - return ''; - }); - } + if (rHighlight.test(arg)) { + arg = arg.replace(rHighlight, (match, _enable) => { + enable = _enable === 'true'; + return ''; + }); + } - if (!enable) { - content = escapeHTML(content); - return ``; - } + if (!enable) { + content = escapeHTML(content); + return `${content}
`; + } - content = stripIndent(content); + content = stripIndent(content); - content = highlight(content, getHighlightOptions(config, arg)); + content = highlight(content, getHighlightOptions(config, arg)); - content = content.replace(/{/g, '{') - .replace(/}/g, '}'); + content = content.replace(/{/g, '{').replace(/}/g, '}'); - return content; -}; + return content; + }; diff --git a/lib/plugins/tag/gist.js b/lib/plugins/tag/gist.js index f4a11fb2d1..b79cd3a1e2 100644 --- a/lib/plugins/tag/gist.js +++ b/lib/plugins/tag/gist.js @@ -1,11 +1,11 @@ 'use strict'; /** -* Gist tag -* -* Syntax: -* {% gist gist_id [filename] %} -*/ + * Gist tag + * + * Syntax: + * {% gist gist_id [filename] %} + */ function gistTag(args, content) { const id = args.shift(); diff --git a/lib/plugins/tag/iframe.js b/lib/plugins/tag/iframe.js index 03fed9a4a6..e05f841c83 100644 --- a/lib/plugins/tag/iframe.js +++ b/lib/plugins/tag/iframe.js @@ -1,11 +1,11 @@ 'use strict'; /** -* Iframe tag -* -* Syntax: -* {% iframe url [width] [height] %} -*/ + * Iframe tag + * + * Syntax: + * {% iframe url [width] [height] %} + */ function iframeTag(args, content) { const url = args[0]; diff --git a/lib/plugins/tag/img.js b/lib/plugins/tag/img.js index 99aeccf7b9..e68caf6791 100644 --- a/lib/plugins/tag/img.js +++ b/lib/plugins/tag/img.js @@ -7,11 +7,11 @@ const rUrl = /((([A-Za-z]{3,9}:(?:\/\/)?)(?:[-;:&=+$,\w]+@)?[A-Za-z0-9.-]+|(?:ww const rMeta = /["']?([^"']+)?["']?\s*["']?([^"']+)?["']?/; /** -* Image tag -* -* Syntax: -* {% img [class names] /path/to/image [width] [height] [title text [alt text]] %} -*/ + * Image tag + * + * Syntax: + * {% img [class names] /path/to/image [width] [height] [title text [alt text]] %} + */ module.exports = ctx => { const { config } = ctx; @@ -33,7 +33,7 @@ module.exports = ctx => { return function imgTag(args, content) { const classes = []; - let src; + let src, width, height, title, alt; // Find image URL and class name while (args.length > 0) { @@ -46,8 +46,6 @@ module.exports = ctx => { } } - let width, height, title, alt; - // Find image width and height if (args && args.length) { if (!/\D+/.test(args[0])) { diff --git a/lib/plugins/tag/include_code.js b/lib/plugins/tag/include_code.js index f249c14797..f776e1aaa1 100644 --- a/lib/plugins/tag/include_code.js +++ b/lib/plugins/tag/include_code.js @@ -11,74 +11,81 @@ const rFrom = /\s*from:(\d+)/i; const rTo = /\s*to:(\d+)/i; /** -* Include code tag -* -* Syntax: -* {% include_code [title] [lang:language] path/to/file %} -*/ - -module.exports = ctx => function includeCodeTag(args) { - const config = ctx.config.highlight || {}; - let codeDir = ctx.config.code_dir; - let arg = args.join(' '); - - // Add trailing slash to codeDir - if (codeDir[codeDir.length - 1] !== '/') codeDir += '/'; - - let lang = ''; - arg = arg.replace(rLang, (match, _lang) => { - lang = _lang; - return ''; - }); - let from = 0; - arg = arg.replace(rFrom, (match, _from) => { - from = _from - 1; - return ''; - }); - let to = Number.MAX_VALUE; - arg = arg.replace(rTo, (match, _to) => { - to = _to; - return ''; - }); - - const match = arg.match(rCaptionTitleFile); - - // Exit if path is not defined - if (!match) return; - - const path = match[2]; - - // If the title is not defined, use file name instead - const title = match[1] || basename(path); - - // If the language is not defined, use file extension instead - lang = lang || extname(path).substring(1); - - const src = join(ctx.source_dir, codeDir, path); - - const caption = `${title}view raw`; - - const options = { - lang, - caption, - gutter: config.line_number, - hljs: config.hljs, - tab: config.tab_replace + * Include code tag + * + * Syntax: + * {% include_code [title] [lang:language] path/to/file %} + */ + +module.exports = ctx => + function includeCodeTag(args) { + const config = ctx.config.highlight || {}; + let codeDir = ctx.config.code_dir; + let arg = args.join(' '); + + // Add trailing slash to codeDir + if (codeDir[codeDir.length - 1] !== '/') codeDir += '/'; + + let lang = ''; + arg = arg.replace(rLang, (match, _lang) => { + lang = _lang; + return ''; + }); + let from = 0; + arg = arg.replace(rFrom, (match, _from) => { + from = _from - 1; + return ''; + }); + let to = Number.MAX_VALUE; + arg = arg.replace(rTo, (match, _to) => { + to = _to; + return ''; + }); + + const match = arg.match(rCaptionTitleFile); + + // Exit if path is not defined + if (!match) return; + + const path = match[2]; + + // If the title is not defined, use file name instead + const title = match[1] || basename(path); + + // If the language is not defined, use file extension instead + lang = lang || extname(path).substring(1); + + const src = join(ctx.source_dir, codeDir, path); + + const caption = `${title}view raw`; + + const options = { + lang, + caption, + gutter: config.line_number, + hljs: config.hljs, + tab: config.tab_replace + }; + + return fs + .exists(src) + .then(exist => { + if (exist) return fs.readFile(src); + }) + .then(code => { + if (!code) return; + + code = stripIndent(code); + const lines = code.split('\n'); + code = lines + .slice(from, to) + .join('\n') + .trim(); + + if (!config.enable) { + return `${content}
`; + } + + return highlight(code, options); + }); }; - - return fs.exists(src).then(exist => { - if (exist) return fs.readFile(src); - }).then(code => { - if (!code) return; - - code = stripIndent(code); - const lines = code.split('\n'); - code = lines.slice(from, to).join('\n').trim(); - - if (!config.enable) { - return `${code}
`; - } - - return highlight(code, options); - }); -}; diff --git a/lib/plugins/tag/index.js b/lib/plugins/tag/index.js index 57e73aca15..3c8f81686f 100644 --- a/lib/plugins/tag/index.js +++ b/lib/plugins/tag/index.js @@ -24,8 +24,8 @@ module.exports = ctx => { const includeCode = require('./include_code')(ctx); - tag.register('include_code', includeCode, {async: true}); - tag.register('include-code', includeCode, {async: true}); + tag.register('include_code', includeCode, { async: true }); + tag.register('include-code', includeCode, { async: true }); tag.register('jsfiddle', require('./jsfiddle')); diff --git a/lib/plugins/tag/jsfiddle.js b/lib/plugins/tag/jsfiddle.js index 57fde79c93..e3afe4557b 100644 --- a/lib/plugins/tag/jsfiddle.js +++ b/lib/plugins/tag/jsfiddle.js @@ -1,15 +1,16 @@ 'use strict'; /** -* jsFiddle tag -* -* Syntax: -* {% jsfiddle shorttag [tabs] [skin] [height] [width] %} -*/ + * jsFiddle tag + * + * Syntax: + * {% jsfiddle shorttag [tabs] [skin] [height] [width] %} + */ function jsfiddleTag(args, content) { const id = args[0]; - const tabs = args[1] && args[1] !== 'default' ? args[1] : 'js,resources,html,css,result'; + const tabs = + args[1] && args[1] !== 'default' ? args[1] : 'js,resources,html,css,result'; const skin = args[2] && args[2] !== 'default' ? args[2] : 'light'; const width = args[3] && args[3] !== 'default' ? args[3] : '100%'; const height = args[4] && args[4] !== 'default' ? args[4] : '300'; diff --git a/lib/plugins/tag/link.js b/lib/plugins/tag/link.js index 744f874f88..ed3c30e62e 100644 --- a/lib/plugins/tag/link.js +++ b/lib/plugins/tag/link.js @@ -5,11 +5,11 @@ const { htmlTag } = require('hexo-util'); const rUrl = /((([A-Za-z]{3,9}:(?:\/\/)?)(?:[-;:&=+$,\w]+@)?[A-Za-z0-9.-]+|(?:www.|[-;:&=+$,\w]+@)[A-Za-z0-9.-]+)((?:\/[+~%/.\w-_]*)?\??(?:[-+=&;%@.\w_]*)#?(?:[.!/\\w]*))?)/; /** -* Link tag -* -* Syntax: -* {% link text url [external] [title] %} -*/ + * Link tag + * + * Syntax: + * {% link text url [external] [title] %} + */ function linkTag(args, content) { let url = ''; diff --git a/lib/plugins/tag/post_link.js b/lib/plugins/tag/post_link.js index 87cf248ceb..bc752d74df 100644 --- a/lib/plugins/tag/post_link.js +++ b/lib/plugins/tag/post_link.js @@ -13,7 +13,7 @@ module.exports = ctx => { const slug = args.shift(); if (!slug) return; - const post = Post.findOne({slug}); + const post = Post.findOne({ slug }); if (!post) return; const title = args.length ? args.join(' ') : post.title; diff --git a/lib/plugins/tag/post_path.js b/lib/plugins/tag/post_path.js index defe0b265f..4de33683c1 100644 --- a/lib/plugins/tag/post_path.js +++ b/lib/plugins/tag/post_path.js @@ -13,7 +13,7 @@ module.exports = ctx => { const slug = args.shift(); if (!slug) return; - const post = Post.findOne({slug}); + const post = Post.findOne({ slug }); if (!post) return; return ctx.config.root + post.path; diff --git a/lib/plugins/tag/pullquote.js b/lib/plugins/tag/pullquote.js index 8a2f945d4a..df7fdbd3d9 100644 --- a/lib/plugins/tag/pullquote.js +++ b/lib/plugins/tag/pullquote.js @@ -1,17 +1,18 @@ 'use strict'; /** -* Pullquote tag -* -* Syntax: -* {% pullquote [class] %} -* Quote string -* {% endpullquote %} -*/ -module.exports = ctx => function pullquoteTag(args, content) { - args.unshift('pullquote'); + * Pullquote tag + * + * Syntax: + * {% pullquote [class] %} + * Quote string + * {% endpullquote %} + */ +module.exports = ctx => + function pullquoteTag(args, content) { + args.unshift('pullquote'); - const result = ctx.render.renderSync({text: content, engine: 'markdown'}); + const result = ctx.render.renderSync({ text: content, engine: 'markdown' }); - return `${code}
${result}`; -}; + return `${result}`; + }; diff --git a/lib/plugins/tag/vimeo.js b/lib/plugins/tag/vimeo.js index 11f6058e57..c395e36360 100644 --- a/lib/plugins/tag/vimeo.js +++ b/lib/plugins/tag/vimeo.js @@ -1,11 +1,11 @@ 'use strict'; /** -* Vimeo tag -* -* Syntax: -* {% vimeo video_id %} -*/ + * Vimeo tag + * + * Syntax: + * {% vimeo video_id %} + */ function vimeoTag(args, content) { const id = args[0]; diff --git a/lib/plugins/tag/youtube.js b/lib/plugins/tag/youtube.js index 19ceed8554..e83c2d3380 100644 --- a/lib/plugins/tag/youtube.js +++ b/lib/plugins/tag/youtube.js @@ -1,11 +1,11 @@ 'use strict'; /** -* Youtube tag -* -* Syntax: -* {% youtube video_id %} -*/ + * Youtube tag + * + * Syntax: + * {% youtube video_id %} + */ function youtubeTag(args, content) { const id = args[0]; diff --git a/lib/theme/index.js b/lib/theme/index.js index 79a1861fca..cede1939c0 100644 --- a/lib/theme/index.js +++ b/lib/theme/index.js @@ -30,12 +30,15 @@ function Theme(ctx) { languages.push('default'); this.i18n = new I18n({ - languages: _(languages).compact().uniq().value() + languages: _(languages) + .compact() + .uniq() + .value() }); - const _View = this.View = function(path, data) { + const _View = (this.View = function(path, data) { Reflect.apply(View, this, [path, data]); - }; + }); util.inherits(_View, View); @@ -66,7 +69,7 @@ Theme.prototype.getView = function(path) { Theme.prototype.setView = function(path, data) { const ext = extname(path); const name = path.substring(0, path.length - ext.length); - const views = this.views[name] = this.views[name] || {}; + const views = (this.views[name] = this.views[name] || {}); views[ext] = new this.View(path, data); }; diff --git a/lib/theme/processors/config.js b/lib/theme/processors/config.js index 53ce70ff09..83466fb119 100644 --- a/lib/theme/processors/config.js +++ b/lib/theme/processors/config.js @@ -8,13 +8,16 @@ exports.process = function(file) { return; } - return file.render().then(result => { - file.box.config = result; - this.log.debug('Theme config loaded.'); - }).catch(err => { - this.log.error('Theme config load failed.'); - throw err; - }); + return file + .render() + .then(result => { + file.box.config = result; + this.log.debug('Theme config loaded.'); + }) + .catch(err => { + this.log.error('Theme config load failed.'); + throw err; + }); }; exports.pattern = new Pattern(/^_config\.\w+$/); diff --git a/lib/theme/processors/source.js b/lib/theme/processors/source.js index 826b6a109e..b25a712835 100644 --- a/lib/theme/processors/source.js +++ b/lib/theme/processors/source.js @@ -28,7 +28,12 @@ exports.pattern = new Pattern(path => { if (!path.startsWith('source/')) return false; path = path.substring(7); - if (common.isHiddenFile(path) || common.isTmpFile(path) || path.includes('node_modules')) return false; - - return {path}; + if ( + common.isHiddenFile(path) || + common.isTmpFile(path) || + path.includes('node_modules') + ) + return false; + + return { path }; }); diff --git a/lib/theme/view.js b/lib/theme/view.js index 9eb720b695..9f4190548f 100644 --- a/lib/theme/view.js +++ b/lib/theme/view.js @@ -26,19 +26,21 @@ View.prototype.render = function(options, callback) { const { layout = options.layout } = data; const locals = this._buildLocals(options); - return this._compiled(this._bindHelpers(locals)).then(result => { - if (result == null || !layout) return result; + return this._compiled(this._bindHelpers(locals)) + .then(result => { + if (result == null || !layout) return result; - const layoutView = this._resolveLayout(layout); - if (!layoutView) return result; + const layoutView = this._resolveLayout(layout); + if (!layoutView) return result; - const layoutLocals = Object.assign({}, locals, { - body: result, - layout: false - }); + const layoutLocals = Object.assign({}, locals, { + body: result, + layout: false + }); - return layoutView.render(layoutLocals, callback); - }).asCallback(callback); + return layoutView.render(layoutLocals, callback); + }) + .asCallback(callback); }; View.prototype.renderSync = function(options = {}) { @@ -120,8 +122,10 @@ View.prototype._precompile = function() { return ctx.execFilterSync(...buildFilterArguments(result)); }; - this._compiled = locals => Promise.resolve(compiled(locals)) - .then(result => ctx.execFilter(...buildFilterArguments(result))); + this._compiled = locals => + Promise.resolve(compiled(locals)).then(result => + ctx.execFilter(...buildFilterArguments(result)) + ); } else { this._compiledSync = locals => render.renderSync(data, locals); diff --git a/test/fixtures/post_render.js b/test/fixtures/post_render.js index 829c64b48c..2f75ea660c 100644 --- a/test/fixtures/post_render.js +++ b/test/fixtures/post_render.js @@ -2,10 +2,7 @@ const util = require('hexo-util'); -const code = [ - 'if tired && night:', - ' sleep()' -].join('\n'); +const code = ['if tired && night:', ' sleep()'].join('\n'); const content = [ '# Title', @@ -28,7 +25,7 @@ exports.content = content; exports.expected = [ 'Title
', - util.highlight(code, {lang: 'python'}), + util.highlight(code, { lang: 'python' }), '\n\nsome content
\n', 'Another title
', '', @@ -40,7 +37,7 @@ exports.expected = [ exports.expected_disable_nunjucks = [ 'Title
', - util.highlight(code, {lang: 'python'}), + util.highlight(code, { lang: 'python' }), '\n\nsome content
\n', 'Another title
', '{% blockquote %}
' - + ''; + const content = ''; hexo.config.meta_generator = true; const result = metaGenerator(content); @@ -35,34 +38,32 @@ describe('Meta Generator', () => { }); it('ignore empty head tag', () => { - const content = '' - + '' - + ''; + const content = ''; hexo.config.meta_generator = true; const result = metaGenerator(content); const $ = cheerio.load(result); $('meta[name="generator"]').length.should.eql(1); - const expected = '' - + '' - + ''; + const expected = + ''; result.should.eql(expected); }); it('apply to first non-empty head tag only', () => { - const content = '' - + '' - + ''; + const content = ''; hexo.config.meta_generator = true; const result = metaGenerator(content); const $ = cheerio.load(result); $('meta[name="generator"]').length.should.eql(1); - const expected = '' - + '' - + ''; + const expected = + ''; result.should.eql(expected); }); }); diff --git a/test/scripts/filters/new_post_path.js b/test/scripts/filters/new_post_path.js index cfe99e265f..be240047dd 100644 --- a/test/scripts/filters/new_post_path.js +++ b/test/scripts/filters/new_post_path.js @@ -11,7 +11,9 @@ const NEW_POST_NAME = ':title.md'; describe('new_post_path', () => { const Hexo = require('../../../lib/hexo'); const hexo = new Hexo(pathFn.join(__dirname, 'new_post_path_test')); - const newPostPath = require('../../../lib/plugins/filter/new_post_path').bind(hexo); + const newPostPath = require('../../../lib/plugins/filter/new_post_path').bind( + hexo + ); const sourceDir = hexo.source_dir; const draftDir = pathFn.join(sourceDir, '_drafts'); const postDir = pathFn.join(sourceDir, '_posts'); @@ -24,39 +26,44 @@ describe('new_post_path', () => { after(() => fs.rmdir(hexo.base_dir)); - it('page layout + path', () => newPostPath({ - path: 'foo', - layout: 'page' - }).then(target => { - target.should.eql(pathFn.join(sourceDir, 'foo.md')); - })); - - it('draft layout + path', () => newPostPath({ - path: 'foo', - layout: 'draft' - }).then(target => { - target.should.eql(pathFn.join(draftDir, 'foo.md')); - })); - - it('default layout + path', () => newPostPath({ - path: 'foo' - }).then(target => { - target.should.eql(pathFn.join(postDir, 'foo.md')); - })); - - it('page layout + slug', () => newPostPath({ - slug: 'foo', - layout: 'page' - }).then(target => { - target.should.eql(pathFn.join(sourceDir, 'foo', 'index.md')); - })); - - it('draft layout + slug', () => newPostPath({ - slug: 'foo', - layout: 'draft' - }).then(target => { - target.should.eql(pathFn.join(draftDir, 'foo.md')); - })); + it('page layout + path', () => + newPostPath({ + path: 'foo', + layout: 'page' + }).then(target => { + target.should.eql(pathFn.join(sourceDir, 'foo.md')); + })); + + it('draft layout + path', () => + newPostPath({ + path: 'foo', + layout: 'draft' + }).then(target => { + target.should.eql(pathFn.join(draftDir, 'foo.md')); + })); + + it('default layout + path', () => + newPostPath({ + path: 'foo' + }).then(target => { + target.should.eql(pathFn.join(postDir, 'foo.md')); + })); + + it('page layout + slug', () => + newPostPath({ + slug: 'foo', + layout: 'page' + }).then(target => { + target.should.eql(pathFn.join(sourceDir, 'foo', 'index.md')); + })); + + it('draft layout + slug', () => + newPostPath({ + slug: 'foo', + layout: 'draft' + }).then(target => { + target.should.eql(pathFn.join(draftDir, 'foo.md')); + })); it('default layout + slug', () => { const now = moment(); @@ -65,7 +72,9 @@ describe('new_post_path', () => { return newPostPath({ slug: 'foo' }).then(target => { - target.should.eql(pathFn.join(postDir, now.format('YYYY-MM-DD') + '-foo.md')); + target.should.eql( + pathFn.join(postDir, now.format('YYYY-MM-DD') + '-foo.md') + ); hexo.config.new_post_name = NEW_POST_NAME; }); }); @@ -78,7 +87,9 @@ describe('new_post_path', () => { slug: 'foo', date: date.toDate() }).then(target => { - target.should.eql(pathFn.join(postDir, date.format('YYYY-M-D') + '-foo.md')); + target.should.eql( + pathFn.join(postDir, date.format('YYYY-M-D') + '-foo.md') + ); hexo.config.new_post_name = NEW_POST_NAME; }); }); @@ -107,49 +118,63 @@ describe('new_post_path', () => { }); }); - it('don\'t append extension name if existed', () => newPostPath({ - path: 'foo.markdown' - }).then(target => { - target.should.eql(pathFn.join(postDir, 'foo.markdown')); - })); + it("don't append extension name if existed", () => + newPostPath({ + path: 'foo.markdown' + }).then(target => { + target.should.eql(pathFn.join(postDir, 'foo.markdown')); + })); it('replace existing files', () => { const filename = 'test.md'; const path = pathFn.join(postDir, filename); - return fs.writeFile(path, '').then(() => newPostPath({ - path: filename - }, true)).then(target => { - target.should.eql(path); - return fs.unlink(path); - }); + return fs + .writeFile(path, '') + .then(() => + newPostPath( + { + path: filename + }, + true + ) + ) + .then(target => { + target.should.eql(path); + return fs.unlink(path); + }); }); it('rename if target existed', () => { - const filename = [ - 'test.md', - 'test-1.md', - 'test-2.md', - 'test-foo.md' - ]; + const filename = ['test.md', 'test-1.md', 'test-2.md', 'test-foo.md']; const path = filename.map(item => pathFn.join(postDir, item)); - return Promise.map(path, item => fs.writeFile(item, '')).then(() => newPostPath({ - path: filename[0] - })).then(target => { - target.should.eql(pathFn.join(postDir, 'test-3.md')); - return path; - }).map(item => fs.unlink(item)); + return Promise.map(path, item => fs.writeFile(item, '')) + .then(() => + newPostPath({ + path: filename[0] + }) + ) + .then(target => { + target.should.eql(pathFn.join(postDir, 'test-3.md')); + return path; + }) + .map(item => fs.unlink(item)); }); it('data is required', () => { const errorCallback = sinon.spy(err => { - err.should.have.property('message', 'Either data.path or data.slug is required!'); + err.should.have.property( + 'message', + 'Either data.path or data.slug is required!' + ); }); - return newPostPath().catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + return newPostPath() + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); }); diff --git a/test/scripts/filters/post_permalink.js b/test/scripts/filters/post_permalink.js index 4b5ba16f7f..23c17623f6 100644 --- a/test/scripts/filters/post_permalink.js +++ b/test/scripts/filters/post_permalink.js @@ -7,7 +7,9 @@ const PERMALINK = ':year/:month/:day/:title/'; describe('post_permalink', () => { const Hexo = require('../../../lib/hexo'); const hexo = new Hexo(); - const postPermalink = require('../../../lib/plugins/filter/post_permalink').bind(hexo); + const postPermalink = require('../../../lib/plugins/filter/post_permalink').bind( + hexo + ); const Post = hexo.model('Post'); let post; @@ -16,16 +18,22 @@ describe('post_permalink', () => { before(() => { let id; - return hexo.init().then(() => Post.insert({ - source: 'foo.md', - slug: 'foo', - date: moment('2014-01-02') - })).then(post => { - id = post._id; - return post.setCategories(['foo', 'bar']); - }).then(() => { - post = Post.findById(id); - }); + return hexo + .init() + .then(() => + Post.insert({ + source: 'foo.md', + slug: 'foo', + date: moment('2014-01-02') + }) + ) + .then(post => { + id = post._id; + return post.setCategories(['foo', 'bar']); + }) + .then(() => { + post = Post.findById(id); + }); }); it('default', () => { diff --git a/test/scripts/filters/render_post.js b/test/scripts/filters/render_post.js index 815bfa87a3..be6eb2d31e 100644 --- a/test/scripts/filters/render_post.js +++ b/test/scripts/filters/render_post.js @@ -7,9 +7,15 @@ describe('Render post', () => { const hexo = new Hexo(); const Post = hexo.model('Post'); const Page = hexo.model('Page'); - const renderPost = require('../../../lib/plugins/filter/before_generate/render_post').bind(hexo); + const renderPost = require('../../../lib/plugins/filter/before_generate/render_post').bind( + hexo + ); - before(() => hexo.init().then(() => hexo.loadPlugin(require.resolve('hexo-renderer-marked')))); + before(() => + hexo + .init() + .then(() => hexo.loadPlugin(require.resolve('hexo-renderer-marked'))) + ); it('post', () => { let id; @@ -18,15 +24,17 @@ describe('Render post', () => { source: 'foo.md', slug: 'foo', _content: fixture.content - }).then(post => { - id = post._id; - return renderPost(); - }).then(() => { - const post = Post.findById(id); - post.content.trim().should.eql(fixture.expected); + }) + .then(post => { + id = post._id; + return renderPost(); + }) + .then(() => { + const post = Post.findById(id); + post.content.trim().should.eql(fixture.expected); - return post.remove(); - }); + return post.remove(); + }); }); it('page', () => { @@ -36,15 +44,17 @@ describe('Render post', () => { source: 'foo.md', path: 'foo.html', _content: fixture.content - }).then(page => { - id = page._id; - return renderPost(); - }).then(() => { - const page = Page.findById(id); - page.content.trim().should.eql(fixture.expected); + }) + .then(page => { + id = page._id; + return renderPost(); + }) + .then(() => { + const page = Page.findById(id); + page.content.trim().should.eql(fixture.expected); - return page.remove(); - }); + return page.remove(); + }); }); it('use data variables', () => { @@ -54,15 +64,16 @@ describe('Render post', () => { source: 'foo.md', path: 'foo.html', _content: '
', diff --git a/test/scripts/box/box.js b/test/scripts/box/box.js index 025c05bce3..4956d33738 100644 --- a/test/scripts/box/box.js +++ b/test/scripts/box/box.js @@ -13,7 +13,7 @@ describe('Box', () => { const Box = require('../../../lib/box'); function newBox(path, config) { - const hexo = new Hexo(baseDir, {silent: true}); + const hexo = new Hexo(baseDir, { silent: true }); hexo.config = Object.assign(hexo.config, config); const base = path ? pathFn.join(baseDir, path) : baseDir; return new Box(hexo, base); @@ -89,20 +89,23 @@ describe('Box', () => { return Promise.all([ fs.writeFile(pathFn.join(box.base, 'a.txt'), 'a'), fs.writeFile(pathFn.join(box.base, 'b', 'c.js'), 'c') - ]).then(() => box.process()).then(() => { - const keys = Object.keys(data); - let key, item; - - for (let i = 0, len = keys.length; i < len; i++) { - key = keys[i]; - item = data[key]; - - item.path.should.eql(key); - item.source.should.eql(pathFn.join(box.base, key)); - item.type.should.eql('create'); - item.params.should.eql({}); - } - }).finally(() => fs.rmdir(box.base)); + ]) + .then(() => box.process()) + .then(() => { + const keys = Object.keys(data); + let key, item; + + for (let i = 0, len = keys.length; i < len; i++) { + key = keys[i]; + item = data[key]; + + item.path.should.eql(key); + item.source.should.eql(pathFn.join(box.base, key)); + item.type.should.eql('create'); + item.params.should.eql({}); + } + }) + .finally(() => fs.rmdir(box.base)); }); it('process() - do nothing if target does not exist', () => { @@ -119,11 +122,15 @@ describe('Box', () => { const processor = sinon.spy(); box.addProcessor(processor); - return fs.writeFile(path, 'a').then(() => box.process()).then(() => { - const file = processor.args[0][0]; - file.type.should.eql('create'); - file.path.should.eql(name); - }).finally(() => fs.rmdir(box.base)); + return fs + .writeFile(path, 'a') + .then(() => box.process()) + .then(() => { + const file = processor.args[0][0]; + file.type.should.eql('create'); + file.path.should.eql(name); + }) + .finally(() => fs.rmdir(box.base)); }); it('process() - mtime changed', () => { @@ -141,11 +148,14 @@ describe('Box', () => { _id: cacheId, modified: 0 }) - ]).then(() => box.process()).then(() => { - const file = processor.args[0][0]; - file.type.should.eql('update'); - file.path.should.eql(name); - }).finally(() => fs.rmdir(box.base)); + ]) + .then(() => box.process()) + .then(() => { + const file = processor.args[0][0]; + file.type.should.eql('update'); + file.path.should.eql(name); + }) + .finally(() => fs.rmdir(box.base)); }); it('process() - hash changed', () => { @@ -157,14 +167,22 @@ describe('Box', () => { const processor = sinon.spy(); box.addProcessor(processor); - return fs.writeFile(path, 'a').then(() => fs.stat(path)).then(stats => box.Cache.insert({ - _id: cacheId, - modified: stats.mtime - })).then(() => box.process()).then(() => { - const file = processor.args[0][0]; - file.type.should.eql('update'); - file.path.should.eql(name); - }).finally(() => fs.rmdir(box.base)); + return fs + .writeFile(path, 'a') + .then(() => fs.stat(path)) + .then(stats => + box.Cache.insert({ + _id: cacheId, + modified: stats.mtime + }) + ) + .then(() => box.process()) + .then(() => { + const file = processor.args[0][0]; + file.type.should.eql('update'); + file.path.should.eql(name); + }) + .finally(() => fs.rmdir(box.base)); }); it('process() - skip', () => { @@ -176,15 +194,23 @@ describe('Box', () => { const processor = sinon.spy(); box.addProcessor(processor); - return fs.writeFile(path, 'a').then(() => fs.stat(path)).then(stats => box.Cache.insert({ - _id: cacheId, - modified: stats.mtime, - hash: util.hash('a').toString('hex') - })).then(() => box.process()).then(() => { - const file = processor.args[0][0]; - file.type.should.eql('skip'); - file.path.should.eql(name); - }).finally(() => fs.rmdir(box.base)); + return fs + .writeFile(path, 'a') + .then(() => fs.stat(path)) + .then(stats => + box.Cache.insert({ + _id: cacheId, + modified: stats.mtime, + hash: util.hash('a').toString('hex') + }) + ) + .then(() => box.process()) + .then(() => { + const file = processor.args[0][0]; + file.type.should.eql('skip'); + file.path.should.eql(name); + }) + .finally(() => fs.rmdir(box.base)); }); it('process() - delete', () => { @@ -202,9 +228,12 @@ describe('Box', () => { box.Cache.insert({ _id: cacheId }) - ]).then(() => box.process()).then(() => { - processor.calledOnce.should.be.true; - }).finally(() => fs.rmdir(box.base)); + ]) + .then(() => box.process()) + .then(() => { + processor.calledOnce.should.be.true; + }) + .finally(() => fs.rmdir(box.base)); }); it('process() - params', () => { @@ -217,13 +246,17 @@ describe('Box', () => { box.addProcessor('posts/:id', processor); - return fs.writeFile(path, 'a').then(() => box.process()).then(() => { - processor.calledOnce.should.be.true; - }).finally(() => fs.rmdir(box.base)); + return fs + .writeFile(path, 'a') + .then(() => box.process()) + .then(() => { + processor.calledOnce.should.be.true; + }) + .finally(() => fs.rmdir(box.base)); }); it('process() - skip files if they match a glob epression in ignore', () => { - const box = newBox('test', {ignore: '**/ignore_me'}); + const box = newBox('test', { ignore: '**/ignore_me' }); const data = {}; box.addProcessor(file => { @@ -233,16 +266,21 @@ describe('Box', () => { return Promise.all([ fs.writeFile(pathFn.join(box.base, 'foo.txt'), 'foo'), fs.writeFile(pathFn.join(box.base, 'ignore_me', 'bar.txt'), 'ignore_me') - ]).then(() => box.process()).then(() => { - const keys = Object.keys(data); + ]) + .then(() => box.process()) + .then(() => { + const keys = Object.keys(data); - keys.length.should.eql(1); - keys[0].should.eql('foo.txt'); - }).finally(() => fs.rmdir(box.base)); + keys.length.should.eql(1); + keys[0].should.eql('foo.txt'); + }) + .finally(() => fs.rmdir(box.base)); }); it('process() - skip files if they match any of the glob expressions in ignore', () => { - const box = newBox('test', {ignore: ['**/ignore_me', '**/ignore_me_too']}); + const box = newBox('test', { + ignore: ['**/ignore_me', '**/ignore_me_too'] + }); const data = {}; box.addProcessor(file => { @@ -252,12 +290,15 @@ describe('Box', () => { return Promise.all([ fs.writeFile(pathFn.join(box.base, 'foo.txt'), 'foo'), fs.writeFile(pathFn.join(box.base, 'ignore_me', 'bar.txt'), 'ignore_me') - ]).then(() => box.process()).then(() => { - const keys = Object.keys(data); + ]) + .then(() => box.process()) + .then(() => { + const keys = Object.keys(data); - keys.length.should.eql(1); - keys[0].should.eql('foo.txt'); - }).finally(() => fs.rmdir(box.base)); + keys.length.should.eql(1); + keys[0].should.eql('foo.txt'); + }) + .finally(() => fs.rmdir(box.base)); }); it('watch() - create', () => { @@ -271,14 +312,16 @@ describe('Box', () => { return Promise.all([fs.writeFile(src, 'a')]) .then(() => box.watch()) .then(() => box.isWatching().should.be.true) - .delay(500).then(() => { + .delay(500) + .then(() => { const file = processor.args[0][0]; file.source.should.eql(src); file.path.should.eql(path); file.type.should.eql('create'); file.params.should.eql({}); - }).finally(() => { + }) + .finally(() => { box.unwatch(); return fs.rmdir(box.base); }); @@ -294,20 +337,22 @@ describe('Box', () => { box.addProcessor(processor); - return Promise.all([ - fs.writeFile(src, 'a'), - Cache.insert({_id: cacheId}) - ]).then(() => box.watch()).then(() => fs.appendFile(src, 'b')).delay(500).then(() => { - const file = processor.lastCall.args[0]; - - file.source.should.eql(src); - file.path.should.eql(path); - file.type.should.eql('update'); - file.params.should.eql({}); - }).finally(() => { - box.unwatch(); - return fs.rmdir(box.base); - }); + return Promise.all([fs.writeFile(src, 'a'), Cache.insert({ _id: cacheId })]) + .then(() => box.watch()) + .then(() => fs.appendFile(src, 'b')) + .delay(500) + .then(() => { + const file = processor.lastCall.args[0]; + + file.source.should.eql(src); + file.path.should.eql(path); + file.type.should.eql('update'); + file.params.should.eql({}); + }) + .finally(() => { + box.unwatch(); + return fs.rmdir(box.base); + }); }); it('watch() - delete', () => { @@ -320,20 +365,22 @@ describe('Box', () => { box.addProcessor(processor); - return Promise.all([ - fs.writeFile(src, 'a'), - Cache.insert({_id: cacheId}) - ]).then(() => box.watch()).then(() => fs.unlink(src)).delay(500).then(() => { - const file = processor.lastCall.args[0]; + return Promise.all([fs.writeFile(src, 'a'), Cache.insert({ _id: cacheId })]) + .then(() => box.watch()) + .then(() => fs.unlink(src)) + .delay(500) + .then(() => { + const file = processor.lastCall.args[0]; - file.source.should.eql(src); - file.path.should.eql(path); - file.type.should.eql('delete'); - file.params.should.eql({}); - }).finally(() => { - box.unwatch(); - return fs.rmdir(box.base); - }); + file.source.should.eql(src); + file.path.should.eql(path); + file.type.should.eql('delete'); + file.params.should.eql({}); + }) + .finally(() => { + box.unwatch(); + return fs.rmdir(box.base); + }); }); it('watch() - rename file', () => { @@ -348,31 +395,36 @@ describe('Box', () => { box.addProcessor(processor); - return Promise.all([ - fs.writeFile(src, 'a'), - Cache.insert({_id: cacheId}) - ]).then(() => box.watch()).then(() => fs.rename(src, newSrc)).delay(500).then(() => { - const lastTwoCalls = processor.args.slice(processor.args.length - 2, processor.args.length); - - lastTwoCalls.forEach(args => { - const file = args[0]; - - switch (file.type) { - case 'create': - file.source.should.eql(newSrc); - file.path.should.eql(newPath); - break; - - case 'delete': - file.source.should.eql(src); - file.path.should.eql(path); - break; - } + return Promise.all([fs.writeFile(src, 'a'), Cache.insert({ _id: cacheId })]) + .then(() => box.watch()) + .then(() => fs.rename(src, newSrc)) + .delay(500) + .then(() => { + const lastTwoCalls = processor.args.slice( + processor.args.length - 2, + processor.args.length + ); + + lastTwoCalls.forEach(args => { + const file = args[0]; + + switch (file.type) { + case 'create': + file.source.should.eql(newSrc); + file.path.should.eql(newPath); + break; + + case 'delete': + file.source.should.eql(src); + file.path.should.eql(path); + break; + } + }); + }) + .finally(() => { + box.unwatch(); + return fs.rmdir(box.base); }); - }).finally(() => { - box.unwatch(); - return fs.rmdir(box.base); - }); }); it('watch() - rename folder', () => { @@ -387,47 +439,60 @@ describe('Box', () => { box.addProcessor(processor); - return Promise.all([ - fs.writeFile(src, 'a'), - Cache.insert({_id: cacheId}) - ]).then(() => box.watch()).then(() => fs.rename(pathFn.join(box.base, 'a'), pathFn.join(box.base, 'b'))).delay(500).then(() => { - const lastTwoCalls = processor.args.slice(processor.args.length - 2, processor.args.length); - - lastTwoCalls.forEach(args => { - const file = args[0]; - - switch (file.type) { - case 'create': - file.source.should.eql(newSrc); - file.path.should.eql(newPath); - break; - - case 'delete': - file.source.should.eql(src); - file.path.should.eql(path); - break; - } + return Promise.all([fs.writeFile(src, 'a'), Cache.insert({ _id: cacheId })]) + .then(() => box.watch()) + .then(() => + fs.rename(pathFn.join(box.base, 'a'), pathFn.join(box.base, 'b')) + ) + .delay(500) + .then(() => { + const lastTwoCalls = processor.args.slice( + processor.args.length - 2, + processor.args.length + ); + + lastTwoCalls.forEach(args => { + const file = args[0]; + + switch (file.type) { + case 'create': + file.source.should.eql(newSrc); + file.path.should.eql(newPath); + break; + + case 'delete': + file.source.should.eql(src); + file.path.should.eql(path); + break; + } + }); + }) + .finally(() => { + box.unwatch(); + return fs.rmdir(box.base); }); - }).finally(() => { - box.unwatch(); - return fs.rmdir(box.base); - }); }); it('watch() - watcher has started', () => { const box = newBox(); - return box.watch().then(() => { - const errorCallback = sinon.spy(err => { - err.should.have.property('message', 'Watcher has already started.'); - }); - - return box.watch().catch(errorCallback).then(() => { - errorCallback.calledOnce.should.be.true; + return box + .watch() + .then(() => { + const errorCallback = sinon.spy(err => { + err.should.have.property('message', 'Watcher has already started.'); + }); + + return box + .watch() + .catch(errorCallback) + .then(() => { + errorCallback.calledOnce.should.be.true; + }); + }) + .finally(() => { + box.unwatch(); }); - }).finally(() => { - box.unwatch(); - }); }); it('watch() - run process() before start watching', () => { @@ -441,29 +506,36 @@ describe('Box', () => { return Promise.all([ fs.writeFile(pathFn.join(box.base, 'a.txt'), 'a'), fs.writeFile(pathFn.join(box.base, 'b', 'c.js'), 'c') - ]).then(() => box.watch()).then(() => { - data.should.have.members(['a.txt', 'b/c.js']); - }).finally(() => { - box.unwatch(); - return fs.rmdir(box.base); - }); + ]) + .then(() => box.watch()) + .then(() => { + data.should.have.members(['a.txt', 'b/c.js']); + }) + .finally(() => { + box.unwatch(); + return fs.rmdir(box.base); + }); }); it('unwatch()', () => { const box = newBox('test'); const processor = sinon.spy(); - return box.watch().then(() => { - box.addProcessor(processor); - box.unwatch(); + return box + .watch() + .then(() => { + box.addProcessor(processor); + box.unwatch(); - return fs.writeFile(pathFn.join(box.base, 'a.txt'), 'a'); - }).then(() => { - processor.called.should.be.false; - }).finally(() => { - box.unwatch(); - return fs.rmdir(box.base); - }); + return fs.writeFile(pathFn.join(box.base, 'a.txt'), 'a'); + }) + .then(() => { + processor.called.should.be.false; + }) + .finally(() => { + box.unwatch(); + return fs.rmdir(box.base); + }); }); it('isWatching()', () => { @@ -471,14 +543,18 @@ describe('Box', () => { box.isWatching().should.be.false; - return box.watch().then(() => { - box.isWatching().should.be.true; - return box.unwatch(); - }).then(() => { - box.isWatching().should.be.false; - }).finally(() => { - box.unwatch(); - }); + return box + .watch() + .then(() => { + box.isWatching().should.be.true; + return box.unwatch(); + }) + .then(() => { + box.isWatching().should.be.false; + }) + .finally(() => { + box.unwatch(); + }); }); it('processBefore & processAfter events', () => { @@ -497,9 +573,13 @@ describe('Box', () => { box.on('processBefore', beforeSpy); box.on('processAfter', afterSpy); - return fs.writeFile(pathFn.join(box.base, 'a.txt'), 'a').then(() => box.process()).then(() => { - beforeSpy.calledOnce.should.be.true; - afterSpy.calledOnce.should.be.true; - }).finally(() => fs.rmdir(box.base)); + return fs + .writeFile(pathFn.join(box.base, 'a.txt'), 'a') + .then(() => box.process()) + .then(() => { + beforeSpy.calledOnce.should.be.true; + afterSpy.calledOnce.should.be.true; + }) + .finally(() => fs.rmdir(box.base)); }); }); diff --git a/test/scripts/box/file.js b/test/scripts/box/file.js index 70e15abe0b..75383bf34f 100644 --- a/test/scripts/box/file.js +++ b/test/scripts/box/file.js @@ -28,23 +28,29 @@ describe('File', () => { const path = 'test.yml'; function makeFile(path, props) { - return new File(Object.assign({ - source: pathFn.join(box.base, path), - path - }, props)); + return new File( + Object.assign( + { + source: pathFn.join(box.base, path), + path + }, + props + ) + ); } const file = makeFile(path, { source: pathFn.join(box.base, path), path, type: 'create', - params: {foo: 'bar'} + params: { foo: 'bar' } }); - before(() => Promise.all([ - fs.writeFile(file.source, body), - hexo.init() - ]).then(() => fs.stat(file.source))); + before(() => + Promise.all([fs.writeFile(file.source, body), hexo.init()]).then(() => + fs.stat(file.source) + ) + ); after(() => fs.rmdir(box.base)); @@ -62,12 +68,10 @@ describe('File', () => { file.readSync().should.eql(body); }); - it('stat()', () => Promise.all([ - fs.stat(file.source), - file.stat() - ]).then(stats => { - stats[0].should.eql(stats[1]); - })); + it('stat()', () => + Promise.all([fs.stat(file.source), file.stat()]).then(stats => { + stats[0].should.eql(stats[1]); + })); it('stat() - callback', callback => { file.stat((err, fileStats) => { diff --git a/test/scripts/console/clean.js b/test/scripts/console/clean.js index 711ddbcd5a..f7a0f516fa 100644 --- a/test/scripts/console/clean.js +++ b/test/scripts/console/clean.js @@ -7,24 +7,32 @@ describe('clean', () => { let hexo, clean; beforeEach(() => { - hexo = new Hexo(__dirname, {silent: true}); + hexo = new Hexo(__dirname, { silent: true }); clean = require('../../../lib/plugins/console/clean').bind(hexo); }); it('delete database', () => { const dbPath = hexo.database.options.path; - return fs.writeFile(dbPath, '').then(() => clean()).then(() => fs.exists(dbPath)).then(exist => { - exist.should.be.false; - }); + return fs + .writeFile(dbPath, '') + .then(() => clean()) + .then(() => fs.exists(dbPath)) + .then(exist => { + exist.should.be.false; + }); }); it('delete public folder', () => { const publicDir = hexo.public_dir; - return fs.mkdirs(publicDir).then(() => clean()).then(() => fs.exists(publicDir)).then(exist => { - exist.should.be.false; - }); + return fs + .mkdirs(publicDir) + .then(() => clean()) + .then(() => fs.exists(publicDir)) + .then(exist => { + exist.should.be.false; + }); }); it('execute corresponding filter', () => { @@ -34,8 +42,12 @@ describe('clean', () => { return fs.unlink(extraDbPath); }); - return fs.writeFile(extraDbPath, '').then(() => clean()).then(() => fs.exists(extraDbPath)).then(exist => { - exist.should.be.false; - }); + return fs + .writeFile(extraDbPath, '') + .then(() => clean()) + .then(() => fs.exists(extraDbPath)) + .then(exist => { + exist.should.be.false; + }); }); }); diff --git a/test/scripts/console/config.js b/test/scripts/console/config.js index 928c164cb5..9b1471b2a9 100644 --- a/test/scripts/console/config.js +++ b/test/scripts/console/config.js @@ -8,7 +8,9 @@ const sinon = require('sinon'); describe('config', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'config_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'config_test'), { + silent: true + }); const config = require('../../../lib/plugins/console/config').bind(hexo); const configModule = rewire('../../../lib/plugins/console/config'); @@ -21,25 +23,29 @@ describe('config', () => { it('read all config', () => { const spy = sinon.spy(); - return configModule.__with__({ - console: { - log: spy - } - })(() => configModule.call(hexo, {_: []})).then(() => { - spy.args[0][0].should.eql(hexo.config); - }); + return configModule + .__with__({ + console: { + log: spy + } + })(() => configModule.call(hexo, { _: [] })) + .then(() => { + spy.args[0][0].should.eql(hexo.config); + }); }); it('read config', () => { const spy = sinon.spy(); - return configModule.__with__({ - console: { - log: spy - } - })(() => configModule.call(hexo, {_: ['title']})).then(() => { - spy.args[0][0].should.eql(hexo.config.title); - }); + return configModule + .__with__({ + console: { + log: spy + } + })(() => configModule.call(hexo, { _: ['title'] })) + .then(() => { + spy.args[0][0].should.eql(hexo.config.title); + }); }); it('read nested config', () => { @@ -49,61 +55,83 @@ describe('config', () => { port: 12345 }; - return configModule.__with__({ - console: { - log: spy - } - })(() => configModule.call(hexo, {_: ['server.port']})).then(() => { - spy.args[0][0].should.eql(hexo.config.server.port); - }).finally(() => { - delete hexo.config.server; - }); + return configModule + .__with__({ + console: { + log: spy + } + })(() => configModule.call(hexo, { _: ['server.port'] })) + .then(() => { + spy.args[0][0].should.eql(hexo.config.server.port); + }) + .finally(() => { + delete hexo.config.server; + }); }); function writeConfig() { const args = Array.from(arguments); - return config({_: args}).then(() => fs.readFile(hexo.config_path)).then(content => yaml.load(content)); + return config({ _: args }) + .then(() => fs.readFile(hexo.config_path)) + .then(content => yaml.load(content)); } - it('write config', () => writeConfig('title', 'My Blog').then(config => { - config.title.should.eql('My Blog'); - })); + it('write config', () => + writeConfig('title', 'My Blog').then(config => { + config.title.should.eql('My Blog'); + })); - it('write config: number', () => writeConfig('server.port', '5000').then(config => { - config.server.port.should.eql(5000); - })); + it('write config: number', () => + writeConfig('server.port', '5000').then(config => { + config.server.port.should.eql(5000); + })); - it('write config: false', () => writeConfig('post_asset_folder', 'false').then(config => { - config.post_asset_folder.should.be.false; - })); + it('write config: false', () => + writeConfig('post_asset_folder', 'false').then(config => { + config.post_asset_folder.should.be.false; + })); - it('write config: true', () => writeConfig('post_asset_folder', 'true').then(config => { - config.post_asset_folder.should.be.true; - })); + it('write config: true', () => + writeConfig('post_asset_folder', 'true').then(config => { + config.post_asset_folder.should.be.true; + })); - it('write config: null', () => writeConfig('language', 'null').then(config => { - should.not.exist(config.language); - })); + it('write config: null', () => + writeConfig('language', 'null').then(config => { + should.not.exist(config.language); + })); - it('write config: regex', () => writeConfig('include', /^pattern$/gim).then(config => { - config.include.should.eql(/^pattern$/gim); - })); + it('write config: regex', () => + writeConfig('include', /^pattern$/gim).then(config => { + config.include.should.eql(/^pattern$/gim); + })); it('write config: json', () => { - const configPath = hexo.config_path = pathFn.join(hexo.base_dir, '_config.json'); - - return fs.writeFile(configPath, '{}').then(() => config({_: ['title', 'My Blog']})).then(() => fs.readFile(configPath)).then(content => { - const json = JSON.parse(content); - - json.title.should.eql('My Blog'); - - hexo.config_path = pathFn.join(hexo.base_dir, '_config.yml'); - return fs.unlink(configPath); - }); + const configPath = (hexo.config_path = pathFn.join( + hexo.base_dir, + '_config.json' + )); + + return fs + .writeFile(configPath, '{}') + .then(() => config({ _: ['title', 'My Blog'] })) + .then(() => fs.readFile(configPath)) + .then(content => { + const json = JSON.parse(content); + + json.title.should.eql('My Blog'); + + hexo.config_path = pathFn.join(hexo.base_dir, '_config.yml'); + return fs.unlink(configPath); + }); }); - it('create config if not exist', () => fs.unlink(hexo.config_path).then(() => writeConfig('subtitle', 'Hello world')).then(config => { - config.subtitle.should.eql('Hello world'); - })); + it('create config if not exist', () => + fs + .unlink(hexo.config_path) + .then(() => writeConfig('subtitle', 'Hello world')) + .then(config => { + config.subtitle.should.eql('Hello world'); + })); }); diff --git a/test/scripts/console/deploy.js b/test/scripts/console/deploy.js index 8b0d9bd4a7..396e86fea8 100644 --- a/test/scripts/console/deploy.js +++ b/test/scripts/console/deploy.js @@ -6,13 +6,15 @@ const sinon = require('sinon'); describe('deploy', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'deploy_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'deploy_test'), { + silent: true + }); const deploy = require('../../../lib/plugins/console/deploy').bind(hexo); before(() => fs.mkdirs(hexo.public_dir).then(() => hexo.init())); beforeEach(() => { - hexo.config.deploy = {type: 'foo'}; + hexo.config.deploy = { type: 'foo' }; hexo.extend.deployer.register('foo', () => {}); }); @@ -39,7 +41,7 @@ describe('deploy', () => { hexo.once('deployAfter', afterListener); hexo.extend.deployer.register('foo', deployer); - return deploy({foo: 'foo', bar: 'bar'}).then(() => { + return deploy({ foo: 'foo', bar: 'bar' }).then(() => { deployer.calledOnce.should.be.true; beforeListener.calledOnce.should.be.true; afterListener.calledOnce.should.be.true; @@ -64,14 +66,14 @@ describe('deploy', () => { }); hexo.config.deploy = [ - {type: 'foo', foo: 'foo'}, - {type: 'bar', bar: 'bar'} + { type: 'foo', foo: 'foo' }, + { type: 'bar', bar: 'bar' } ]; hexo.extend.deployer.register('foo', deployer1); hexo.extend.deployer.register('bar', deployer2); - return deploy({test: true}).then(() => { + return deploy({ test: true }).then(() => { deployer1.calledOnce.should.be.true; deployer2.calledOnce.should.be.true; }); @@ -79,12 +81,22 @@ describe('deploy', () => { it('deployer not found'); - it('generate', () => fs.writeFile(pathFn.join(hexo.source_dir, 'test.txt'), 'test').then(() => deploy({generate: true})).then(() => fs.readFile(pathFn.join(hexo.public_dir, 'test.txt'))).then(content => { - content.should.eql('test'); - return fs.rmdir(hexo.source_dir); - })); - - it('run generate if public directory not exist', () => fs.rmdir(hexo.public_dir).then(() => deploy({})).then(() => fs.exists(hexo.public_dir)).then(exist => { - exist.should.be.true; - })); + it('generate', () => + fs + .writeFile(pathFn.join(hexo.source_dir, 'test.txt'), 'test') + .then(() => deploy({ generate: true })) + .then(() => fs.readFile(pathFn.join(hexo.public_dir, 'test.txt'))) + .then(content => { + content.should.eql('test'); + return fs.rmdir(hexo.source_dir); + })); + + it('run generate if public directory not exist', () => + fs + .rmdir(hexo.public_dir) + .then(() => deploy({})) + .then(() => fs.exists(hexo.public_dir)) + .then(exist => { + exist.should.be.true; + })); }); diff --git a/test/scripts/console/generate.js b/test/scripts/console/generate.js index 4755e87a00..2dd6a35298 100644 --- a/test/scripts/console/generate.js +++ b/test/scripts/console/generate.js @@ -11,7 +11,7 @@ describe('generate', () => { let hexo, generate; beforeEach(() => { - hexo = new Hexo(pathFn.join(__dirname, 'generate_test'), {silent: true}); + hexo = new Hexo(pathFn.join(__dirname, 'generate_test'), { silent: true }); generate = generateConsole.bind(hexo); return fs.mkdirs(hexo.base_dir).then(() => hexo.init()); @@ -20,7 +20,6 @@ describe('generate', () => { afterEach(() => fs.rmdir(hexo.base_dir)); function testGenerate(options) { - return Promise.all([ // Add some source files fs.writeFile(pathFn.join(hexo.source_dir, 'test.txt'), 'test'), @@ -29,22 +28,27 @@ describe('generate', () => { fs.writeFile(pathFn.join(hexo.public_dir, 'foo.txt'), 'foo'), fs.writeFile(pathFn.join(hexo.public_dir, 'bar', 'boo.txt'), 'boo'), fs.writeFile(pathFn.join(hexo.public_dir, 'faz', 'yo.txt'), 'yo') - ]).then(() => generate(options)).then(() => Promise.all([ - fs.readFile(pathFn.join(hexo.public_dir, 'test.txt')), - fs.readFile(pathFn.join(hexo.public_dir, 'faz', 'yo.txt')), - fs.exists(pathFn.join(hexo.public_dir, 'foo.txt')), - fs.exists(pathFn.join(hexo.public_dir, 'bar', 'boo.txt')) - ])).then(result => { - // Check the new file - result[0].should.eql('test'); - - // Check the updated file - result[1].should.eql('yoooo'); - - // Old files should not be deleted - result[2].should.be.true; - result[3].should.be.true; - }); + ]) + .then(() => generate(options)) + .then(() => + Promise.all([ + fs.readFile(pathFn.join(hexo.public_dir, 'test.txt')), + fs.readFile(pathFn.join(hexo.public_dir, 'faz', 'yo.txt')), + fs.exists(pathFn.join(hexo.public_dir, 'foo.txt')), + fs.exists(pathFn.join(hexo.public_dir, 'bar', 'boo.txt')) + ]) + ) + .then(result => { + // Check the new file + result[0].should.eql('test'); + + // Check the updated file + result[1].should.eql('yoooo'); + + // Old files should not be deleted + result[2].should.be.true; + result[3].should.be.true; + }); } it('default', () => testGenerate()); @@ -55,41 +59,61 @@ describe('generate', () => { const content = 'test'; // Add some source files - return fs.writeFile(src, content).then(() => // First generation - generate()).then(() => // Delete generated files - fs.unlink(dest)).then(() => // Second generation - generate()).then(() => fs.readFile(dest)).then(result => { - result.should.eql(content); - - // Remove source files and generated files - return Promise.all([ - fs.unlink(src), + return fs + .writeFile(src, content) + .then(() => + // First generation + generate() + ) + .then(() => + // Delete generated files fs.unlink(dest) - ]); - }); + ) + .then(() => + // Second generation + generate() + ) + .then(() => fs.readFile(dest)) + .then(result => { + result.should.eql(content); + + // Remove source files and generated files + return Promise.all([fs.unlink(src), fs.unlink(dest)]); + }); }); - it('don\'t write if file unchanged', () => { + it("don't write if file unchanged", () => { const src = pathFn.join(hexo.source_dir, 'test.txt'); const dest = pathFn.join(hexo.public_dir, 'test.txt'); const content = 'test'; const newContent = 'newtest'; // Add some source files - return fs.writeFile(src, content).then(() => // First generation - generate()).then(() => // Change the generated file - fs.writeFile(dest, newContent)).then(() => // Second generation - generate()).then(() => // Read the generated file - fs.readFile(dest)).then(result => { - // Make sure the generated file didn't changed - result.should.eql(newContent); - - // Remove source files and generated files - return Promise.all([ - fs.unlink(src), - fs.unlink(dest) - ]); - }); + return fs + .writeFile(src, content) + .then(() => + // First generation + generate() + ) + .then(() => + // Change the generated file + fs.writeFile(dest, newContent) + ) + .then(() => + // Second generation + generate() + ) + .then(() => + // Read the generated file + fs.readFile(dest) + ) + .then(result => { + // Make sure the generated file didn't changed + result.should.eql(newContent); + + // Remove source files and generated files + return Promise.all([fs.unlink(src), fs.unlink(dest)]); + }); }); it('force regenerate', () => { @@ -98,20 +122,31 @@ describe('generate', () => { const content = 'test'; let mtime; - return fs.writeFile(src, content).then(() => // First generation - generate()).then(() => // Read file status - fs.stat(dest)).then(stats => { - mtime = stats.mtime.getTime(); - }).delay(1000).then(() => // Force regenerate - generate({force: true})).then(() => fs.stat(dest)).then(stats => { - stats.mtime.getTime().should.be.above(mtime); - - // Remove source files and generated files - return Promise.all([ - fs.unlink(src), - fs.unlink(dest) - ]); - }); + return fs + .writeFile(src, content) + .then(() => + // First generation + generate() + ) + .then(() => + // Read file status + fs.stat(dest) + ) + .then(stats => { + mtime = stats.mtime.getTime(); + }) + .delay(1000) + .then(() => + // Force regenerate + generate({ force: true }) + ) + .then(() => fs.stat(dest)) + .then(stats => { + stats.mtime.getTime().should.be.above(mtime); + + // Remove source files and generated files + return Promise.all([fs.unlink(src), fs.unlink(dest)]); + }); }); it('watch - update', () => { @@ -119,22 +154,35 @@ describe('generate', () => { const dest = pathFn.join(hexo.public_dir, 'test.txt'); const content = 'test'; - return testGenerate({watch: true}).then(() => // Update the file - fs.writeFile(src, content)).delay(300).then(() => fs.readFile(dest)).then(result => { - // Check the updated file - result.should.eql(content); - }).finally(() => { - // Stop watching - hexo.unwatch(); - }); + return testGenerate({ watch: true }) + .then(() => + // Update the file + fs.writeFile(src, content) + ) + .delay(300) + .then(() => fs.readFile(dest)) + .then(result => { + // Check the updated file + result.should.eql(content); + }) + .finally(() => { + // Stop watching + hexo.unwatch(); + }); }); - it('watch - delete', () => testGenerate({watch: true}).then(() => fs.unlink(pathFn.join(hexo.source_dir, 'test.txt'))).delay(300).then(() => fs.exists(pathFn.join(hexo.public_dir, 'test.txt'))).then(exist => { - exist.should.be.false; - }).finally(() => { - // Stop watching - hexo.unwatch(); - })); + it('watch - delete', () => + testGenerate({ watch: true }) + .then(() => fs.unlink(pathFn.join(hexo.source_dir, 'test.txt'))) + .delay(300) + .then(() => fs.exists(pathFn.join(hexo.public_dir, 'test.txt'))) + .then(exist => { + exist.should.be.false; + }) + .finally(() => { + // Stop watching + hexo.unwatch(); + })); it('deploy', () => { const deployer = sinon.spy(); @@ -145,41 +193,53 @@ describe('generate', () => { type: 'test' }; - return generate({deploy: true}).then(() => { + return generate({ deploy: true }).then(() => { deployer.calledOnce.should.be.true; }); }); - it('update theme source files', () => Promise.all([ - // Add some source files - fs.writeFile(pathFn.join(hexo.theme_dir, 'source', 'a.txt'), 'a'), - fs.writeFile(pathFn.join(hexo.theme_dir, 'source', 'b.txt'), 'b'), - fs.writeFile(pathFn.join(hexo.theme_dir, 'source', 'c.swig'), 'c') - ]).then(() => generate()).then(() => // Update source file + it('update theme source files', () => Promise.all([ - fs.writeFile(pathFn.join(hexo.theme_dir, 'source', 'b.txt'), 'bb'), - fs.writeFile(pathFn.join(hexo.theme_dir, 'source', 'c.swig'), 'cc') - ])).then(() => // Generate again - generate()).then(() => // Read the updated source file - Promise.all([ - fs.readFile(pathFn.join(hexo.public_dir, 'b.txt')), - fs.readFile(pathFn.join(hexo.public_dir, 'c.html')) - ])).then(result => { - result[0].should.eql('bb'); - result[1].should.eql('cc'); - })); + // Add some source files + fs.writeFile(pathFn.join(hexo.theme_dir, 'source', 'a.txt'), 'a'), + fs.writeFile(pathFn.join(hexo.theme_dir, 'source', 'b.txt'), 'b'), + fs.writeFile(pathFn.join(hexo.theme_dir, 'source', 'c.swig'), 'c') + ]) + .then(() => generate()) + .then(() => + // Update source file + Promise.all([ + fs.writeFile(pathFn.join(hexo.theme_dir, 'source', 'b.txt'), 'bb'), + fs.writeFile(pathFn.join(hexo.theme_dir, 'source', 'c.swig'), 'cc') + ]) + ) + .then(() => + // Generate again + generate() + ) + .then(() => + // Read the updated source file + Promise.all([ + fs.readFile(pathFn.join(hexo.public_dir, 'b.txt')), + fs.readFile(pathFn.join(hexo.public_dir, 'c.html')) + ]) + ) + .then(result => { + result[0].should.eql('bb'); + result[1].should.eql('cc'); + })); it('proceeds after error when bail option is not set', () => { - hexo.extend.renderer.register('err', 'html', () => Promise.reject(new Error('Testing unhandled exception'))); - hexo.extend.generator.register('test_page', () => - [ - { - path: 'testing-path', - layout: 'post', - data: {} - } - ] + hexo.extend.renderer.register('err', 'html', () => + Promise.reject(new Error('Testing unhandled exception')) ); + hexo.extend.generator.register('test_page', () => [ + { + path: 'testing-path', + layout: 'post', + data: {} + } + ]); return Promise.all([ fs.writeFile(pathFn.join(hexo.theme_dir, 'layout', 'post.err'), 'post') @@ -189,35 +249,35 @@ describe('generate', () => { }); it('proceeds after error when bail option is set to false', () => { - hexo.extend.renderer.register('err', 'html', () => Promise.reject(new Error('Testing unhandled exception'))); - hexo.extend.generator.register('test_page', () => - [ - { - path: 'testing-path', - layout: 'post', - data: {} - } - ] + hexo.extend.renderer.register('err', 'html', () => + Promise.reject(new Error('Testing unhandled exception')) ); + hexo.extend.generator.register('test_page', () => [ + { + path: 'testing-path', + layout: 'post', + data: {} + } + ]); return Promise.all([ fs.writeFile(pathFn.join(hexo.theme_dir, 'layout', 'post.err'), 'post') ]).then(() => { - return generate({bail: false}); + return generate({ bail: false }); }); }); it('breaks after error when bail option is set to true', () => { - hexo.extend.renderer.register('err', 'html', () => Promise.reject(new Error('Testing unhandled exception'))); - hexo.extend.generator.register('test_page', () => - [ - { - path: 'testing-path', - layout: 'post', - data: {} - } - ] + hexo.extend.renderer.register('err', 'html', () => + Promise.reject(new Error('Testing unhandled exception')) ); + hexo.extend.generator.register('test_page', () => [ + { + path: 'testing-path', + layout: 'post', + data: {} + } + ]); const errorCallback = sinon.spy(err => { err.should.have.property('message', 'Testing unhandled exception'); @@ -226,13 +286,17 @@ describe('generate', () => { return Promise.all([ fs.writeFile(pathFn.join(hexo.theme_dir, 'layout', 'post.err'), 'post') ]).then(() => { - return generate({bail: true}).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + return generate({ bail: true }) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); }); it('should generate all files even when concurrency is set', () => { - return generate({ concurrency: 1 }).then(() => generate({ concurrency: 2 })); + return generate({ concurrency: 1 }).then(() => + generate({ concurrency: 2 }) + ); }); }); diff --git a/test/scripts/console/list_categories.js b/test/scripts/console/list_categories.js index 822bc312a1..2d43a499be 100644 --- a/test/scripts/console/list_categories.js +++ b/test/scripts/console/list_categories.js @@ -9,7 +9,9 @@ describe('Console list', () => { const hexo = new Hexo(__dirname); const Post = hexo.model('Post'); - const listCategories = require('../../../lib/plugins/console/list/category').bind(hexo); + const listCategories = require('../../../lib/plugins/console/list/category').bind( + hexo + ); before(() => { const log = console.log; @@ -31,16 +33,19 @@ describe('Console list', () => { it('categories', () => { const posts = [ - {source: 'foo', slug: 'foo', title: 'Its', date: 1e8}, - {source: 'bar', slug: 'bar', title: 'Math', date: 1e8 + 1}, - {source: 'baz', slug: 'baz', title: 'Dude', date: 1e8 - 1} + { source: 'foo', slug: 'foo', title: 'Its', date: 1e8 }, + { source: 'bar', slug: 'bar', title: 'Math', date: 1e8 + 1 }, + { source: 'baz', slug: 'baz', title: 'Dude', date: 1e8 - 1 } ]; - return hexo.init() - .then(() => Post.insert(posts)).then(posts => Promise.each([ - ['foo'], - ['baz'], - ['baz'] - ], (tags, i) => posts[i].setCategories(tags))).then(() => { + return hexo + .init() + .then(() => Post.insert(posts)) + .then(posts => + Promise.each([['foo'], ['baz'], ['baz']], (tags, i) => + posts[i].setCategories(tags) + ) + ) + .then(() => { hexo.locals.invalidate(); }) .then(() => { diff --git a/test/scripts/console/list_page.js b/test/scripts/console/list_page.js index d4f2afd1c5..b9709f4770 100644 --- a/test/scripts/console/list_page.js +++ b/test/scripts/console/list_page.js @@ -7,7 +7,9 @@ describe('Console list', () => { const Hexo = require('../../../lib/hexo'); const hexo = new Hexo(); const Page = hexo.model('Page'); - const listPages = require('../../../lib/plugins/console/list/page').bind(hexo); + const listPages = require('../../../lib/plugins/console/list/page').bind( + hexo + ); hexo.config.permalink = ':title/'; before(() => { @@ -29,12 +31,12 @@ describe('Console list', () => { expect(console.log.calledWith(sinon.match('No pages.'))).to.be.true; }); - it('page', () => Page.insert({ - source: 'foo', - title: 'Hello World', - path: 'bar' - }) - .then(() => { + it('page', () => + Page.insert({ + source: 'foo', + title: 'Hello World', + path: 'bar' + }).then(() => { listPages(); expect(console.log.calledWith(sinon.match('Date'))).to.be.true; expect(console.log.calledWith(sinon.match('Title'))).to.be.true; diff --git a/test/scripts/console/list_post.js b/test/scripts/console/list_post.js index 96f424fdfb..0c514b96ec 100644 --- a/test/scripts/console/list_post.js +++ b/test/scripts/console/list_post.js @@ -8,7 +8,9 @@ describe('Console list', () => { const hexo = new Hexo(__dirname); const Post = hexo.model('Post'); - const listPosts = require('../../../lib/plugins/console/list/post').bind(hexo); + const listPosts = require('../../../lib/plugins/console/list/post').bind( + hexo + ); before(() => { const log = console.log; @@ -33,12 +35,14 @@ describe('Console list', () => { it('post', () => { const posts = [ - {source: 'foo', slug: 'foo', title: 'Its', date: 1e8}, - {source: 'bar', slug: 'bar', title: 'Math', date: 1e8 + 1}, - {source: 'baz', slug: 'baz', title: 'Dude', date: 1e8 - 1} + { source: 'foo', slug: 'foo', title: 'Its', date: 1e8 }, + { source: 'bar', slug: 'bar', title: 'Math', date: 1e8 + 1 }, + { source: 'baz', slug: 'baz', title: 'Dude', date: 1e8 - 1 } ]; - return hexo.init() - .then(() => Post.insert(posts)).then(() => { + return hexo + .init() + .then(() => Post.insert(posts)) + .then(() => { hexo.locals.invalidate(); }) .then(() => { @@ -49,9 +53,11 @@ describe('Console list', () => { expect(console.log.calledWith(sinon.match('Category'))).to.be.true; expect(console.log.calledWith(sinon.match('Tags'))).to.be.true; for (let i = 0; i < posts.length; i++) { - expect(console.log.calledWith(sinon.match(posts[i].source))).to.be.true; + expect(console.log.calledWith(sinon.match(posts[i].source))).to.be + .true; expect(console.log.calledWith(sinon.match(posts[i].slug))).to.be.true; - expect(console.log.calledWith(sinon.match(posts[i].title))).to.be.true; + expect(console.log.calledWith(sinon.match(posts[i].title))).to.be + .true; } }); }); diff --git a/test/scripts/console/list_tags.js b/test/scripts/console/list_tags.js index 50b38419f1..01f2abc1c9 100644 --- a/test/scripts/console/list_tags.js +++ b/test/scripts/console/list_tags.js @@ -33,16 +33,19 @@ describe('Console list', () => { it('tags', () => { const posts = [ - {source: 'foo', slug: 'foo', title: 'Its', date: 1e8}, - {source: 'bar', slug: 'bar', title: 'Math', date: 1e8 + 1}, - {source: 'baz', slug: 'baz', title: 'Dude', date: 1e8 - 1} + { source: 'foo', slug: 'foo', title: 'Its', date: 1e8 }, + { source: 'bar', slug: 'bar', title: 'Math', date: 1e8 + 1 }, + { source: 'baz', slug: 'baz', title: 'Dude', date: 1e8 - 1 } ]; - return hexo.init() - .then(() => Post.insert(posts)).then(posts => Promise.each([ - ['foo'], - ['baz'], - ['baz'] - ], (tags, i) => posts[i].setTags(tags))).then(() => { + return hexo + .init() + .then(() => Post.insert(posts)) + .then(posts => + Promise.each([['foo'], ['baz'], ['baz']], (tags, i) => + posts[i].setTags(tags) + ) + ) + .then(() => { hexo.locals.invalidate(); }) .then(() => { diff --git a/test/scripts/console/migrate.js b/test/scripts/console/migrate.js index a029b50fd8..37f51897c2 100644 --- a/test/scripts/console/migrate.js +++ b/test/scripts/console/migrate.js @@ -4,7 +4,7 @@ const sinon = require('sinon'); describe('migrate', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(__dirname, {silent: true}); + const hexo = new Hexo(__dirname, { silent: true }); const migrate = require('../../../lib/plugins/console/migrate').bind(hexo); it('default', () => { @@ -15,7 +15,7 @@ describe('migrate', () => { hexo.extend.migrator.register('test', migrator); - return migrate({_: ['test'], foo: 1, bar: 2}).then(() => { + return migrate({ _: ['test'], foo: 1, bar: 2 }).then(() => { migrator.calledOnce.should.be.true; }); }); diff --git a/test/scripts/console/new.js b/test/scripts/console/new.js index 2ed1a11326..ed59db2643 100644 --- a/test/scripts/console/new.js +++ b/test/scripts/console/new.js @@ -8,7 +8,7 @@ const sinon = require('sinon'); describe('new', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'new_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'new_test'), { silent: true }); const n = require('../../../lib/plugins/console/new').bind(hexo); const post = hexo.post; const now = Date.now(); @@ -17,16 +17,21 @@ describe('new', () => { before(() => { clock = sinon.useFakeTimers(now); - return fs.mkdirs(hexo.base_dir).then(() => hexo.init()).then(() => hexo.scaffold.set('post', [ - 'title: {{ title }}', - 'date: {{ date }}', - 'tags:', - '---' - ].join('\n'))).then(() => hexo.scaffold.set('draft', [ - 'title: {{ title }}', - 'tags:', - '---' - ].join('\n'))); + return fs + .mkdirs(hexo.base_dir) + .then(() => hexo.init()) + .then(() => + hexo.scaffold.set( + 'post', + ['title: {{ title }}', 'date: {{ date }}', 'tags:', '---'].join('\n') + ) + ) + .then(() => + hexo.scaffold.set( + 'draft', + ['title: {{ title }}', 'tags:', '---'].join('\n') + ) + ); }); after(() => { @@ -37,124 +42,148 @@ describe('new', () => { it('title', () => { const date = moment(now); const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); - const body = [ - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; + const body = + [ + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; return n({ _: ['Hello World'] - }).then(() => fs.readFile(path)).then(content => { - content.should.eql(body); - return fs.unlink(path); - }); + }) + .then(() => fs.readFile(path)) + .then(content => { + content.should.eql(body); + return fs.unlink(path); + }); }); it('layout', () => { const path = pathFn.join(hexo.source_dir, '_drafts', 'Hello-World.md'); - const body = [ - 'title: Hello World', - 'tags:', - '---' - ].join('\n') + '\n'; + const body = ['title: Hello World', 'tags:', '---'].join('\n') + '\n'; return n({ _: ['draft', 'Hello World'] - }).then(() => fs.readFile(path)).then(content => { - content.should.eql(body); - return fs.unlink(path); - }); + }) + .then(() => fs.readFile(path)) + .then(content => { + content.should.eql(body); + return fs.unlink(path); + }); }); it('slug', () => { const date = moment(now); const path = pathFn.join(hexo.source_dir, '_posts', 'foo.md'); - const body = [ - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; + const body = + [ + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; return n({ _: ['Hello World'], slug: 'foo' - }).then(() => fs.readFile(path)).then(content => { - content.should.eql(body); - return fs.unlink(path); - }); + }) + .then(() => fs.readFile(path)) + .then(content => { + content.should.eql(body); + return fs.unlink(path); + }); }); it('path', () => { const date = moment(now); const path = pathFn.join(hexo.source_dir, '_posts', 'bar.md'); - const body = [ - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; + const body = + [ + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; return n({ _: ['Hello World'], slug: 'foo', path: 'bar' - }).then(() => fs.readFile(path)).then(content => { - content.should.eql(body); - return fs.unlink(path); - }); + }) + .then(() => fs.readFile(path)) + .then(content => { + content.should.eql(body); + return fs.unlink(path); + }); }); it('rename if target existed', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World-1.md'); - return post.create({ - title: 'Hello World' - }).then(() => n({ - _: ['Hello World'] - })).then(() => fs.exists(path)).then(exist => { - exist.should.be.true; - - return Promise.all([ - fs.unlink(path), - fs.unlink(pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md')) - ]); - }); + return post + .create({ + title: 'Hello World' + }) + .then(() => + n({ + _: ['Hello World'] + }) + ) + .then(() => fs.exists(path)) + .then(exist => { + exist.should.be.true; + + return Promise.all([ + fs.unlink(path), + fs.unlink(pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md')) + ]); + }); }); it('replace existing files', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); - return post.create({ - title: 'Hello World' - }).then(() => n({ - _: ['Hello World'], - replace: true - })).then(() => fs.exists(pathFn.join(hexo.source_dir, '_posts', 'Hello-World-1.md'))).then(exist => { - exist.should.be.false; - return fs.unlink(path); - }); + return post + .create({ + title: 'Hello World' + }) + .then(() => + n({ + _: ['Hello World'], + replace: true + }) + ) + .then(() => + fs.exists(pathFn.join(hexo.source_dir, '_posts', 'Hello-World-1.md')) + ) + .then(exist => { + exist.should.be.false; + return fs.unlink(path); + }); }); it('extra data', () => { const date = moment(now); const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); - const body = [ - 'title: Hello World', - 'foo: bar', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; + const body = + [ + 'title: Hello World', + 'foo: bar', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; return n({ _: ['Hello World'], foo: 'bar' - }).then(() => fs.readFile(path)).then(content => { - content.should.eql(body); - return fs.unlink(path); - }); + }) + .then(() => fs.readFile(path)) + .then(content => { + content.should.eql(body); + return fs.unlink(path); + }); }); }); diff --git a/test/scripts/console/publish.js b/test/scripts/console/publish.js index 8252dbe74f..7e178913af 100644 --- a/test/scripts/console/publish.js +++ b/test/scripts/console/publish.js @@ -8,7 +8,9 @@ const sinon = require('sinon'); describe('publish', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'publish_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'publish_test'), { + silent: true + }); const publish = require('../../../lib/plugins/console/publish').bind(hexo); const post = hexo.post; const now = Date.now(); @@ -17,18 +19,27 @@ describe('publish', () => { before(() => { clock = sinon.useFakeTimers(now); - return fs.mkdirs(hexo.base_dir).then(() => hexo.init()).then(() => hexo.scaffold.set('post', [ - '---', - 'title: {{ title }}', - 'date: {{ date }}', - 'tags:', - '---' - ].join('\n'))).then(() => hexo.scaffold.set('draft', [ - '---', - 'title: {{ title }}', - 'tags:', - '---' - ].join('\n'))); + return fs + .mkdirs(hexo.base_dir) + .then(() => hexo.init()) + .then(() => + hexo.scaffold.set( + 'post', + [ + '---', + 'title: {{ title }}', + 'date: {{ date }}', + 'tags:', + '---' + ].join('\n') + ) + ) + .then(() => + hexo.scaffold.set( + 'draft', + ['---', 'title: {{ title }}', 'tags:', '---'].join('\n') + ) + ); }); after(() => { @@ -36,87 +47,106 @@ describe('publish', () => { return fs.rmdir(hexo.base_dir); }); - beforeEach(() => post.create({ - title: 'Hello World', - layout: 'draft' - })); + beforeEach(() => + post.create({ + title: 'Hello World', + layout: 'draft' + }) + ); it('slug', () => { const draftPath = pathFn.join(hexo.source_dir, '_drafts', 'Hello-World.md'); const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); const date = moment(now); - const content = [ - '---', - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; + const content = + [ + '---', + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; return publish({ _: ['Hello-World'] - }).then(() => Promise.all([ - fs.exists(draftPath), - fs.readFile(path) - ])).spread((exist, data) => { - exist.should.be.false; - data.should.eql(content); - - return fs.unlink(path); - }); + }) + .then(() => Promise.all([fs.exists(draftPath), fs.readFile(path)])) + .spread((exist, data) => { + exist.should.be.false; + data.should.eql(content); + + return fs.unlink(path); + }); }); it('layout', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); const date = moment(now); - const content = [ - '---', - 'layout: photo', - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; + const content = + [ + '---', + 'layout: photo', + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; return publish({ _: ['photo', 'Hello-World'] - }).then(() => fs.readFile(path)).then(data => { - data.should.eql(content); - return fs.unlink(path); - }); + }) + .then(() => fs.readFile(path)) + .then(data => { + data.should.eql(content); + return fs.unlink(path); + }); }); it('rename if target existed', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World-1.md'); - return post.create({ - title: 'Hello World' - }).then(() => publish({ - _: ['Hello-World'] - })).then(() => fs.exists(path)).then(exist => { - exist.should.be.true; - - return Promise.all([ - fs.unlink(path), - fs.unlink(pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md')) - ]); - }); + return post + .create({ + title: 'Hello World' + }) + .then(() => + publish({ + _: ['Hello-World'] + }) + ) + .then(() => fs.exists(path)) + .then(exist => { + exist.should.be.true; + + return Promise.all([ + fs.unlink(path), + fs.unlink(pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md')) + ]); + }); }); it('replace existing target', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); - return post.create({ - title: 'Hello World' - }).then(() => publish({ - _: ['Hello-World'], - replace: true - })).then(() => fs.exists(pathFn.join(hexo.source_dir, '_posts', 'Hello-World-1.md'))).then(exist => { - exist.should.be.false; - - return fs.unlink(path); - }); + return post + .create({ + title: 'Hello World' + }) + .then(() => + publish({ + _: ['Hello-World'], + replace: true + }) + ) + .then(() => + fs.exists(pathFn.join(hexo.source_dir, '_posts', 'Hello-World-1.md')) + ) + .then(exist => { + exist.should.be.false; + + return fs.unlink(path); + }); }); }); diff --git a/test/scripts/console/render.js b/test/scripts/console/render.js index 5243703740..8b8bd8bc81 100644 --- a/test/scripts/console/render.js +++ b/test/scripts/console/render.js @@ -6,74 +6,75 @@ const Promise = require('bluebird'); describe('render', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'render_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'render_test'), { + silent: true + }); const render = require('../../../lib/plugins/console/render').bind(hexo); before(() => fs.mkdirs(hexo.base_dir).then(() => hexo.init())); after(() => fs.rmdir(hexo.base_dir)); - const body = [ - 'foo: 1', - 'bar:', - ' boo: 2' - ].join('\n'); + const body = ['foo: 1', 'bar:', ' boo: 2'].join('\n'); it('relative path', () => { const src = pathFn.join(hexo.base_dir, 'test.yml'); const dest = pathFn.join(hexo.base_dir, 'result.json'); - return fs.writeFile(src, body).then(() => render({_: ['test.yml'], output: 'result.json'})).then(() => fs.readFile(dest)).then(result => { - JSON.parse(result).should.eql({ - foo: 1, - bar: { - boo: 2 - } + return fs + .writeFile(src, body) + .then(() => render({ _: ['test.yml'], output: 'result.json' })) + .then(() => fs.readFile(dest)) + .then(result => { + JSON.parse(result).should.eql({ + foo: 1, + bar: { + boo: 2 + } + }); + + return Promise.all([fs.unlink(src), fs.unlink(dest)]); }); - - return Promise.all([ - fs.unlink(src), - fs.unlink(dest) - ]); - }); }); it('absolute path', () => { const src = pathFn.join(hexo.base_dir, 'test.yml'); const dest = pathFn.join(hexo.base_dir, 'result.json'); - return fs.writeFile(src, body).then(() => render({_: [src], output: 'result.json'})).then(() => fs.readFile(dest)).then(result => { - JSON.parse(result).should.eql({ - foo: 1, - bar: { - boo: 2 - } + return fs + .writeFile(src, body) + .then(() => render({ _: [src], output: 'result.json' })) + .then(() => fs.readFile(dest)) + .then(result => { + JSON.parse(result).should.eql({ + foo: 1, + bar: { + boo: 2 + } + }); + + return Promise.all([fs.unlink(src), fs.unlink(dest)]); }); - - return Promise.all([ - fs.unlink(src), - fs.unlink(dest) - ]); - }); }); it('absolute output', () => { const src = pathFn.join(hexo.base_dir, 'test.yml'); const dest = pathFn.join(hexo.base_dir, 'result.json'); - return fs.writeFile(src, body).then(() => render({_: ['test.yml'], output: dest})).then(() => fs.readFile(dest)).then(result => { - JSON.parse(result).should.eql({ - foo: 1, - bar: { - boo: 2 - } + return fs + .writeFile(src, body) + .then(() => render({ _: ['test.yml'], output: dest })) + .then(() => fs.readFile(dest)) + .then(result => { + JSON.parse(result).should.eql({ + foo: 1, + bar: { + boo: 2 + } + }); + + return Promise.all([fs.unlink(src), fs.unlink(dest)]); }); - - return Promise.all([ - fs.unlink(src), - fs.unlink(dest) - ]); - }); }); it('output'); @@ -82,37 +83,49 @@ describe('render', () => { const src = pathFn.join(hexo.base_dir, 'test'); const dest = pathFn.join(hexo.base_dir, 'result.json'); - return fs.writeFile(src, body).then(() => render({_: ['test'], output: 'result.json', engine: 'yaml'})).then(() => fs.readFile(dest)).then(result => { - JSON.parse(result).should.eql({ - foo: 1, - bar: { - boo: 2 - } + return fs + .writeFile(src, body) + .then(() => + render({ _: ['test'], output: 'result.json', engine: 'yaml' }) + ) + .then(() => fs.readFile(dest)) + .then(result => { + JSON.parse(result).should.eql({ + foo: 1, + bar: { + boo: 2 + } + }); + + return Promise.all([fs.unlink(src), fs.unlink(dest)]); }); - - return Promise.all([ - fs.unlink(src), - fs.unlink(dest) - ]); - }); }); it('pretty', () => { const src = pathFn.join(hexo.base_dir, 'test.yml'); const dest = pathFn.join(hexo.base_dir, 'result.json'); - return fs.writeFile(src, body).then(() => render({_: ['test.yml'], output: 'result.json', pretty: true})).then(() => fs.readFile(dest)).then(result => { - result.should.eql(JSON.stringify({ - foo: 1, - bar: { - boo: 2 - } - }, null, ' ')); - - return Promise.all([ - fs.unlink(src), - fs.unlink(dest) - ]); - }); + return fs + .writeFile(src, body) + .then(() => + render({ _: ['test.yml'], output: 'result.json', pretty: true }) + ) + .then(() => fs.readFile(dest)) + .then(result => { + result.should.eql( + JSON.stringify( + { + foo: 1, + bar: { + boo: 2 + } + }, + null, + ' ' + ) + ); + + return Promise.all([fs.unlink(src), fs.unlink(dest)]); + }); }); }); diff --git a/test/scripts/extend/console.js b/test/scripts/extend/console.js index 5eaa2fcd59..2d68d60d6a 100644 --- a/test/scripts/extend/console.js +++ b/test/scripts/extend/console.js @@ -45,7 +45,7 @@ describe('Console', () => { } // name, desc, options, fn - c.register('test', 'this is a test', {init: true}, () => {}); + c.register('test', 'this is a test', { init: true }, () => {}); c.get('test').should.exist; c.get('test').desc.should.eql('this is a test'); @@ -53,7 +53,7 @@ describe('Console', () => { // name, desc, options, not fn try { - c.register('test', 'this is a test', {init: true}); + c.register('test', 'this is a test', { init: true }); } catch (err) { err.should.be .instanceOf(TypeError) @@ -78,7 +78,7 @@ describe('Console', () => { const c = new Console(); c.register('test', (args, callback) => { - args.should.eql({foo: 'bar'}); + args.should.eql({ foo: 'bar' }); callback(null, 'foo'); }); diff --git a/test/scripts/extend/deployer.js b/test/scripts/extend/deployer.js index e07d37c4e1..6ee657faf5 100644 --- a/test/scripts/extend/deployer.js +++ b/test/scripts/extend/deployer.js @@ -34,7 +34,7 @@ describe('Deployer', () => { const d = new Deployer(); d.register('test', (args, callback) => { - args.should.eql({foo: 'bar'}); + args.should.eql({ foo: 'bar' }); callback(null, 'foo'); }); @@ -49,7 +49,7 @@ describe('Deployer', () => { const d = new Deployer(); d.register('test', args => { - args.should.eql({foo: 'bar'}); + args.should.eql({ foo: 'bar' }); return 'foo'; }); diff --git a/test/scripts/extend/filter.js b/test/scripts/extend/filter.js index 1c9d88bf32..e3c9f3aa00 100644 --- a/test/scripts/extend/filter.js +++ b/test/scripts/extend/filter.js @@ -63,7 +63,9 @@ describe('Filter', () => { f.register('test', () => {}, 15); - f.list('test').map(item => item.priority).should.eql([5, 10, 15]); + f.list('test') + .map(item => item.priority) + .should.eql([5, 10, 15]); }); it('unregister()', () => { @@ -151,7 +153,7 @@ describe('Filter', () => { const filter2 = sinon.spy(data => { filter1.calledOnce.should.be.true; - data.should.eql({foo: 1}); + data.should.eql({ foo: 1 }); data.bar = 2; }); @@ -161,7 +163,7 @@ describe('Filter', () => { return f.exec('test', {}).then(data => { filter1.calledOnce.should.be.true; filter2.calledOnce.should.be.true; - data.should.eql({foo: 1, bar: 2}); + data.should.eql({ foo: 1, bar: 2 }); }); }); @@ -181,17 +183,23 @@ describe('Filter', () => { f.register('test', filter1); f.register('test', filter2); - return f.exec('test', {}, { - args: [1, 2] - }).then(() => { - filter1.calledOnce.should.be.true; - filter2.calledOnce.should.be.true; - }); + return f + .exec( + 'test', + {}, + { + args: [1, 2] + } + ) + .then(() => { + filter1.calledOnce.should.be.true; + filter2.calledOnce.should.be.true; + }); }); it('exec() - context', () => { const f = new Filter(); - const ctx = {foo: 1, bar: 2}; + const ctx = { foo: 1, bar: 2 }; const filter1 = sinon.spy(function(data) { this.should.eql(ctx); @@ -204,7 +212,7 @@ describe('Filter', () => { f.register('test', filter1); f.register('test', filter2); - return f.exec('test', {}, {context: ctx}).then(() => { + return f.exec('test', {}, { context: ctx }).then(() => { filter1.calledOnce.should.be.true; filter2.calledOnce.should.be.true; }); @@ -242,14 +250,14 @@ describe('Filter', () => { const filter2 = sinon.spy(data => { filter1.calledOnce.should.be.true; - data.should.eql({foo: 1}); + data.should.eql({ foo: 1 }); data.bar = 2; }); f.register('test', filter1); f.register('test', filter2); - f.execSync('test', {}).should.eql({foo: 1, bar: 2}); + f.execSync('test', {}).should.eql({ foo: 1, bar: 2 }); filter1.calledOnce.should.be.true; filter2.calledOnce.should.be.true; }); @@ -270,9 +278,13 @@ describe('Filter', () => { f.register('test', filter1); f.register('test', filter2); - f.execSync('test', {}, { - args: [1, 2] - }); + f.execSync( + 'test', + {}, + { + args: [1, 2] + } + ); filter1.calledOnce.should.be.true; filter2.calledOnce.should.be.true; @@ -280,7 +292,7 @@ describe('Filter', () => { it('execSync() - context', () => { const f = new Filter(); - const ctx = {foo: 1, bar: 2}; + const ctx = { foo: 1, bar: 2 }; const filter1 = sinon.spy(function(data) { this.should.eql(ctx); @@ -293,7 +305,7 @@ describe('Filter', () => { f.register('test', filter1); f.register('test', filter2); - f.execSync('test', {}, {context: ctx}); + f.execSync('test', {}, { context: ctx }); filter1.calledOnce.should.be.true; filter2.calledOnce.should.be.true; }); diff --git a/test/scripts/extend/migrator.js b/test/scripts/extend/migrator.js index a00a341945..6462c95f66 100644 --- a/test/scripts/extend/migrator.js +++ b/test/scripts/extend/migrator.js @@ -34,7 +34,7 @@ describe('Migrator', () => { const d = new Migrator(); d.register('test', (args, callback) => { - args.should.eql({foo: 'bar'}); + args.should.eql({ foo: 'bar' }); callback(null, 'foo'); }); @@ -49,7 +49,7 @@ describe('Migrator', () => { const d = new Migrator(); d.register('test', args => { - args.should.eql({foo: 'bar'}); + args.should.eql({ foo: 'bar' }); return 'foo'; }); diff --git a/test/scripts/extend/tag.js b/test/scripts/extend/tag.js index 2481ea96b8..99dbee3eed 100644 --- a/test/scripts/extend/tag.js +++ b/test/scripts/extend/tag.js @@ -12,15 +12,19 @@ describe('Tag', () => { tag.register('test', (args, content) => args.join(' ')); - return tag.render('{% test foo.bar | abcdef > fn(a, b, c) < fn() %}').then(result => { - result.should.eql('foo.bar | abcdef > fn(a, b, c) < fn()'); - }); + return tag + .render('{% test foo.bar | abcdef > fn(a, b, c) < fn() %}') + .then(result => { + result.should.eql('foo.bar | abcdef > fn(a, b, c) < fn()'); + }); }); it('register() - async', () => { const tag = new Tag(); - tag.register('test', (args, content) => Promise.resolve(args.join(' ')), {async: true}); + tag.register('test', (args, content) => Promise.resolve(args.join(' ')), { + async: true + }); return tag.render('{% test foo bar %}').then(result => { result.should.eql('foo bar'); @@ -30,13 +34,15 @@ describe('Tag', () => { it('register() - block', () => { const tag = new Tag(); - tag.register('test', (args, content) => args.join(' ') + ' ' + content, true); + tag.register( + 'test', + (args, content) => args.join(' ') + ' ' + content, + true + ); - const str = [ - '{% test foo bar %}', - 'test content', - '{% endtest %}' - ].join('\n'); + const str = ['{% test foo bar %}', 'test content', '{% endtest %}'].join( + '\n' + ); return tag.render(str).then(result => { result.should.eql('foo bar test content'); @@ -46,13 +52,15 @@ describe('Tag', () => { it('register() - async block', () => { const tag = new Tag(); - tag.register('test', (args, content) => Promise.resolve(args.join(' ') + ' ' + content), {ends: true, async: true}); + tag.register( + 'test', + (args, content) => Promise.resolve(args.join(' ') + ' ' + content), + { ends: true, async: true } + ); - const str = [ - '{% test foo bar %}', - 'test content', - '{% endtest %}' - ].join('\n'); + const str = ['{% test foo bar %}', 'test content', '{% endtest %}'].join( + '\n' + ); return tag.render(str).then(result => { result.should.eql('foo bar test content'); @@ -85,10 +93,17 @@ describe('Tag', () => { it('register() - nested async / async test', () => { const tag = new Tag(); - tag.register('test', (args, content) => content, {ends: true, async: true}); - tag.register('async', (args, content) => { - return Promise.resolve(args.join(' ') + ' ' + content); - }, {ends: true, async: true}); + tag.register('test', (args, content) => content, { + ends: true, + async: true + }); + tag.register( + 'async', + (args, content) => { + return Promise.resolve(args.join(' ') + ' ' + content); + }, + { ends: true, async: true } + ); const str = [ '{% test %}', @@ -110,11 +125,7 @@ describe('Tag', () => { tag.register('test', (args, content) => content, true); - const str = [ - '{% test %}', - ' test content', - '{% endtest %}' - ].join('\n'); + const str = ['{% test %}', ' test content', '{% endtest %}'].join('\n'); return tag.render(str).then(result => { result.should.eql('test content'); @@ -124,9 +135,13 @@ describe('Tag', () => { it('register() - async callback', () => { const tag = new Tag(); - tag.register('test', (args, content, callback) => { - callback(null, args.join(' ')); - }, {async: true}); + tag.register( + 'test', + (args, content, callback) => { + callback(null, args.join(' ')); + }, + { async: true } + ); return tag.render('{% test foo bar %}').then(result => { result.should.eql('foo bar'); @@ -168,7 +183,7 @@ describe('Tag', () => { return this.foo; }); - return tag.render('{% test %}', {foo: 'bar'}).then(result => { + return tag.render('{% test %}', { foo: 'bar' }).then(result => { result.should.eql('bar'); }); }); diff --git a/test/scripts/extend/tag_errors.js b/test/scripts/extend/tag_errors.js index 3322332c2a..c3d2b67d7d 100644 --- a/test/scripts/extend/tag_errors.js +++ b/test/scripts/extend/tag_errors.js @@ -18,13 +18,10 @@ describe('Tag Errors', () => { it('unknown tag', () => { const tag = new Tag(); - const body = [ - '{% abc %}', - ' content', - '{% endabc %}' - ].join('\n'); + const body = ['{% abc %}', ' content', '{% endabc %}'].join('\n'); - return tag.render(body) + return tag + .render(body) .then(result => { console.log(result); throw new Error('should return error'); @@ -37,16 +34,12 @@ describe('Tag Errors', () => { it('no closing tag 1', () => { const tag = new Tag(); - tag.register('test', - (args, content) => {}, - { ends: true }); + tag.register('test', (args, content) => {}, { ends: true }); - const body = [ - '{% test %}', - ' content' - ].join('\n'); + const body = ['{% test %}', ' content'].join('\n'); - return tag.render(body) + return tag + .render(body) .then(result => { console.log(result); throw new Error('should return error'); @@ -61,17 +54,12 @@ describe('Tag Errors', () => { it('no closing tag 2', () => { const tag = new Tag(); - tag.register('test', - (args, content) => {}, - { ends: true }); + tag.register('test', (args, content) => {}, { ends: true }); - const body = [ - '{% test %}', - ' content', - '{% test %}' - ].join('\n'); + const body = ['{% test %}', ' content', '{% test %}'].join('\n'); - return tag.render(body) + return tag + .render(body) .then(result => { console.log(result); throw new Error('should return error'); @@ -90,7 +78,8 @@ describe('Tag Errors', () => { '{{docker ps -aq | map docker inspect -f "{{.Name}} {{.Mounts}}"}}
' ].join('\n'); - return tag.render(body) + return tag + .render(body) .then(result => { console.log(result); throw new Error('should return error'); @@ -103,9 +92,7 @@ describe('Tag Errors', () => { it('nested curly braces', () => { const tag = new Tag(); - tag.register('test', - (args, content) => {}, - { ends: true }); + tag.register('test', (args, content) => {}, { ends: true }); const body = [ '{% test %}', @@ -113,7 +100,8 @@ describe('Tag Errors', () => { '{% endtest %}' ].join('\n'); - return tag.render(body) + return tag + .render(body) .then(result => { console.log(result); throw new Error('should return error'); @@ -122,5 +110,4 @@ describe('Tag Errors', () => { assertNunjucksError(err, 2, 'expected variable end'); }); }); - }); diff --git a/test/scripts/filters/backtick_code_block.js b/test/scripts/filters/backtick_code_block.js index 76a70a078f..52bc8b7fb7 100644 --- a/test/scripts/filters/backtick_code_block.js +++ b/test/scripts/filters/backtick_code_block.js @@ -7,16 +7,15 @@ const defaultConfig = require('../../../lib/hexo/default_config'); describe('Backtick code block', () => { const Hexo = require('../../../lib/hexo'); const hexo = new Hexo(); - const codeBlock = require('../../../lib/plugins/filter/before_post_render/backtick_code_block').bind(hexo); + const codeBlock = require('../../../lib/plugins/filter/before_post_render/backtick_code_block').bind( + hexo + ); - const code = [ - 'if (tired && night){', - ' sleep();', - '}' - ].join('\n'); + const code = ['if (tired && night){', ' sleep();', '}'].join('\n'); function highlight(code, options) { - return util.highlight(code, options || {}) + return util + .highlight(code, options || {}) .replace(/{/g, '{') .replace(/}/g, '}'); } @@ -27,13 +26,9 @@ describe('Backtick code block', () => { }); it('disabled', () => { - const content = [ - '``` js', - code, - '```' - ].join('\n'); + const content = ['``` js', code, '```'].join('\n'); - const data = {content}; + const data = { content }; hexo.config.highlight.enable = false; codeBlock(data); @@ -41,13 +36,9 @@ describe('Backtick code block', () => { }); it('with no config (disabled)', () => { - const content = [ - '``` js', - code, - '```' - ].join('\n'); + const content = ['``` js', code, '```'].join('\n'); - const data = {content}; + const data = { content }; const oldConfig = hexo.config.highlight; delete hexo.config.highlight; @@ -60,24 +51,18 @@ describe('Backtick code block', () => { it('default', () => { const data = { - content: [ - '``` js', - code, - '```' - ].join('\n') + content: ['``` js', code, '```'].join('\n') }; codeBlock(data); - data.content.should.eql('' + highlight(code, {lang: 'js'}) + ' '); + data.content.should.eql( + '' + highlight(code, { lang: 'js' }) + ' ' + ); }); it('without language name', () => { const data = { - content: [ - '```', - code, - '```' - ].join('\n') + content: ['```', code, '```'].join('\n') }; const expected = highlight(code); @@ -88,11 +73,7 @@ describe('Backtick code block', () => { it('without language name - ignore tab character', () => { const data = { - content: [ - '``` \t', - code, - '```' - ].join('\n') + content: ['``` \t', code, '```'].join('\n') }; const expected = highlight(code); @@ -103,11 +84,7 @@ describe('Backtick code block', () => { it('title', () => { const data = { - content: [ - '``` js Hello world', - code, - '```' - ].join('\n') + content: ['``` js Hello world', code, '```'].join('\n') }; const expected = highlight(code, { @@ -121,11 +98,7 @@ describe('Backtick code block', () => { it('url', () => { const data = { - content: [ - '``` js Hello world https://hexo.io/', - code, - '```' - ].join('\n') + content: ['``` js Hello world https://hexo.io/', code, '```'].join('\n') }; const expected = highlight(code, { @@ -139,11 +112,9 @@ describe('Backtick code block', () => { it('link text', () => { const data = { - content: [ - '``` js Hello world https://hexo.io/ Hexo', - code, - '```' - ].join('\n') + content: ['``` js Hello world https://hexo.io/ Hexo', code, '```'].join( + '\n' + ) }; const expected = highlight(code, { @@ -156,14 +127,15 @@ describe('Backtick code block', () => { }); it('indent', () => { - const indentCode = code.split('\n').map(line => ' ' + line).join('\n'); + const indentCode = code + .split('\n') + .map(line => ' ' + line) + .join('\n'); const data = { - content: [ - '``` js Hello world https://hexo.io/', - indentCode, - '```' - ].join('\n') + content: ['``` js Hello world https://hexo.io/', indentCode, '```'].join( + '\n' + ) }; const expected = highlight(code, { @@ -179,11 +151,7 @@ describe('Backtick code block', () => { hexo.config.highlight.line_number = false; const data = { - content: [ - '``` js', - code, - '```' - ].join('\n') + content: ['``` js', code, '```'].join('\n') }; const expected = highlight(code, { @@ -200,11 +168,7 @@ describe('Backtick code block', () => { hexo.config.highlight.first_line_number = 'always1'; const data = { - content: [ - '``` js', - code, - '```' - ].join('\n') + content: ['``` js', code, '```'].join('\n') }; const expected = highlight(code, { @@ -221,11 +185,7 @@ describe('Backtick code block', () => { hexo.config.highlight.first_line_number = 'inilne'; const data = { - content: [ - '``` js', - code, - '```' - ].join('\n') + content: ['``` js', code, '```'].join('\n') }; const expected = highlight(code, { @@ -241,11 +201,7 @@ describe('Backtick code block', () => { hexo.config.highlight.line_number = true; const data = { - content: [ - '``` js', - code, - '```' - ].join('\n') + content: ['``` js', code, '```'].join('\n') }; const expected = highlight(code, { @@ -262,11 +218,7 @@ describe('Backtick code block', () => { hexo.config.highlight.first_line_number = 'always1'; const data = { - content: [ - '``` js=', - code, - '```' - ].join('\n') + content: ['``` js=', code, '```'].join('\n') }; const expected = highlight(code, { @@ -284,11 +236,7 @@ describe('Backtick code block', () => { hexo.config.highlight.first_line_number = 'inline'; const data = { - content: [ - '``` js', - code, - '```' - ].join('\n') + content: ['``` js', code, '```'].join('\n') }; const expected = highlight(code, { @@ -306,11 +254,7 @@ describe('Backtick code block', () => { hexo.config.highlight.first_line_number = 'inline'; const data = { - content: [ - '``` js=1', - code, - '```' - ].join('\n') + content: ['``` js=1', code, '```'].join('\n') }; const expected = highlight(code, { @@ -328,11 +272,7 @@ describe('Backtick code block', () => { hexo.config.highlight.first_line_number = 'inline'; const data = { - content: [ - '``` js=2', - code, - '```' - ].join('\n') + content: ['``` js=2', code, '```'].join('\n') }; const expected = highlight(code, { @@ -348,18 +288,10 @@ describe('Backtick code block', () => { it('tab replace', () => { hexo.config.highlight.tab_replace = ' '; - const code = [ - 'if (tired && night){', - '\tsleep();', - '}' - ].join('\n'); + const code = ['if (tired && night){', '\tsleep();', '}'].join('\n'); const data = { - content: [ - '``` js', - code, - '```' - ].join('\n') + content: ['``` js', code, '```'].join('\n') }; const expected = highlight(code, { diff --git a/test/scripts/filters/excerpt.js b/test/scripts/filters/excerpt.js index e3e9efe39c..e2c3f8c07d 100644 --- a/test/scripts/filters/excerpt.js +++ b/test/scripts/filters/excerpt.js @@ -3,14 +3,12 @@ describe('Excerpt', () => { const Hexo = require('../../../lib/hexo'); const hexo = new Hexo(); - const excerpt = require('../../../lib/plugins/filter/after_post_render/excerpt').bind(hexo); + const excerpt = require('../../../lib/plugins/filter/after_post_render/excerpt').bind( + hexo + ); it('without ', () => { - const content = [ - 'foo', - 'bar', - 'baz' - ].join('\n'); + const content = ['foo', 'bar', 'baz'].join('\n'); const data = { content @@ -23,13 +21,13 @@ describe('Excerpt', () => { }); it('with ', () => { - _moreCases().forEach(_test); function _moreCases() { const template = ''; // see: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp#Special_characters_meaning_in_regular_expressions - const spaces = ' \f\n\r\t\v\u00a0\u1680\u2000\u2001\u2002\u2003\u2004\u2005\u2006\u2007\u2008\u2009\u200a\u2028\u2029\u202f\u205f\u3000\ufeff'; + const spaces = + ' \f\n\r\t\v\u00a0\u1680\u2000\u2001\u2002\u2003\u2004\u2005\u2006\u2007\u2008\u2009\u200a\u2028\u2029\u202f\u205f\u3000\ufeff'; const cases = []; let more, lead, tail, s, e; @@ -55,12 +53,7 @@ describe('Excerpt', () => { } function _test(more) { - const content = [ - 'foo', - 'bar', - more, - 'baz' - ].join('\n'); + const content = ['foo', 'bar', more, 'baz'].join('\n'); const data = { content @@ -68,21 +61,13 @@ describe('Excerpt', () => { excerpt(data); - data.content.should.eql([ - 'foo', - 'bar', - '', - 'baz' - ].join('\n')); - - data.excerpt.should.eql([ - 'foo', - 'bar' - ].join('\n')); - - data.more.should.eql([ - 'baz' - ].join('\n')); + data.content.should.eql( + ['foo', 'bar', '', 'baz'].join('\n') + ); + + data.excerpt.should.eql(['foo', 'bar'].join('\n')); + + data.more.should.eql(['baz'].join('\n')); } }); @@ -101,31 +86,17 @@ describe('Excerpt', () => { excerpt(data); - data.content.should.eql([ - 'foo', - '', - 'bar', - '', - 'baz' - ].join('\n')); + data.content.should.eql( + ['foo', '', 'bar', '', 'baz'].join('\n') + ); - data.excerpt.should.eql([ - 'foo' - ].join('\n')); + data.excerpt.should.eql(['foo'].join('\n')); - data.more.should.eql([ - 'bar', - '', - 'baz' - ].join('\n')); + data.more.should.eql(['bar', '', 'baz'].join('\n')); }); it('skip processing if post/page.excerpt is present in the front-matter', () => { - const content = [ - 'foo', - '', - 'bar' - ].join('\n'); + const content = ['foo', '', 'bar'].join('\n'); const data = { content, @@ -134,20 +105,10 @@ describe('Excerpt', () => { excerpt(data); - data.content.should.eql([ - 'foo', - '', - 'bar' - ].join('\n')); + data.content.should.eql(['foo', '', 'bar'].join('\n')); - data.excerpt.should.eql([ - 'baz' - ].join('\n')); + data.excerpt.should.eql(['baz'].join('\n')); - data.more.should.eql([ - 'foo', - '', - 'bar' - ].join('\n')); + data.more.should.eql(['foo', '', 'bar'].join('\n')); }); }); diff --git a/test/scripts/filters/external_link.js b/test/scripts/filters/external_link.js index 1e095d6a82..fe433d5758 100644 --- a/test/scripts/filters/external_link.js +++ b/test/scripts/filters/external_link.js @@ -3,17 +3,17 @@ describe('External link', () => { const Hexo = require('../../../lib/hexo'); const hexo = new Hexo(); - const externalLink = require('../../../lib/plugins/filter/after_post_render/external_link').bind(hexo); + const externalLink = require('../../../lib/plugins/filter/after_post_render/external_link').bind( + hexo + ); hexo.config.external_link = true; hexo.config.url = 'https://example.com'; it('disabled', () => { - const content = 'foo' - + 'Hexo' - + 'bar'; + const content = 'fooHexobar'; - const data = {content}; + const data = { content }; hexo.config.external_link = false; externalLink(data); @@ -46,32 +46,34 @@ describe('External link', () => { 'Example Domain' ].join('\n'); - const data = {content}; + const data = { content }; externalLink(data); - data.content.should.eql([ - '# External link test', - '1. External link', - 'Hexo', - '2. External link with "rel" Attribute', - 'Hexo', - 'Hexo', - 'Hexo', - 'Hexo', - 'Hexo', - 'Hexo', - '3. External link with Other Attributes', - 'Hexo', - 'Hexo', - '4. Internal link', - 'Link', - '5. Ignore links have "target" attribute', - 'Hexo', - '6. Ignore links don\'t have "href" attribute', - 'Anchor', - '7. Ignore links whose hostname is same as config', - 'Example Domain' - ].join('\n')); + data.content.should.eql( + [ + '# External link test', + '1. External link', + 'Hexo', + '2. External link with "rel" Attribute', + 'Hexo', + 'Hexo', + 'Hexo', + 'Hexo', + 'Hexo', + 'Hexo', + '3. External link with Other Attributes', + 'Hexo', + 'Hexo', + '4. Internal link', + 'Link', + '5. Ignore links have "target" attribute', + 'Hexo', + '6. Ignore links don\'t have "href" attribute', + 'Anchor', + '7. Ignore links whose hostname is same as config', + 'Example Domain' + ].join('\n') + ); }); }); diff --git a/test/scripts/filters/i18n_locals.js b/test/scripts/filters/i18n_locals.js index 75fe3ed9f0..fc92812b53 100644 --- a/test/scripts/filters/i18n_locals.js +++ b/test/scripts/filters/i18n_locals.js @@ -3,7 +3,9 @@ describe('i18n locals', () => { const Hexo = require('../../../lib/hexo'); const hexo = new Hexo(); - const i18nFilter = require('../../../lib/plugins/filter/template_locals/i18n').bind(hexo); + const i18nFilter = require('../../../lib/plugins/filter/template_locals/i18n').bind( + hexo + ); const theme = hexo.theme; const i18n = theme.i18n; diff --git a/test/scripts/filters/meta_generator.js b/test/scripts/filters/meta_generator.js index 03814a4e63..42443141be 100644 --- a/test/scripts/filters/meta_generator.js +++ b/test/scripts/filters/meta_generator.js @@ -3,7 +3,9 @@ describe('Meta Generator', () => { const Hexo = require('../../../lib/hexo'); const hexo = new Hexo(); - const metaGenerator = require('../../../lib/plugins/filter/meta_generator').bind(hexo); + const metaGenerator = require('../../../lib/plugins/filter/meta_generator').bind( + hexo + ); const cheerio = require('cheerio'); it('default', () => { @@ -12,7 +14,9 @@ describe('Meta Generator', () => { const $ = cheerio.load(result); $('meta[name="generator"]').length.should.eql(1); - $('meta[name="generator"]').attr('content').should.eql(`Hexo ${hexo.version}`); + $('meta[name="generator"]') + .attr('content') + .should.eql(`Hexo ${hexo.version}`); }); it('disable meta_generator', () => { @@ -25,8 +29,7 @@ describe('Meta Generator', () => { }); it('no duplicate generator tag', () => { - const content = 'Hello {{site.data.foo.name}}
' - }).then(page => { - id = page._id; - return renderPost({foo: {name: 'Hexo'}}); - }).then(() => { - const page = Page.findById(id); - page.content.trim().should.eql('Hello Hexo
'); + }) + .then(page => { + id = page._id; + return renderPost({ foo: { name: 'Hexo' } }); + }) + .then(() => { + const page = Page.findById(id); + page.content.trim().should.eql('Hello Hexo
'); - return page.remove(); - }); + return page.remove(); + }); }); - }); diff --git a/test/scripts/filters/save_database.js b/test/scripts/filters/save_database.js index 641cdfb8b5..20ecbab1e6 100644 --- a/test/scripts/filters/save_database.js +++ b/test/scripts/filters/save_database.js @@ -6,23 +6,29 @@ const Promise = require('bluebird'); describe('Save database', () => { const Hexo = require('../../../lib/hexo'); const hexo = new Hexo(); - const saveDatabase = Promise.method(require('../../../lib/plugins/filter/before_exit/save_database')).bind(hexo); + const saveDatabase = Promise.method( + require('../../../lib/plugins/filter/before_exit/save_database') + ).bind(hexo); const dbPath = hexo.database.options.path; it('default', () => { hexo.env.init = true; - return saveDatabase().then(() => fs.exists(dbPath)).then(exist => { - exist.should.be.true; - return fs.unlink(dbPath); - }); + return saveDatabase() + .then(() => fs.exists(dbPath)) + .then(exist => { + exist.should.be.true; + return fs.unlink(dbPath); + }); }); it('do nothing if hexo is not initialized', () => { hexo.env.init = false; - return saveDatabase().then(() => fs.exists(dbPath)).then(exist => { - exist.should.be.false; - }); + return saveDatabase() + .then(() => fs.exists(dbPath)) + .then(exist => { + exist.should.be.false; + }); }); }); diff --git a/test/scripts/filters/titlecase.js b/test/scripts/filters/titlecase.js index 38e3ae43f0..1cde9251f9 100644 --- a/test/scripts/filters/titlecase.js +++ b/test/scripts/filters/titlecase.js @@ -3,11 +3,13 @@ describe('Titlecase', () => { const Hexo = require('../../../lib/hexo'); const hexo = new Hexo(); - const titlecase = require('../../../lib/plugins/filter/before_post_render/titlecase').bind(hexo); + const titlecase = require('../../../lib/plugins/filter/before_post_render/titlecase').bind( + hexo + ); it('disabled', () => { const title = 'Today is a good day'; - const data = {title}; + const data = { title }; hexo.config.titlecase = false; titlecase(data); @@ -16,7 +18,7 @@ describe('Titlecase', () => { it('enabled', () => { const title = 'Today is a good day'; - const data = {title}; + const data = { title }; hexo.config.titlecase = true; titlecase(data); diff --git a/test/scripts/generators/asset.js b/test/scripts/generators/asset.js index fa1f75cc8c..3e1de8a0c8 100644 --- a/test/scripts/generators/asset.js +++ b/test/scripts/generators/asset.js @@ -7,7 +7,7 @@ const testUtil = require('../../util'); describe('asset', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'asset_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'asset_test'), { silent: true }); const generator = require('../../../lib/plugins/generator/asset').bind(hexo); const Asset = hexo.model('Asset'); @@ -27,19 +27,19 @@ describe('asset', () => { const content = 'foo: bar'; return Promise.all([ - Asset.insert({_id: path, path}), + Asset.insert({ _id: path, path }), fs.writeFile(source, content) - ]).then(() => generator(hexo.locals)).then(data => { - data[0].path.should.eql('test.json'); - data[0].data.modified.should.be.true; - - return data[0].data.data().then(result => { - result.should.eql('{"foo":"bar"}'); - }); - }).then(() => Promise.all([ - Asset.removeById(path), - fs.unlink(source) - ])); + ]) + .then(() => generator(hexo.locals)) + .then(data => { + data[0].path.should.eql('test.json'); + data[0].data.modified.should.be.true; + + return data[0].data.data().then(result => { + result.should.eql('{"foo":"bar"}'); + }); + }) + .then(() => Promise.all([Asset.removeById(path), fs.unlink(source)])); }); it('not renderable', () => { @@ -48,17 +48,17 @@ describe('asset', () => { const content = 'test content'; return Promise.all([ - Asset.insert({_id: path, path}), + Asset.insert({ _id: path, path }), fs.writeFile(source, content) - ]).then(() => generator(hexo.locals)).then(data => { - data[0].path.should.eql(path); - data[0].data.modified.should.be.true; - - return checkStream(data[0].data.data(), content); - }).then(() => Promise.all([ - Asset.removeById(path), - fs.unlink(source) - ])); + ]) + .then(() => generator(hexo.locals)) + .then(data => { + data[0].path.should.eql(path); + data[0].data.modified.should.be.true; + + return checkStream(data[0].data.data(), content); + }) + .then(() => Promise.all([Asset.removeById(path), fs.unlink(source)])); }); it('skip render', () => { @@ -67,17 +67,17 @@ describe('asset', () => { const content = 'foo: bar'; return Promise.all([ - Asset.insert({_id: path, path, renderable: false}), + Asset.insert({ _id: path, path, renderable: false }), fs.writeFile(source, content) - ]).then(() => generator(hexo.locals)).then(data => { - data[0].path.should.eql('test.yml'); - data[0].data.modified.should.be.true; - - return checkStream(data[0].data.data(), content); - }).then(() => Promise.all([ - Asset.removeById(path), - fs.unlink(source) - ])); + ]) + .then(() => generator(hexo.locals)) + .then(data => { + data[0].path.should.eql('test.yml'); + data[0].data.modified.should.be.true; + + return checkStream(data[0].data.data(), content); + }) + .then(() => Promise.all([Asset.removeById(path), fs.unlink(source)])); }); it('remove assets which does not exist', () => { @@ -86,25 +86,26 @@ describe('asset', () => { return Asset.insert({ _id: path, path - }).then(() => generator(hexo.locals)).then(() => { - should.not.exist(Asset.findById(path)); - }); + }) + .then(() => generator(hexo.locals)) + .then(() => { + should.not.exist(Asset.findById(path)); + }); }); - it('don\'t remove extension name', () => { + it("don't remove extension name", () => { const path = 'test.min.js'; const source = pathFn.join(hexo.base_dir, path); return Promise.all([ - Asset.insert({_id: path, path}), + Asset.insert({ _id: path, path }), fs.writeFile(source, '') - ]).then(() => generator(hexo.locals)).then(data => { - data[0].path.should.eql('test.min.js'); + ]) + .then(() => generator(hexo.locals)) + .then(data => { + data[0].path.should.eql('test.min.js'); - return Promise.all([ - Asset.removeById(path), - fs.unlink(source) - ]); - }); + return Promise.all([Asset.removeById(path), fs.unlink(source)]); + }); }); }); diff --git a/test/scripts/generators/page.js b/test/scripts/generators/page.js index 27105df15c..7447706733 100644 --- a/test/scripts/generators/page.js +++ b/test/scripts/generators/page.js @@ -4,49 +4,63 @@ const Promise = require('bluebird'); describe('page', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(__dirname, {silent: true}); + const hexo = new Hexo(__dirname, { silent: true }); const Page = hexo.model('Page'); - const generator = Promise.method(require('../../../lib/plugins/generator/page').bind(hexo)); + const generator = Promise.method( + require('../../../lib/plugins/generator/page').bind(hexo) + ); function locals() { hexo.locals.invalidate(); return hexo.locals.toObject(); } - it('default layout', () => Page.insert({ - source: 'foo', - path: 'bar' - }).then(page => generator(locals()).then(data => { - page.__page = true; - - data.should.eql([ - { - path: page.path, - layout: ['page', 'post', 'index'], - data: page - } - ]); - - return page.remove(); - }))); - - it('custom layout', () => Page.insert({ - source: 'foo', - path: 'bar', - layout: 'photo' - }).then(page => generator(locals()).then(data => { - data[0].layout.should.eql(['photo', 'page', 'post', 'index']); - - return page.remove(); - }))); + it('default layout', () => + Page.insert({ + source: 'foo', + path: 'bar' + }).then(page => + generator(locals()).then(data => { + page.__page = true; - [false, 'false', 'off'].forEach(layout => { - it('layout = ' + JSON.stringify(layout), () => Page.insert({ + data.should.eql([ + { + path: page.path, + layout: ['page', 'post', 'index'], + data: page + } + ]); + + return page.remove(); + }) + )); + + it('custom layout', () => + Page.insert({ source: 'foo', path: 'bar', - layout - }).then(page => generator(locals()).then(data => { - should.not.exist(data[0].layout); - }).finally(() => page.remove()))); + layout: 'photo' + }).then(page => + generator(locals()).then(data => { + data[0].layout.should.eql(['photo', 'page', 'post', 'index']); + + return page.remove(); + }) + )); + + [false, 'false', 'off'].forEach(layout => { + it('layout = ' + JSON.stringify(layout), () => + Page.insert({ + source: 'foo', + path: 'bar', + layout + }).then(page => + generator(locals()) + .then(data => { + should.not.exist(data[0].layout); + }) + .finally(() => page.remove()) + ) + ); }); }); diff --git a/test/scripts/generators/post.js b/test/scripts/generators/post.js index 6a0bf67fbc..b8d4ae6b43 100644 --- a/test/scripts/generators/post.js +++ b/test/scripts/generators/post.js @@ -4,9 +4,11 @@ const Promise = require('bluebird'); describe('post', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(__dirname, {silent: true}); + const hexo = new Hexo(__dirname, { silent: true }); const Post = hexo.model('Post'); - const generator = Promise.method(require('../../../lib/plugins/generator/post').bind(hexo)); + const generator = Promise.method( + require('../../../lib/plugins/generator/post').bind(hexo) + ); hexo.config.permalink = ':title/'; @@ -17,53 +19,69 @@ describe('post', () => { before(() => hexo.init()); - it('default layout', () => Post.insert({ - source: 'foo', - slug: 'bar' - }).then(post => generator(locals()).then(data => { - post.__post = true; + it('default layout', () => + Post.insert({ + source: 'foo', + slug: 'bar' + }).then(post => + generator(locals()).then(data => { + post.__post = true; - data.should.eql([ - { - path: 'bar/', - layout: ['post', 'page', 'index'], - data: post - } - ]); + data.should.eql([ + { + path: 'bar/', + layout: ['post', 'page', 'index'], + data: post + } + ]); - return post.remove(); - }))); + return post.remove(); + }) + )); - it('custom layout', () => Post.insert({ - source: 'foo', - slug: 'bar', - layout: 'photo' - }).then(post => generator(locals()).then(data => { - data[0].layout.should.eql(['photo', 'post', 'page', 'index']); + it('custom layout', () => + Post.insert({ + source: 'foo', + slug: 'bar', + layout: 'photo' + }).then(post => + generator(locals()).then(data => { + data[0].layout.should.eql(['photo', 'post', 'page', 'index']); - return post.remove(); - }))); + return post.remove(); + }) + )); - it('layout disabled', () => Post.insert({ - source: 'foo', - slug: 'bar', - layout: false - }).then(post => generator(locals()).then(data => { - should.not.exist(data[0].layout); + it('layout disabled', () => + Post.insert({ + source: 'foo', + slug: 'bar', + layout: false + }).then(post => + generator(locals()).then(data => { + should.not.exist(data[0].layout); - return post.remove(); - }))); + return post.remove(); + }) + )); - it('prev/next post', () => Post.insert([ - {source: 'foo', slug: 'foo', date: 1e8}, - {source: 'bar', slug: 'bar', date: 1e8 + 1}, - {source: 'baz', slug: 'baz', date: 1e8 - 1} - ]).then(posts => generator(locals()).then(data => { - should.not.exist(data[0].data.prev); - data[0].data.next._id.should.eq(posts[0]._id); - data[1].data.prev._id.should.eq(posts[1]._id); - data[1].data.next._id.should.eq(posts[2]._id); - data[2].data.prev._id.should.eq(posts[0]._id); - should.not.exist(data[2].data.next); - }).thenReturn(posts)).map(post => post.remove())); + it('prev/next post', () => + Post.insert([ + { source: 'foo', slug: 'foo', date: 1e8 }, + { source: 'bar', slug: 'bar', date: 1e8 + 1 }, + { source: 'baz', slug: 'baz', date: 1e8 - 1 } + ]) + .then(posts => + generator(locals()) + .then(data => { + should.not.exist(data[0].data.prev); + data[0].data.next._id.should.eq(posts[0]._id); + data[1].data.prev._id.should.eq(posts[1]._id); + data[1].data.next._id.should.eq(posts[2]._id); + data[2].data.prev._id.should.eq(posts[0]._id); + should.not.exist(data[2].data.next); + }) + .thenReturn(posts) + ) + .map(post => post.remove())); }); diff --git a/test/scripts/helpers/css.js b/test/scripts/helpers/css.js index f9c8ba4b5f..f808239c7e 100644 --- a/test/scripts/helpers/css.js +++ b/test/scripts/helpers/css.js @@ -30,7 +30,12 @@ describe('css', () => { }); it('an array', () => { - assertResult(css(['foo', 'bar', 'baz']), '/foo.css', '/bar.css', '/baz.css'); + assertResult( + css(['foo', 'bar', 'baz']), + '/foo.css', + '/bar.css', + '/baz.css' + ); }); it('multiple strings', () => { @@ -38,10 +43,20 @@ describe('css', () => { }); it('multiple arrays', () => { - assertResult(css(['foo', 'bar'], ['baz']), '/foo.css', '/bar.css', '/baz.css'); + assertResult( + css(['foo', 'bar'], ['baz']), + '/foo.css', + '/bar.css', + '/baz.css' + ); }); it('mixed', () => { - assertResult(css(['foo', 'bar'], 'baz'), '/foo.css', '/bar.css', '/baz.css'); + assertResult( + css(['foo', 'bar'], 'baz'), + '/foo.css', + '/bar.css', + '/baz.css' + ); }); }); diff --git a/test/scripts/helpers/date.js b/test/scripts/helpers/date.js index d45bed0298..c741104ffb 100644 --- a/test/scripts/helpers/date.js +++ b/test/scripts/helpers/date.js @@ -42,17 +42,29 @@ describe('date', () => { // page.lang ctx.page.lang = 'zh-tw'; - date(Date.now(), 'MMM D YYYY').should.eql(moment().locale('zh-tw').format('MMM D YYYY')); + date(Date.now(), 'MMM D YYYY').should.eql( + moment() + .locale('zh-tw') + .format('MMM D YYYY') + ); ctx.page.lang = ''; // config.language ctx.config.language = 'ja'; - date(Date.now(), 'MMM D YYYY').should.eql(moment().locale('ja').format('MMM D YYYY')); + date(Date.now(), 'MMM D YYYY').should.eql( + moment() + .locale('ja') + .format('MMM D YYYY') + ); ctx.config.language = ''; // timezone ctx.config.timezone = 'UTC'; - date(Date.now(), 'LLL').should.eql(moment().tz('UTC').format('LLL')); + date(Date.now(), 'LLL').should.eql( + moment() + .tz('UTC') + .format('LLL') + ); ctx.config.timezone = ''; }); @@ -118,17 +130,29 @@ describe('date', () => { // page.lang ctx.page.lang = 'zh-tw'; - time(Date.now(), 'A H:mm').should.eql(moment().locale('zh-tw').format('A H:mm')); + time(Date.now(), 'A H:mm').should.eql( + moment() + .locale('zh-tw') + .format('A H:mm') + ); ctx.page.lang = ''; // config.language ctx.config.language = 'ja'; - time(Date.now(), 'A H:mm').should.eql(moment().locale('ja').format('A H:mm')); + time(Date.now(), 'A H:mm').should.eql( + moment() + .locale('ja') + .format('A H:mm') + ); ctx.config.language = ''; // timezone ctx.config.timezone = 'UTC'; - time().should.eql(moment().tz('UTC').format(hexo.config.time_format)); + time().should.eql( + moment() + .tz('UTC') + .format(hexo.config.time_format) + ); ctx.config.timezone = ''; }); @@ -141,7 +165,8 @@ describe('date', () => { }; const fullDate = dateHelper.full_date.bind(ctx); - const fullDateFormat = hexo.config.date_format + ' ' + hexo.config.time_format; + const fullDateFormat = + hexo.config.date_format + ' ' + hexo.config.time_format; // now fullDate().should.eql(moment().format(fullDateFormat)); @@ -152,25 +177,41 @@ describe('date', () => { // date fullDate(new Date()).should.eql(moment().format(fullDateFormat)); - fullDate(new Date(), 'MMM-D-YYYY').should.eql(moment().format('MMM-D-YYYY')); + fullDate(new Date(), 'MMM-D-YYYY').should.eql( + moment().format('MMM-D-YYYY') + ); // number fullDate(Date.now()).should.eql(moment().format(fullDateFormat)); - fullDate(Date.now(), 'MMM-D-YYYY').should.eql(moment().format('MMM-D-YYYY')); + fullDate(Date.now(), 'MMM-D-YYYY').should.eql( + moment().format('MMM-D-YYYY') + ); // page.lang ctx.page.lang = 'zh-tw'; - fullDate(Date.now(), 'LLL').should.eql(moment().locale('zh-tw').format('LLL')); + fullDate(Date.now(), 'LLL').should.eql( + moment() + .locale('zh-tw') + .format('LLL') + ); ctx.page.lang = ''; // config.language ctx.config.language = 'ja'; - fullDate(Date.now(), 'LLL').should.eql(moment().locale('ja').format('LLL')); + fullDate(Date.now(), 'LLL').should.eql( + moment() + .locale('ja') + .format('LLL') + ); ctx.config.language = ''; // timezone ctx.config.timezone = 'UTC'; - fullDate().should.eql(moment().tz('UTC').format(fullDateFormat)); + fullDate().should.eql( + moment() + .tz('UTC') + .format(fullDateFormat) + ); ctx.config.timezone = ''; }); @@ -186,7 +227,13 @@ describe('date', () => { function result(date, format) { date = date || new Date(); format = format || hexo.config.date_format; - return ''; + return ( + '' + ); } function check(date, format) { @@ -211,17 +258,41 @@ describe('date', () => { // page.lang ctx.page.lang = 'zh-tw'; - timeTag(Date.now(), 'LLL').should.eql(''); + timeTag(Date.now(), 'LLL').should.eql( + '' + ); ctx.page.lang = ''; // config.language ctx.config.language = 'ja'; - timeTag(Date.now(), 'LLL').should.eql(''); + timeTag(Date.now(), 'LLL').should.eql( + '' + ); ctx.config.language = ''; // timezone ctx.config.timezone = 'UTC'; - timeTag(Date.now(), 'LLL').should.eql(''); + timeTag(Date.now(), 'LLL').should.eql( + '' + ); ctx.config.timezone = ''; }); }); diff --git a/test/scripts/helpers/debug.js b/test/scripts/helpers/debug.js index 5bc8b8e4fd..fb6041d974 100644 --- a/test/scripts/helpers/debug.js +++ b/test/scripts/helpers/debug.js @@ -20,9 +20,15 @@ describe('debug', () => { }); it('inspect deep object', () => { - const obj = { baz: { thud: 'narf', dur: { foo: 'bar', baz: { bang: 'zoom' } } } }; - debug.inspectObject(obj, {depth: 2}).should.not.eql(inspect(obj, {depth: 5})); - debug.inspectObject(obj, {depth: 5}).should.eql(inspect(obj, {depth: 5})); + const obj = { + baz: { thud: 'narf', dur: { foo: 'bar', baz: { bang: 'zoom' } } } + }; + debug + .inspectObject(obj, { depth: 2 }) + .should.not.eql(inspect(obj, { depth: 5 })); + debug + .inspectObject(obj, { depth: 5 }) + .should.eql(inspect(obj, { depth: 5 })); }); it('log should print to console', () => { diff --git a/test/scripts/helpers/favicon_tag.js b/test/scripts/helpers/favicon_tag.js index 17b5f6dc67..af5422af99 100644 --- a/test/scripts/helpers/favicon_tag.js +++ b/test/scripts/helpers/favicon_tag.js @@ -13,6 +13,8 @@ describe('favicon_tag', () => { const favicon = require('../../../lib/plugins/helper/favicon_tag').bind(ctx); it('path', () => { - favicon('favicon.ico').should.eql(''); + favicon('favicon.ico').should.eql( + '' + ); }); }); diff --git a/test/scripts/helpers/feed_tag.js b/test/scripts/helpers/feed_tag.js index 5d2b7b2f7c..06981b0310 100644 --- a/test/scripts/helpers/feed_tag.js +++ b/test/scripts/helpers/feed_tag.js @@ -13,14 +13,20 @@ describe('feed_tag', () => { const feed = require('../../../lib/plugins/helper/feed_tag').bind(ctx); it('path', () => { - feed('atom.xml').should.eql(''); + feed('atom.xml').should.eql( + '' + ); }); it('title', () => { - feed('atom.xml', {title: 'RSS Feed'}).should.eql(''); + feed('atom.xml', { title: 'RSS Feed' }).should.eql( + '' + ); }); it('type', () => { - feed('rss.xml', {type: 'rss'}).should.eql(''); + feed('rss.xml', { type: 'rss' }).should.eql( + '' + ); }); }); diff --git a/test/scripts/helpers/fragment_cache.js b/test/scripts/helpers/fragment_cache.js index 5a816cb0cf..bfc508b909 100644 --- a/test/scripts/helpers/fragment_cache.js +++ b/test/scripts/helpers/fragment_cache.js @@ -3,13 +3,13 @@ describe('fragment_cache', () => { const fragment_cache = require('../../../lib/plugins/helper/fragment_cache')(); - fragment_cache.call({cache: true}, 'foo', () => 123); + fragment_cache.call({ cache: true }, 'foo', () => 123); it('cache enabled', () => { - fragment_cache.call({cache: true}, 'foo').should.eql(123); + fragment_cache.call({ cache: true }, 'foo').should.eql(123); }); it('cache disabled', () => { - fragment_cache.call({cache: false}, 'foo', () => 456).should.eql(456); + fragment_cache.call({ cache: false }, 'foo', () => 456).should.eql(456); }); }); diff --git a/test/scripts/helpers/gravatar.js b/test/scripts/helpers/gravatar.js index 8b577e97af..bf5541617f 100644 --- a/test/scripts/helpers/gravatar.js +++ b/test/scripts/helpers/gravatar.js @@ -6,7 +6,10 @@ describe('gravatar', () => { const gravatar = require('../../../lib/plugins/helper/gravatar'); function md5(str) { - return crypto.createHash('md5').update(str).digest('hex'); + return crypto + .createHash('md5') + .update(str) + .digest('hex'); } const email = 'abc@abc.com'; @@ -17,7 +20,9 @@ describe('gravatar', () => { }); it('size', () => { - gravatar(email, 100).should.eql('https://www.gravatar.com/avatar/' + hash + '?s=100'); + gravatar(email, 100).should.eql( + 'https://www.gravatar.com/avatar/' + hash + '?s=100' + ); }); it('options', () => { @@ -25,6 +30,8 @@ describe('gravatar', () => { s: 200, r: 'pg', d: 'mm' - }).should.eql('https://www.gravatar.com/avatar/' + hash + '?s=200&r=pg&d=mm'); + }).should.eql( + 'https://www.gravatar.com/avatar/' + hash + '?s=200&r=pg&d=mm' + ); }); }); diff --git a/test/scripts/helpers/image_tag.js b/test/scripts/helpers/image_tag.js index 293c8e020f..60bd6d218b 100644 --- a/test/scripts/helpers/image_tag.js +++ b/test/scripts/helpers/image_tag.js @@ -13,21 +13,26 @@ describe('image_tag', () => { const img = require('../../../lib/plugins/helper/image_tag').bind(ctx); it('path', () => { - img('https://hexo.io/image.jpg').should.eql(''); + img('https://hexo.io/image.jpg').should.eql( + '' + ); }); it('class (string)', () => { - img('https://hexo.io/image.jpg', {class: 'foo'}) - .should.eql(''); + img('https://hexo.io/image.jpg', { class: 'foo' }).should.eql( + '' + ); }); it('class (array)', () => { - img('https://hexo.io/image.jpg', {class: ['foo', 'bar']}) - .should.eql(''); + img('https://hexo.io/image.jpg', { class: ['foo', 'bar'] }).should.eql( + '' + ); }); it('alt', () => { - img('https://hexo.io/image.jpg', {alt: 'Image caption'}) - .should.eql(''); + img('https://hexo.io/image.jpg', { alt: 'Image caption' }).should.eql( + '' + ); }); }); diff --git a/test/scripts/helpers/is.js b/test/scripts/helpers/is.js index 404fa4dfee..4da7a713b8 100644 --- a/test/scripts/helpers/is.js +++ b/test/scripts/helpers/is.js @@ -6,73 +6,96 @@ describe('is', () => { const is = require('../../../lib/plugins/helper/is'); it('is_current', () => { - is.current.call({path: 'index.html', config: hexo.config}).should.be.true; - is.current.call({path: 'tags/index.html', config: hexo.config}).should.be.false; - is.current.call({path: 'index.html', config: hexo.config}, '/').should.be.true; - is.current.call({path: 'index.html', config: hexo.config}, 'index.html').should.be.true; - is.current.call({path: 'tags/index.html', config: hexo.config}, '/').should.be.false; - is.current.call({path: 'tags/index.html', config: hexo.config}, '/index.html').should.be.false; - is.current.call({path: 'index.html', config: hexo.config}, '/', true).should.be.true; - is.current.call({path: 'index.html', config: hexo.config}, '/index.html', true).should.be.true; - is.current.call({path: 'foo/bar', config: hexo.config}, 'foo', true).should.be.false; - is.current.call({path: 'foo/bar', config: hexo.config}, 'foo').should.be.true; - is.current.call({path: 'foo/bar', config: hexo.config}, 'foo/bar').should.be.true; - is.current.call({path: 'foo/bar', config: hexo.config}, 'foo/baz').should.be.false; + is.current.call({ path: 'index.html', config: hexo.config }).should.be.true; + is.current.call({ path: 'tags/index.html', config: hexo.config }).should.be + .false; + is.current.call({ path: 'index.html', config: hexo.config }, '/').should.be + .true; + is.current.call({ path: 'index.html', config: hexo.config }, 'index.html') + .should.be.true; + is.current.call({ path: 'tags/index.html', config: hexo.config }, '/') + .should.be.false; + is.current.call( + { path: 'tags/index.html', config: hexo.config }, + '/index.html' + ).should.be.false; + is.current.call({ path: 'index.html', config: hexo.config }, '/', true) + .should.be.true; + is.current.call( + { path: 'index.html', config: hexo.config }, + '/index.html', + true + ).should.be.true; + is.current.call({ path: 'foo/bar', config: hexo.config }, 'foo', true) + .should.be.false; + is.current.call({ path: 'foo/bar', config: hexo.config }, 'foo').should.be + .true; + is.current.call({ path: 'foo/bar', config: hexo.config }, 'foo/bar').should + .be.true; + is.current.call({ path: 'foo/bar', config: hexo.config }, 'foo/baz').should + .be.false; }); it('is_home', () => { - is.home.call({page: {__index: true}}).should.be.true; - is.home.call({page: {}}).should.be.false; + is.home.call({ page: { __index: true } }).should.be.true; + is.home.call({ page: {} }).should.be.false; }); it('is_post', () => { - is.post.call({page: {__post: true}}).should.be.true; - is.post.call({page: {}}).should.be.false; + is.post.call({ page: { __post: true } }).should.be.true; + is.post.call({ page: {} }).should.be.false; }); it('is_page', () => { - is.page.call({page: {__page: true}}).should.be.true; - is.page.call({page: {}}).should.be.false; + is.page.call({ page: { __page: true } }).should.be.true; + is.page.call({ page: {} }).should.be.false; }); it('is_archive', () => { - is.archive.call({page: {}}).should.be.false; - is.archive.call({page: {archive: true}}).should.be.true; - is.archive.call({page: {archive: false}}).should.be.false; + is.archive.call({ page: {} }).should.be.false; + is.archive.call({ page: { archive: true } }).should.be.true; + is.archive.call({ page: { archive: false } }).should.be.false; }); it('is_year', () => { - is.year.call({page: {}}).should.be.false; - is.year.call({page: {archive: true}}).should.be.false; - is.year.call({page: {archive: true, year: 2014}}).should.be.true; - is.year.call({page: {archive: true, year: 2014}}, 2014).should.be.true; - is.year.call({page: {archive: true, year: 2014}}, 2015).should.be.false; - is.year.call({page: {archive: true, year: 2014, month: 10}}).should.be.true; + is.year.call({ page: {} }).should.be.false; + is.year.call({ page: { archive: true } }).should.be.false; + is.year.call({ page: { archive: true, year: 2014 } }).should.be.true; + is.year.call({ page: { archive: true, year: 2014 } }, 2014).should.be.true; + is.year.call({ page: { archive: true, year: 2014 } }, 2015).should.be.false; + is.year.call({ page: { archive: true, year: 2014, month: 10 } }).should.be + .true; }); it('is_month', () => { - is.month.call({page: {}}).should.be.false; - is.month.call({page: {archive: true}}).should.be.false; - is.month.call({page: {archive: true, year: 2014}}).should.be.false; - is.month.call({page: {archive: true, year: 2014, month: 10}}).should.be.true; - is.month.call({page: {archive: true, year: 2014, month: 10}}, 2014, 10).should.be.true; - is.month.call({page: {archive: true, year: 2014, month: 10}}, 2015, 10).should.be.false; - is.month.call({page: {archive: true, year: 2014, month: 10}}, 2014, 12).should.be.false; - is.month.call({page: {archive: true, year: 2014, month: 10}}, 10).should.be.true; - is.month.call({page: {archive: true, year: 2014, month: 10}}, 12).should.be.false; + is.month.call({ page: {} }).should.be.false; + is.month.call({ page: { archive: true } }).should.be.false; + is.month.call({ page: { archive: true, year: 2014 } }).should.be.false; + is.month.call({ page: { archive: true, year: 2014, month: 10 } }).should.be + .true; + is.month.call({ page: { archive: true, year: 2014, month: 10 } }, 2014, 10) + .should.be.true; + is.month.call({ page: { archive: true, year: 2014, month: 10 } }, 2015, 10) + .should.be.false; + is.month.call({ page: { archive: true, year: 2014, month: 10 } }, 2014, 12) + .should.be.false; + is.month.call({ page: { archive: true, year: 2014, month: 10 } }, 10).should + .be.true; + is.month.call({ page: { archive: true, year: 2014, month: 10 } }, 12).should + .be.false; }); it('is_category', () => { - is.category.call({page: {category: 'foo'}}).should.be.true; - is.category.call({page: {category: 'foo'}}, 'foo').should.be.true; - is.category.call({page: {category: 'foo'}}, 'bar').should.be.false; - is.category.call({page: {}}).should.be.false; + is.category.call({ page: { category: 'foo' } }).should.be.true; + is.category.call({ page: { category: 'foo' } }, 'foo').should.be.true; + is.category.call({ page: { category: 'foo' } }, 'bar').should.be.false; + is.category.call({ page: {} }).should.be.false; }); it('is_tag', () => { - is.tag.call({page: {tag: 'foo'}}).should.be.true; - is.tag.call({page: {tag: 'foo'}}, 'foo').should.be.true; - is.tag.call({page: {tag: 'foo'}}, 'bar').should.be.false; - is.tag.call({page: {}}).should.be.false; + is.tag.call({ page: { tag: 'foo' } }).should.be.true; + is.tag.call({ page: { tag: 'foo' } }, 'foo').should.be.true; + is.tag.call({ page: { tag: 'foo' } }, 'bar').should.be.false; + is.tag.call({ page: {} }).should.be.false; }); }); diff --git a/test/scripts/helpers/link_to.js b/test/scripts/helpers/link_to.js index 0f8f3c7c82..ba80b6c164 100644 --- a/test/scripts/helpers/link_to.js +++ b/test/scripts/helpers/link_to.js @@ -13,35 +13,44 @@ describe('link_to', () => { const linkTo = require('../../../lib/plugins/helper/link_to').bind(ctx); it('path', () => { - linkTo('https://hexo.io/').should.eql('hexo.io'); + linkTo('https://hexo.io/').should.eql( + 'hexo.io' + ); }); it('title', () => { - linkTo('https://hexo.io/', 'Hexo').should.eql('Hexo'); + linkTo('https://hexo.io/', 'Hexo').should.eql( + 'Hexo' + ); }); it('external (boolean)', () => { - linkTo('https://hexo.io/', 'Hexo', true) - .should.eql('Hexo'); + linkTo('https://hexo.io/', 'Hexo', true).should.eql( + 'Hexo' + ); }); it('external (object)', () => { - linkTo('https://hexo.io/', 'Hexo', {external: true}) - .should.eql('Hexo'); + linkTo('https://hexo.io/', 'Hexo', { external: true }).should.eql( + 'Hexo' + ); }); it('class (string)', () => { - linkTo('https://hexo.io/', 'Hexo', {class: 'foo'}) - .should.eql('Hexo'); + linkTo('https://hexo.io/', 'Hexo', { class: 'foo' }).should.eql( + 'Hexo' + ); }); it('class (array)', () => { - linkTo('https://hexo.io/', 'Hexo', {class: ['foo', 'bar']}) - .should.eql('Hexo'); + linkTo('https://hexo.io/', 'Hexo', { class: ['foo', 'bar'] }).should.eql( + 'Hexo' + ); }); it('id', () => { - linkTo('https://hexo.io/', 'Hexo', {id: 'foo'}) - .should.eql('Hexo'); + linkTo('https://hexo.io/', 'Hexo', { id: 'foo' }).should.eql( + 'Hexo' + ); }); }); diff --git a/test/scripts/helpers/list_archives.js b/test/scripts/helpers/list_archives.js index d9c8990b9e..46bc9506c3 100644 --- a/test/scripts/helpers/list_archives.js +++ b/test/scripts/helpers/list_archives.js @@ -12,32 +12,43 @@ describe('list_archives', () => { ctx.url_for = require('../../../lib/plugins/helper/url_for').bind(ctx); - const listArchives = require('../../../lib/plugins/helper/list_archives').bind(ctx); + const listArchives = require('../../../lib/plugins/helper/list_archives').bind( + ctx + ); function resetLocals() { hexo.locals.invalidate(); ctx.site = hexo.locals.toObject(); } - before(() => hexo.init().then(() => Post.insert([ - {source: 'foo', slug: 'foo', date: new Date(2014, 1, 2)}, - {source: 'bar', slug: 'bar', date: new Date(2013, 5, 6)}, - {source: 'baz', slug: 'baz', date: new Date(2013, 9, 10)}, - {source: 'boo', slug: 'boo', date: new Date(2013, 5, 8)} - ])).then(() => { - resetLocals(); - })); + before(() => + hexo + .init() + .then(() => + Post.insert([ + { source: 'foo', slug: 'foo', date: new Date(2014, 1, 2) }, + { source: 'bar', slug: 'bar', date: new Date(2013, 5, 6) }, + { source: 'baz', slug: 'baz', date: new Date(2013, 9, 10) }, + { source: 'boo', slug: 'boo', date: new Date(2013, 5, 8) } + ]) + ) + .then(() => { + resetLocals(); + }) + ); it('default', () => { const result = listArchives(); - result.should.eql([ - '', - '
' - ].join('')); + result.should.eql( + [ + '- February 20141
', - '- October 20131
', - '- June 20132
', - '', + '
' + ].join('') + ); }); it('type: yearly', () => { @@ -45,12 +56,14 @@ describe('list_archives', () => { type: 'yearly' }); - result.should.eql([ - '' - ].join('')); + result.should.eql( + [ + '' + ].join('') + ); }); it('format', () => { @@ -58,13 +71,15 @@ describe('list_archives', () => { format: 'YYYY/M' }); - result.should.eql([ - '' - ].join('')); + result.should.eql( + [ + '' + ].join('') + ); }); it('style: false', () => { @@ -72,11 +87,13 @@ describe('list_archives', () => { style: false }); - result.should.eql([ - 'February 20141', - 'October 20131', - 'June 20132' - ].join(', ')); + result.should.eql( + [ + 'February 20141', + 'October 20131', + 'June 20132' + ].join(', ') + ); }); it('show_count', () => { @@ -84,13 +101,15 @@ describe('list_archives', () => { show_count: false }); - result.should.eql([ - '- February 20141
', + '- October 20131
', + '- June 20132
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- February 2014
', - '- October 2013
', - '- June 2013
', - '', + '
' + ].join('') + ); }); it('order', () => { @@ -98,13 +117,15 @@ describe('list_archives', () => { order: 1 }); - result.should.eql([ - '- February 2014
', + '- October 2013
', + '- June 2013
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- June 20132
', - '- October 20131
', - '- February 20141
', - '', + '
' + ].join('') + ); }); it('transform', () => { @@ -114,13 +135,15 @@ describe('list_archives', () => { } }); - result.should.eql([ - '- June 20132
', + '- October 20131
', + '- February 20141
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- FEBRUARY 20141
', - '- OCTOBER 20131
', - '- JUNE 20132
', - '', + '
' + ].join('') + ); }); it('separator', () => { @@ -129,11 +152,13 @@ describe('list_archives', () => { separator: '' }); - result.should.eql([ - 'February 20141', - 'October 20131', - 'June 20132' - ].join('')); + result.should.eql( + [ + 'February 20141', + 'October 20131', + 'June 20132' + ].join('') + ); }); it('class', () => { @@ -141,13 +166,15 @@ describe('list_archives', () => { class: 'test' }); - result.should.eql([ - '- FEBRUARY 20141
', + '- OCTOBER 20131
', + '- JUNE 20132
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- February 20141
', - '- October 20131
', - '- June 20132
', - '', + '
' + ].join('') + ); }); it('page.lang', () => { @@ -155,13 +182,15 @@ describe('list_archives', () => { const result = listArchives(); ctx.page.lang = ''; - result.should.eql([ - '' - ].join('')); + result.should.eql( + [ + '' + ].join('') + ); }); it('config.language', () => { @@ -169,13 +198,15 @@ describe('list_archives', () => { const result = listArchives(); ctx.config.language = ''; - result.should.eql([ - '- February 20141
', + '- October 20131
', + '- June 20132
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- Februar 20141
', - '- Oktober 20131
', - '- Juni 20132
', - '', + '
' + ].join('') + ); }); it('timezone'); diff --git a/test/scripts/helpers/list_categories.js b/test/scripts/helpers/list_categories.js index f145eac462..119924dda7 100644 --- a/test/scripts/helpers/list_categories.js +++ b/test/scripts/helpers/list_categories.js @@ -14,67 +14,82 @@ describe('list_categories', () => { ctx.url_for = require('../../../lib/plugins/helper/url_for').bind(ctx); - const listCategories = require('../../../lib/plugins/helper/list_categories').bind(ctx); - - before(() => hexo.init().then(() => Post.insert([ - {source: 'foo', slug: 'foo'}, - {source: 'bar', slug: 'bar'}, - {source: 'baz', slug: 'baz'}, - {source: 'boo', slug: 'boo'}, - {source: 'bat', slug: 'bat'} - ])).then(posts => Promise.each([ - ['baz'], - ['baz', 'bar'], - ['foo'], - ['baz'], - ['bat', ['baz', 'bar']] - ], (cats, i) => posts[i].setCategories(cats))).then(() => { - hexo.locals.invalidate(); - ctx.site = hexo.locals.toObject(); - ctx.page = ctx.site.posts.data[1]; - })); + const listCategories = require('../../../lib/plugins/helper/list_categories').bind( + ctx + ); + + before(() => + hexo + .init() + .then(() => + Post.insert([ + { source: 'foo', slug: 'foo' }, + { source: 'bar', slug: 'bar' }, + { source: 'baz', slug: 'baz' }, + { source: 'boo', slug: 'boo' }, + { source: 'bat', slug: 'bat' } + ]) + ) + .then(posts => + Promise.each( + [['baz'], ['baz', 'bar'], ['foo'], ['baz'], ['bat', ['baz', 'bar']]], + (cats, i) => posts[i].setCategories(cats) + ) + ) + .then(() => { + hexo.locals.invalidate(); + ctx.site = hexo.locals.toObject(); + ctx.page = ctx.site.posts.data[1]; + }) + ); it('default', () => { const result = listCategories(); - result.should.eql([ - '- Februar 20141
', + '- Oktober 20131
', + '- Juni 20132
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- ', - 'bat1', - '
', - '- ', - 'baz4', - '
', - '', - '
', - '- ', - 'bar2', - '
', - '- ', - 'foo1', - '
', - '', + '
' + ].join('') + ); }); it('specified collection', () => { - const result = listCategories(Category.find({ - parent: {$exists: false} - })); - - result.should.eql([ - '' - ].join('')); + const result = listCategories( + Category.find({ + parent: { $exists: false } + }) + ); + + result.should.eql( + [ + '' + ].join('') + ); }); it('style: false', () => { @@ -82,12 +97,14 @@ describe('list_categories', () => { style: false }); - result.should.eql([ - 'bat1', - 'baz4', - 'bar2', - 'foo1' - ].join(', ')); + result.should.eql( + [ + 'bat1', + 'baz4', + 'bar2', + 'foo1' + ].join(', ') + ); }); it('show_count: false', () => { @@ -95,24 +112,26 @@ describe('list_categories', () => { show_count: false }); - result.should.eql([ - '- ', + 'bat1', + '
', + '- ', + 'baz4', + '
', + '', + '
', + '- ', + 'bar2', + '
', + '- ', + 'foo1', + '
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- ', - 'bat', - '
', - '- ', - 'baz', - '
', - '', - '
', - '- ', - 'bar', - '
', - '- ', - 'foo', - '
', - '', + '
' + ].join('') + ); }); it('class', () => { @@ -120,24 +139,26 @@ describe('list_categories', () => { class: 'test' }); - result.should.eql([ - '- ', + 'bat', + '
', + '- ', + 'baz', + '
', + '', + '
', + '- ', + 'bar', + '
', + '- ', + 'foo', + '
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- ', - 'bat1', - '
', - '- ', - 'baz4', - '
', - '', - '
', - '- ', - 'bar2', - '
', - '- ', - 'foo1', - '
', - '', + '
' + ].join('') + ); }); it('depth', () => { @@ -145,19 +166,21 @@ describe('list_categories', () => { depth: 1 }); - result.should.eql([ - '' - ].join('')); + result.should.eql( + [ + '' + ].join('') + ); }); it('orderby', () => { @@ -165,24 +188,26 @@ describe('list_categories', () => { orderby: 'length' }); - result.should.eql([ - '- ', + 'bat1', + '
', + '- ', + 'baz4', + '
', + '', + '
', + '- ', + 'bar2', + '
', + '- ', + 'foo1', + '
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- ', - 'foo1', - '
', - '- ', - 'bat1', - '
', - '- ', - 'baz4', - '
', - '', - '
', - '- ', - 'bar2', - '
', - '', + '
' + ].join('') + ); }); it('order', () => { @@ -190,24 +215,26 @@ describe('list_categories', () => { order: -1 }); - result.should.eql([ - '- ', + 'foo1', + '
', + '- ', + 'bat1', + '
', + '- ', + 'baz4', + '
', + '', + '
', + '- ', + 'bar2', + '
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- ', - 'foo1', - '
', - '- ', - 'baz4', - '
', - '', - '
', - '- ', - 'bar2', - '
', - '- ', - 'bat1', - '
', - '', + '
' + ].join('') + ); }); it('transform', () => { @@ -217,24 +244,26 @@ describe('list_categories', () => { } }); - result.should.eql([ - '- ', + 'foo1', + '
', + '- ', + 'baz4', + '
', + '', + '
', + '- ', + 'bar2', + '
', + '- ', + 'bat1', + '
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- ', - 'BAT1', - '
', - '- ', - 'BAZ4', - '
', - '', - '
', - '- ', - 'BAR2', - '
', - '- ', - 'FOO1', - '
', - '', + '
' + ].join('') + ); }); it('separator (blank)', () => { @@ -243,12 +272,14 @@ describe('list_categories', () => { separator: '' }); - result.should.eql([ - 'bat1', - 'baz4', - 'bar2', - 'foo1' - ].join('')); + result.should.eql( + [ + 'bat1', + 'baz4', + 'bar2', + 'foo1' + ].join('') + ); }); it('separator (non-blank)', () => { @@ -257,12 +288,14 @@ describe('list_categories', () => { separator: '|' }); - result.should.eql([ - 'bat1|', - 'baz4|', - 'bar2|', - 'foo1' - ].join('')); + result.should.eql( + [ + 'bat1|', + 'baz4|', + 'bar2|', + 'foo1' + ].join('') + ); }); it('children-indicator', () => { @@ -270,24 +303,26 @@ describe('list_categories', () => { children_indicator: 'has-children' }); - result.should.eql([ - '- ', + 'BAT1', + '
', + '- ', + 'BAZ4', + '
', + '', + '
', + '- ', + 'BAR2', + '
', + '- ', + 'FOO1', + '
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- ', - 'bat1', - '
', - '- ', - 'baz4', - '
', - '', - '
', - '- ', - 'bar2', - '
', - '- ', - 'foo1', - '
', - '', + '
' + ].join('') + ); }); it('show-current', () => { @@ -295,23 +330,25 @@ describe('list_categories', () => { show_current: true }); - result.should.eql([ - '- ', + 'bat1', + '
', + '- ', + 'baz4', + '
', + '', + '
', + '- ', + 'bar2', + '
', + '- ', + 'foo1', + '
', + '', - '
' - ].join('')); + result.should.eql( + [ + '- ', - 'bat1', - '
', - '- ', - 'baz4', - '
', - '', - '
', - '- ', - 'bar2', - '
', - '- ', - 'foo1', - '
', - '', + '
' + ].join('') + ); }); }); diff --git a/test/scripts/helpers/list_posts.js b/test/scripts/helpers/list_posts.js index 032c1a7133..18882a69b1 100644 --- a/test/scripts/helpers/list_posts.js +++ b/test/scripts/helpers/list_posts.js @@ -15,37 +15,50 @@ describe('list_posts', () => { hexo.config.permalink = ':title/'; - before(() => hexo.init().then(() => Post.insert([ - {source: 'foo', slug: 'foo', title: 'Its', date: 1e8}, - {source: 'bar', slug: 'bar', title: 'Chemistry', date: 1e8 + 1}, - {source: 'baz', slug: 'baz', title: 'Bitch', date: 1e8 - 1} - ])).then(() => { - hexo.locals.invalidate(); - ctx.site = hexo.locals.toObject(); - })); + before(() => + hexo + .init() + .then(() => + Post.insert([ + { source: 'foo', slug: 'foo', title: 'Its', date: 1e8 }, + { source: 'bar', slug: 'bar', title: 'Chemistry', date: 1e8 + 1 }, + { source: 'baz', slug: 'baz', title: 'Bitch', date: 1e8 - 1 } + ]) + ) + .then(() => { + hexo.locals.invalidate(); + ctx.site = hexo.locals.toObject(); + }) + ); it('default', () => { const result = listPosts(); - result.should.eql([ - '' - ].join('')); + result.should.eql( + [ + '' + ].join('') + ); }); it('specified collection', () => { - const result = listPosts(Post.find({ - title: 'Its' - })); - - result.should.eql([ - '- ', + 'bat1', + '
', + '- ', + 'baz4', + '
', + '', + '
', + '- ', + 'bar2', + '
', + '- ', + 'foo1', + '
', + '', - '
' - ].join('')); + const result = listPosts( + Post.find({ + title: 'Its' + }) + ); + + result.should.eql( + [ + '- Its
', - '', + '
' + ].join('') + ); }); it('style: false', () => { @@ -53,11 +66,13 @@ describe('list_posts', () => { style: false }); - result.should.eql([ - 'Chemistry', - 'Its', - 'Bitch' - ].join(', ')); + result.should.eql( + [ + 'Chemistry', + 'Its', + 'Bitch' + ].join(', ') + ); }); it('orderby', () => { @@ -65,13 +80,15 @@ describe('list_posts', () => { orderby: 'title' }); - result.should.eql([ - '' - ].join('')); + result.should.eql( + [ + '' + ].join('') + ); }); it('order', () => { @@ -79,13 +96,15 @@ describe('list_posts', () => { order: 1 }); - result.should.eql([ - '' - ].join('')); + result.should.eql( + [ + '' + ].join('') + ); }); it('class', () => { @@ -93,13 +112,15 @@ describe('list_posts', () => { class: 'test' }); - result.should.eql([ - '' - ].join('')); + result.should.eql( + [ + '' + ].join('') + ); }); it('transform', () => { @@ -109,13 +130,15 @@ describe('list_posts', () => { } }); - result.should.eql([ - '' - ].join('')); + result.should.eql( + [ + '' + ].join('') + ); }); it('separator', () => { @@ -124,11 +147,13 @@ describe('list_posts', () => { separator: '' }); - result.should.eql([ - 'Chemistry', - 'Its', - 'Bitch' - ].join('')); + result.should.eql( + [ + 'Chemistry', + 'Its', + 'Bitch' + ].join('') + ); }); it('amount', () => { @@ -136,11 +161,13 @@ describe('list_posts', () => { amount: 2 }); - result.should.eql([ - '' - ].join('')); + result.should.eql( + [ + '' + ].join('') + ); }); }); diff --git a/test/scripts/helpers/list_tags.js b/test/scripts/helpers/list_tags.js index ccfce8a39b..605e1eb6e8 100644 --- a/test/scripts/helpers/list_tags.js +++ b/test/scripts/helpers/list_tags.js @@ -16,45 +16,59 @@ describe('list_tags', () => { const listTags = require('../../../lib/plugins/helper/list_tags').bind(ctx); - before(() => hexo.init().then(() => Post.insert([ - {source: 'foo', slug: 'foo'}, - {source: 'bar', slug: 'bar'}, - {source: 'baz', slug: 'baz'}, - {source: 'boo', slug: 'boo'} - ])).then(posts => // TODO: Warehouse needs to add a mutex lock when writing data to avoid data sync problem - Promise.each([ - ['foo'], - ['baz'], - ['baz'], - ['bar'] - ], (tags, i) => posts[i].setTags(tags))).then(() => { - hexo.locals.invalidate(); - ctx.site = hexo.locals.toObject(); - })); + before(() => + hexo + .init() + .then(() => + Post.insert([ + { source: 'foo', slug: 'foo' }, + { source: 'bar', slug: 'bar' }, + { source: 'baz', slug: 'baz' }, + { source: 'boo', slug: 'boo' } + ]) + ) + .then(( + posts // TODO: Warehouse needs to add a mutex lock when writing data to avoid data sync problem + ) => + Promise.each([['foo'], ['baz'], ['baz'], ['bar']], (tags, i) => + posts[i].setTags(tags) + ) + ) + .then(() => { + hexo.locals.invalidate(); + ctx.site = hexo.locals.toObject(); + }) + ); it('default', () => { const result = listTags(); - result.should.eql([ - ' ' - ].join('')); + result.should.eql( + [ + ' ' + ].join('') + ); }); it('specified collection', () => { - const result = listTags(Tag.find({ - name: /^b/ - })); - - result.should.eql([ - ' ' - ].join('')); + const result = listTags( + Tag.find({ + name: /^b/ + }) + ); + + result.should.eql( + [ + ' ' + ].join('') + ); }); it('style: false', () => { @@ -62,11 +76,13 @@ describe('list_tags', () => { style: false }); - result.should.eql([ - 'bar1', - 'baz2', - 'foo1' - ].join(', ')); + result.should.eql( + [ + 'bar1', + 'baz2', + 'foo1' + ].join(', ') + ); }); it('show_count: false', () => { @@ -74,13 +90,15 @@ describe('list_tags', () => { show_count: false }); - result.should.eql([ - ' ' - ].join('')); + result.should.eql( + [ + ' ' + ].join('') + ); }); it('class', () => { @@ -88,13 +106,15 @@ describe('list_tags', () => { class: 'test' }); - result.should.eql([ - '' - ].join('')); + result.should.eql( + [ + '' + ].join('') + ); }); it('orderby', () => { @@ -102,13 +122,15 @@ describe('list_tags', () => { orderby: 'length' }); - result.should.eql([ - ' ' - ].join('')); + result.should.eql( + [ + ' ' + ].join('') + ); }); it('order', () => { @@ -116,13 +138,15 @@ describe('list_tags', () => { order: -1 }); - result.should.eql([ - ' ' - ].join('')); + result.should.eql( + [ + ' ' + ].join('') + ); }); it('transform', () => { @@ -132,13 +156,15 @@ describe('list_tags', () => { } }); - result.should.eql([ - ' ' - ].join('')); + result.should.eql( + [ + ' ' + ].join('') + ); }); it('separator', () => { @@ -147,11 +173,13 @@ describe('list_tags', () => { separator: '' }); - result.should.eql([ - 'bar1', - 'baz2', - 'foo1' - ].join('')); + result.should.eql( + [ + 'bar1', + 'baz2', + 'foo1' + ].join('') + ); }); it('amount', () => { @@ -159,11 +187,13 @@ describe('list_tags', () => { amount: 2 }); - result.should.eql([ - ' ' - ].join('')); + result.should.eql( + [ + ' ' + ].join('') + ); }); }); diff --git a/test/scripts/helpers/mail_to.js b/test/scripts/helpers/mail_to.js index 73bb24c4ee..3b29293a4d 100644 --- a/test/scripts/helpers/mail_to.js +++ b/test/scripts/helpers/mail_to.js @@ -15,67 +15,92 @@ describe('mail_to', () => { const mailto = require('../../../lib/plugins/helper/mail_to').bind(ctx); it('path', () => { - mailto('abc@example.com').should.eql('abc@example.com'); + mailto('abc@example.com').should.eql( + 'abc@example.com' + ); }); it('text', () => { - mailto('abc@example.com', 'Email').should.eql('Email'); + mailto('abc@example.com', 'Email').should.eql( + 'Email' + ); }); it('subject', () => { - mailto('abc@example.com', 'Email', {subject: 'Hello'}) - .should.eql('Email'); + mailto('abc@example.com', 'Email', { subject: 'Hello' }).should.eql( + 'Email' + ); }); it('cc (string)', () => { - const data = {cc: 'abc@abc.com'}; + const data = { cc: 'abc@abc.com' }; const querystring = qs.stringify(data); - mailto('abc@example.com', 'Email', {cc: 'abc@abc.com'}) - .should.eql('Email'); + mailto('abc@example.com', 'Email', { cc: 'abc@abc.com' }).should.eql( + 'Email' + ); }); it('cc (array)', () => { - const data = {cc: 'abc@abc.com,bcd@bcd.com'}; + const data = { cc: 'abc@abc.com,bcd@bcd.com' }; const querystring = qs.stringify(data); - mailto('abc@example.com', 'Email', {cc: ['abc@abc.com', 'bcd@bcd.com']}) - .should.eql('Email'); + mailto('abc@example.com', 'Email', { + cc: ['abc@abc.com', 'bcd@bcd.com'] + }).should.eql( + 'Email' + ); }); it('bcc (string)', () => { - const data = {bcc: 'abc@abc.com'}; + const data = { bcc: 'abc@abc.com' }; const querystring = qs.stringify(data); - mailto('abc@example.com', 'Email', {bcc: 'abc@abc.com'}) - .should.eql('Email'); + mailto('abc@example.com', 'Email', { bcc: 'abc@abc.com' }).should.eql( + 'Email' + ); }); it('bcc (array)', () => { - const data = {bcc: 'abc@abc.com,bcd@bcd.com'}; + const data = { bcc: 'abc@abc.com,bcd@bcd.com' }; const querystring = qs.stringify(data); - mailto('abc@example.com', 'Email', {bcc: ['abc@abc.com', 'bcd@bcd.com']}) - .should.eql('Email'); + mailto('abc@example.com', 'Email', { + bcc: ['abc@abc.com', 'bcd@bcd.com'] + }).should.eql( + 'Email' + ); }); it('body', () => { - mailto('abc@example.com', 'Email', {body: 'Hello'}) - .should.eql('Email'); + mailto('abc@example.com', 'Email', { body: 'Hello' }).should.eql( + 'Email' + ); }); it('class (string)', () => { - mailto('abc@example.com', 'Email', {class: 'foo'}) - .should.eql('Email'); + mailto('abc@example.com', 'Email', { class: 'foo' }).should.eql( + 'Email' + ); }); it('class (array)', () => { - mailto('abc@example.com', 'Email', {class: ['foo', 'bar']}) - .should.eql('Email'); + mailto('abc@example.com', 'Email', { class: ['foo', 'bar'] }).should.eql( + 'Email' + ); }); it('id', () => { - mailto('abc@example.com', 'Email', {id: 'foo'}) - .should.eql('Email'); + mailto('abc@example.com', 'Email', { id: 'foo' }).should.eql( + 'Email' + ); }); }); diff --git a/test/scripts/helpers/markdown.js b/test/scripts/helpers/markdown.js index 524c64b7fe..e6dd0f88ed 100644 --- a/test/scripts/helpers/markdown.js +++ b/test/scripts/helpers/markdown.js @@ -10,9 +10,15 @@ describe('markdown', () => { const markdown = require('../../../lib/plugins/helper/markdown').bind(ctx); - before(() => hexo.init().then(() => hexo.loadPlugin(require.resolve('hexo-renderer-marked')))); + before(() => + hexo + .init() + .then(() => hexo.loadPlugin(require.resolve('hexo-renderer-marked'))) + ); it('default', () => { - markdown('123456 **bold** and *italic*').should.eql('- Its
', + '123456 bold and italic
\n'); + markdown('123456 **bold** and *italic*').should.eql( + '123456 bold and italic
\n' + ); }); }); diff --git a/test/scripts/helpers/number_format.js b/test/scripts/helpers/number_format.js index 1ae0f95f96..87da664cd7 100644 --- a/test/scripts/helpers/number_format.js +++ b/test/scripts/helpers/number_format.js @@ -8,19 +8,19 @@ describe('number_format', () => { }); it('precision', () => { - numberFormat(1234.567, {precision: false}).should.eql('1,234.567'); - numberFormat(1234.567, {precision: 0}).should.eql('1,234'); - numberFormat(1234.567, {precision: 1}).should.eql('1,234.6'); - numberFormat(1234.567, {precision: 2}).should.eql('1,234.57'); - numberFormat(1234.567, {precision: 3}).should.eql('1,234.567'); - numberFormat(1234.567, {precision: 4}).should.eql('1,234.5670'); + numberFormat(1234.567, { precision: false }).should.eql('1,234.567'); + numberFormat(1234.567, { precision: 0 }).should.eql('1,234'); + numberFormat(1234.567, { precision: 1 }).should.eql('1,234.6'); + numberFormat(1234.567, { precision: 2 }).should.eql('1,234.57'); + numberFormat(1234.567, { precision: 3 }).should.eql('1,234.567'); + numberFormat(1234.567, { precision: 4 }).should.eql('1,234.5670'); }); it('delimiter', () => { - numberFormat(1234.567, {delimiter: ' '}).should.eql('1 234.567'); + numberFormat(1234.567, { delimiter: ' ' }).should.eql('1 234.567'); }); it('separator', () => { - numberFormat(1234.567, {separator: '*'}).should.eql('1,234*567'); + numberFormat(1234.567, { separator: '*' }).should.eql('1,234*567'); }); }); diff --git a/test/scripts/helpers/open_graph.js b/test/scripts/helpers/open_graph.js index 18faaab6e9..15651c00b0 100644 --- a/test/scripts/helpers/open_graph.js +++ b/test/scripts/helpers/open_graph.js @@ -23,57 +23,75 @@ describe('open_graph', () => { Post.insert({ source: 'foo.md', slug: 'bar' - }).then(post => post.setTags(['optimize', 'web']) - .thenReturn(Post.findById(post._id))).then(post => { - openGraph.call({ - page: post, - config: hexo.config, - is_post: isPost - }).should.eql([ - meta({name: 'keywords', content: 'optimize,web'}), - meta({property: 'og:type', content: 'website'}), - meta({property: 'og:title', content: hexo.config.title}), - meta({property: 'og:url'}), - meta({property: 'og:site_name', content: hexo.config.title}), - meta({property: 'og:locale', content: 'en'}), - meta({property: 'og:updated_time', content: post.updated.toISOString()}), - meta({name: 'twitter:card', content: 'summary'}) - ].join('\n')); - - return Post.removeById(post._id); - }); + }) + .then(post => + post.setTags(['optimize', 'web']).thenReturn(Post.findById(post._id)) + ) + .then(post => { + openGraph + .call({ + page: post, + config: hexo.config, + is_post: isPost + }) + .should.eql( + [ + meta({ name: 'keywords', content: 'optimize,web' }), + meta({ property: 'og:type', content: 'website' }), + meta({ property: 'og:title', content: hexo.config.title }), + meta({ property: 'og:url' }), + meta({ property: 'og:site_name', content: hexo.config.title }), + meta({ property: 'og:locale', content: 'en' }), + meta({ + property: 'og:updated_time', + content: post.updated.toISOString() + }), + meta({ name: 'twitter:card', content: 'summary' }) + ].join('\n') + ); + + return Post.removeById(post._id); + }); }); it('title - page', () => { const ctx = { - page: {title: 'Hello world'}, + page: { title: 'Hello world' }, config: hexo.config, is_post: isPost }; const result = openGraph.call(ctx); - result.should.contain(meta({property: 'og:title', content: ctx.page.title})); + result.should.contain( + meta({ property: 'og:title', content: ctx.page.title }) + ); }); it('title - options', () => { - const result = openGraph.call({ - page: {title: 'Hello world'}, - config: hexo.config, - is_post: isPost - }, {title: 'test'}); + const result = openGraph.call( + { + page: { title: 'Hello world' }, + config: hexo.config, + is_post: isPost + }, + { title: 'test' } + ); - result.should.contain(meta({property: 'og:title', content: 'test'})); + result.should.contain(meta({ property: 'og:title', content: 'test' })); }); it('type - options', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {type: 'photo'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { type: 'photo' } + ); - result.should.contain(meta({property: 'og:type', content: 'photo'})); + result.should.contain(meta({ property: 'og:type', content: 'photo' })); }); it('type - is_post', () => { @@ -85,7 +103,7 @@ describe('open_graph', () => { } }); - result.should.contain(meta({property: 'og:type', content: 'article'})); + result.should.contain(meta({ property: 'og:type', content: 'article' })); }); it('url - context', () => { @@ -98,18 +116,23 @@ describe('open_graph', () => { const result = openGraph.call(ctx); - result.should.contain(meta({property: 'og:url', content: ctx.url})); + result.should.contain(meta({ property: 'og:url', content: ctx.url })); }); it('url - options', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost, - url: 'https://hexo.io/foo' - }, {url: 'https://hexo.io/bar'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost, + url: 'https://hexo.io/foo' + }, + { url: 'https://hexo.io/bar' } + ); - result.should.contain(meta({property: 'og:url', content: 'https://hexo.io/bar'})); + result.should.contain( + meta({ property: 'og:url', content: 'https://hexo.io/bar' }) + ); }); it('images - content', () => { @@ -126,7 +149,9 @@ describe('open_graph', () => { is_post: isPost }); - result.should.contain(meta({property: 'og:image', content: 'https://hexo.io/test.jpg'})); + result.should.contain( + meta({ property: 'og:image', content: 'https://hexo.io/test.jpg' }) + ); }); it('images - string', () => { @@ -138,28 +163,29 @@ describe('open_graph', () => { is_post: isPost }); - result.should.contain(meta({property: 'og:image', content: 'https://hexo.io/test.jpg'})); + result.should.contain( + meta({ property: 'og:image', content: 'https://hexo.io/test.jpg' }) + ); }); it('images - array', () => { const result = openGraph.call({ page: { - photos: [ - 'https://hexo.io/foo.jpg', - 'https://hexo.io/bar.jpg' - ] + photos: ['https://hexo.io/foo.jpg', 'https://hexo.io/bar.jpg'] }, config: hexo.config, is_post: isPost }); - result.should.contain([ - meta({property: 'og:image', content: 'https://hexo.io/foo.jpg'}), - meta({property: 'og:image', content: 'https://hexo.io/bar.jpg'}) - ].join('\n')); + result.should.contain( + [ + meta({ property: 'og:image', content: 'https://hexo.io/foo.jpg' }), + meta({ property: 'og:image', content: 'https://hexo.io/bar.jpg' }) + ].join('\n') + ); }); - it('images - don\'t pollute context', () => { + it("images - don't pollute context", () => { const ctx = { page: { content: [ @@ -179,43 +205,63 @@ describe('open_graph', () => { }); it('images - options.image', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {image: 'https://hexo.io/test.jpg'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { image: 'https://hexo.io/test.jpg' } + ); - result.should.contain(meta({property: 'og:image', content: 'https://hexo.io/test.jpg'})); + result.should.contain( + meta({ property: 'og:image', content: 'https://hexo.io/test.jpg' }) + ); }); it('images - options.images', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {images: 'https://hexo.io/test.jpg'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { images: 'https://hexo.io/test.jpg' } + ); - result.should.contain(meta({property: 'og:image', content: 'https://hexo.io/test.jpg'})); + result.should.contain( + meta({ property: 'og:image', content: 'https://hexo.io/test.jpg' }) + ); }); it('images - prepend config.url to the path (without prefixing /)', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {images: 'test.jpg'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { images: 'test.jpg' } + ); - result.should.contain(meta({property: 'og:image', content: hexo.config.url + '/test.jpg'})); + result.should.contain( + meta({ property: 'og:image', content: hexo.config.url + '/test.jpg' }) + ); }); it('images - prepend config.url to the path (with prefixing /)', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {images: '/test.jpg'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { images: '/test.jpg' } + ); - result.should.contain(meta({property: 'og:image', content: hexo.config.url + '/test.jpg'})); + result.should.contain( + meta({ property: 'og:image', content: hexo.config.url + '/test.jpg' }) + ); }); it('images - resolve relative path when site is hosted in subdirectory', () => { @@ -225,76 +271,99 @@ describe('open_graph', () => { config.root = 'blog'; const postUrl = urlFn.resolve(config.url, '/foo/bar/index.html'); - const result = openGraph.call({ - page: {}, - config, - is_post: isPost, - url: postUrl - }, {images: 'test.jpg'}); + const result = openGraph.call( + { + page: {}, + config, + is_post: isPost, + url: postUrl + }, + { images: 'test.jpg' } + ); - result.should.contain(meta({property: 'og:image', content: urlFn.resolve(config.url, '/foo/bar/test.jpg')})); + result.should.contain( + meta({ + property: 'og:image', + content: urlFn.resolve(config.url, '/foo/bar/test.jpg') + }) + ); }); it('site_name - options', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {site_name: 'foo'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { site_name: 'foo' } + ); - result.should.contain(meta({property: 'og:site_name', content: 'foo'})); + result.should.contain(meta({ property: 'og:site_name', content: 'foo' })); }); it('description - page', () => { const ctx = { - page: {description: 'test'}, + page: { description: 'test' }, config: hexo.config, is_post: isPost }; const result = openGraph.call(ctx); - result.should.contain(meta({name: 'description', content: ctx.page.description})); - result.should.contain(meta({property: 'og:description', content: ctx.page.description})); + result.should.contain( + meta({ name: 'description', content: ctx.page.description }) + ); + result.should.contain( + meta({ property: 'og:description', content: ctx.page.description }) + ); }); it('description - options', () => { const ctx = { - page: {description: 'test'}, + page: { description: 'test' }, config: hexo.config, is_post: isPost }; - const result = openGraph.call(ctx, {description: 'foo'}); + const result = openGraph.call(ctx, { description: 'foo' }); - result.should.contain(meta({name: 'description', content: 'foo'})); - result.should.contain(meta({property: 'og:description', content: 'foo'})); + result.should.contain(meta({ name: 'description', content: 'foo' })); + result.should.contain(meta({ property: 'og:description', content: 'foo' })); }); it('description - excerpt', () => { const ctx = { - page: {excerpt: 'test'}, + page: { excerpt: 'test' }, config: hexo.config, is_post: isPost }; const result = openGraph.call(ctx); - result.should.contain(meta({name: 'description', content: ctx.page.excerpt})); - result.should.contain(meta({property: 'og:description', content: ctx.page.excerpt})); + result.should.contain( + meta({ name: 'description', content: ctx.page.excerpt }) + ); + result.should.contain( + meta({ property: 'og:description', content: ctx.page.excerpt }) + ); }); it('description - content', () => { const ctx = { - page: {content: 'test'}, + page: { content: 'test' }, config: hexo.config, is_post: isPost }; const result = openGraph.call(ctx); - result.should.contain(meta({name: 'description', content: ctx.page.content})); - result.should.contain(meta({property: 'og:description', content: ctx.page.content})); + result.should.contain( + meta({ name: 'description', content: ctx.page.content }) + ); + result.should.contain( + meta({ property: 'og:description', content: ctx.page.content }) + ); }); it('description - config', () => { @@ -308,15 +377,19 @@ describe('open_graph', () => { const result = openGraph.call(ctx); - result.should.contain(meta({name: 'description', content: hexo.config.description})); - result.should.contain(meta({property: 'og:description', content: hexo.config.description})); + result.should.contain( + meta({ name: 'description', content: hexo.config.description }) + ); + result.should.contain( + meta({ property: 'og:description', content: hexo.config.description }) + ); hexo.config.description = ''; }); it('description - escape', () => { const ctx = { - page: {description: 'Important! Today is "not" \'Xmas\'!'}, + page: { description: 'Important! Today is "not" \'Xmas\'!' }, config: hexo.config, is_post: isPost }; @@ -324,119 +397,170 @@ describe('open_graph', () => { const result = openGraph.call(ctx); const escaped = 'Important! Today is "not" 'Xmas'!'; - result.should.contain(meta({name: 'description', content: escaped})); - result.should.contain(meta({property: 'og:description', content: escaped})); + result.should.contain(meta({ name: 'description', content: escaped })); + result.should.contain( + meta({ property: 'og:description', content: escaped }) + ); }); it('twitter_card - options', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {twitter_card: 'photo'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { twitter_card: 'photo' } + ); - result.should.contain(meta({name: 'twitter:card', content: 'photo'})); + result.should.contain(meta({ name: 'twitter:card', content: 'photo' })); }); it('twitter_id - options (without prefixing @)', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {twitter_id: 'hexojs'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { twitter_id: 'hexojs' } + ); - result.should.contain(meta({name: 'twitter:creator', content: '@hexojs'})); + result.should.contain( + meta({ name: 'twitter:creator', content: '@hexojs' }) + ); }); it('twitter_id - options (with prefixing @)', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {twitter_id: '@hexojs'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { twitter_id: '@hexojs' } + ); - result.should.contain(meta({name: 'twitter:creator', content: '@hexojs'})); + result.should.contain( + meta({ name: 'twitter:creator', content: '@hexojs' }) + ); }); it('twitter_site - options', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {twitter_site: 'Hello'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { twitter_site: 'Hello' } + ); - result.should.contain(meta({name: 'twitter:site', content: 'Hello'})); + result.should.contain(meta({ name: 'twitter:site', content: 'Hello' })); }); it('google_plus - options', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {google_plus: '+123456789'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { google_plus: '+123456789' } + ); - result.should.contain(tag('link', {rel: 'publisher', href: '+123456789'})); + result.should.contain( + tag('link', { rel: 'publisher', href: '+123456789' }) + ); }); it('fb_admins - options', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {fb_admins: '123456789'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { fb_admins: '123456789' } + ); - result.should.contain(meta({property: 'fb:admins', content: '123456789'})); + result.should.contain( + meta({ property: 'fb:admins', content: '123456789' }) + ); }); it('fb_app_id - options', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {fb_app_id: '123456789'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { fb_app_id: '123456789' } + ); - result.should.contain(meta({property: 'fb:app_id', content: '123456789'})); + result.should.contain( + meta({ property: 'fb:app_id', content: '123456789' }) + ); }); it('updated - options', () => { - const result = openGraph.call({ - page: { updated: moment('2016-05-23T21:20:21.372Z') }, - config: {}, - is_post: isPost - }, { }); + const result = openGraph.call( + { + page: { updated: moment('2016-05-23T21:20:21.372Z') }, + config: {}, + is_post: isPost + }, + {} + ); - result.should.contain(meta({property: 'og:updated_time', content: '2016-05-23T21:20:21.372Z'})); + result.should.contain( + meta({ property: 'og:updated_time', content: '2016-05-23T21:20:21.372Z' }) + ); }); it('updated - options - allow overriding og:updated_time', () => { - const result = openGraph.call({ - page: { updated: moment('2016-05-23T21:20:21.372Z') }, - config: {}, - is_post: isPost - }, { updated: moment('2015-04-22T20:19:20.371Z') }); + const result = openGraph.call( + { + page: { updated: moment('2016-05-23T21:20:21.372Z') }, + config: {}, + is_post: isPost + }, + { updated: moment('2015-04-22T20:19:20.371Z') } + ); - result.should.contain(meta({property: 'og:updated_time', content: '2015-04-22T20:19:20.371Z'})); + result.should.contain( + meta({ property: 'og:updated_time', content: '2015-04-22T20:19:20.371Z' }) + ); }); it('updated - options - allow disabling og:updated_time', () => { - const result = openGraph.call({ - page: { updated: moment('2016-05-23T21:20:21.372Z') }, - config: {}, - is_post: isPost - }, { updated: false }); + const result = openGraph.call( + { + page: { updated: moment('2016-05-23T21:20:21.372Z') }, + config: {}, + is_post: isPost + }, + { updated: false } + ); - result.should.not.contain(meta({property: 'og:updated_time', content: '2016-05-23T21:20:21.372Z'})); + result.should.not.contain( + meta({ property: 'og:updated_time', content: '2016-05-23T21:20:21.372Z' }) + ); }); it('description - do not add /(?:og:)?description/ meta tags if there is no description', () => { - const result = openGraph.call({ - page: { }, - config: {}, - is_post: isPost - }, { }); + const result = openGraph.call( + { + page: {}, + config: {}, + is_post: isPost + }, + {} + ); - result.should.not.contain(meta({property: 'og:description'})); - result.should.not.contain(meta({property: 'description'})); + result.should.not.contain(meta({ property: 'og:description' })); + result.should.not.contain(meta({ property: 'description' })); }); it('keywords - page keywords string', () => { @@ -449,7 +573,7 @@ describe('open_graph', () => { const result = openGraph.call(ctx); const escaped = 'optimize,web'; - result.should.contain(meta({name: 'keywords', content: escaped})); + result.should.contain(meta({ name: 'keywords', content: escaped })); }); it('keywords - page keywords array', () => { @@ -462,7 +586,7 @@ describe('open_graph', () => { const result = openGraph.call(ctx); const keywords = 'optimize,web'; - result.should.contain(meta({name: 'keywords', content: keywords})); + result.should.contain(meta({ name: 'keywords', content: keywords })); }); it('keywords - page tags', () => { @@ -475,7 +599,7 @@ describe('open_graph', () => { const result = openGraph.call(ctx); const keywords = 'optimize,web'; - result.should.contain(meta({name: 'keywords', content: keywords})); + result.should.contain(meta({ name: 'keywords', content: keywords })); }); it('keywords - config keywords string', () => { @@ -488,7 +612,7 @@ describe('open_graph', () => { const result = openGraph.call(ctx); const keywords = 'optimize,web'; - result.should.contain(meta({name: 'keywords', content: keywords})); + result.should.contain(meta({ name: 'keywords', content: keywords })); }); it('keywords - config keywords array', () => { @@ -501,7 +625,7 @@ describe('open_graph', () => { const result = openGraph.call(ctx); const keywords = 'optimize,web'; - result.should.contain(meta({name: 'keywords', content: keywords})); + result.should.contain(meta({ name: 'keywords', content: keywords })); }); it('keywords - page keywords first', () => { @@ -517,7 +641,7 @@ describe('open_graph', () => { const result = openGraph.call(ctx); const keywords = 'web1,web2'; - result.should.contain(meta({name: 'keywords', content: keywords})); + result.should.contain(meta({ name: 'keywords', content: keywords })); }); it('keywords - page tags second', () => { @@ -530,7 +654,7 @@ describe('open_graph', () => { const result = openGraph.call(ctx); const keywords = 'optimize,web'; - result.should.contain(meta({name: 'keywords', content: keywords})); + result.should.contain(meta({ name: 'keywords', content: keywords })); }); it('keywords - page tags empty', () => { @@ -543,7 +667,7 @@ describe('open_graph', () => { const result = openGraph.call(ctx); const keywords = 'web5,web6'; - result.should.contain(meta({name: 'keywords', content: keywords})); + result.should.contain(meta({ name: 'keywords', content: keywords })); }); it('keywords - escape', () => { @@ -556,17 +680,20 @@ describe('open_graph', () => { const result = openGraph.call(ctx); const keywords = 'optimize,web&<>"'/,site'; - result.should.contain(meta({name: 'keywords', content: keywords})); + result.should.contain(meta({ name: 'keywords', content: keywords })); }); it('og:locale - options.language', () => { - const result = openGraph.call({ - page: {}, - config: hexo.config, - is_post: isPost - }, {language: 'es-cr'}); + const result = openGraph.call( + { + page: {}, + config: hexo.config, + is_post: isPost + }, + { language: 'es-cr' } + ); - result.should.contain(meta({property: 'og:locale', content: 'es-cr'})); + result.should.contain(meta({ property: 'og:locale', content: 'es-cr' })); }); it('og:locale - page.lang', () => { @@ -576,7 +703,7 @@ describe('open_graph', () => { is_post: isPost }); - result.should.contain(meta({property: 'og:locale', content: 'es-mx'})); + result.should.contain(meta({ property: 'og:locale', content: 'es-mx' })); }); it('og:locale - page.language', () => { @@ -586,7 +713,7 @@ describe('open_graph', () => { is_post: isPost }); - result.should.contain(meta({property: 'og:locale', content: 'es-gt'})); + result.should.contain(meta({ property: 'og:locale', content: 'es-gt' })); }); it('og:locale - config.language', () => { @@ -598,7 +725,7 @@ describe('open_graph', () => { is_post: isPost }); - result.should.contain(meta({property: 'og:locale', content: 'es-pa'})); + result.should.contain(meta({ property: 'og:locale', content: 'es-pa' })); }); it('og:locale - no language set', () => { @@ -608,6 +735,6 @@ describe('open_graph', () => { is_post: isPost }); - result.should.not.contain(meta({property: 'og:locale'})); + result.should.not.contain(meta({ property: 'og:locale' })); }); }); diff --git a/test/scripts/helpers/paginator.js b/test/scripts/helpers/paginator.js index d02ea0d75c..9f750d2638 100644 --- a/test/scripts/helpers/paginator.js +++ b/test/scripts/helpers/paginator.js @@ -27,11 +27,16 @@ describe('paginator', () => { const total = data.total; const pages = data.pages; const space = data.space || '…'; - const prevNext = Object.prototype.hasOwnProperty.call(data, 'prev_next') ? data.prev_next : true; + const prevNext = Object.prototype.hasOwnProperty.call(data, 'prev_next') + ? data.prev_next + : true; let num; if (prevNext && current > 1) { - expected += 'Prev'; + expected += + 'Prev'; } for (let i = 0, len = pages.length; i < len; i++) { @@ -42,12 +47,16 @@ describe('paginator', () => { } else if (num === current) { expected += '' + current + ''; } else { - expected += '' + num + ''; + expected += + '' + num + ''; } } if (prevNext && current < total) { - expected += 'Next'; + expected += + 'Next'; } result.should.eql(expected); @@ -180,14 +189,16 @@ describe('paginator', () => { base: 'archives/' }); - result.should.eql([ - '1', - '2', - '3', - '…', - '10', - 'Next' - ].join('')); + result.should.eql( + [ + '1', + '2', + '3', + '…', + '10', + 'Next' + ].join('') + ); }); it('format', () => { @@ -196,14 +207,16 @@ describe('paginator', () => { format: 'index-%d.html' }); - result.should.eql([ - '1', - '2', - '3', - '…', - '10', - 'Next' - ].join('')); + result.should.eql( + [ + '1', + '2', + '3', + '…', + '10', + 'Next' + ].join('') + ); }); it('prev_text / next_text', () => { @@ -213,16 +226,18 @@ describe('paginator', () => { next_text: 'Older' }); - result.should.eql([ - 'Newer', - '1', - '2', - '3', - '4', - '…', - '10', - 'Older' - ].join('')); + result.should.eql( + [ + 'Newer', + '1', + '2', + '3', + '4', + '…', + '10', + 'Older' + ].join('') + ); }); it('prev_next', () => { @@ -231,14 +246,16 @@ describe('paginator', () => { prev_next: false }); - result.should.eql([ - '1', - '2', - '3', - '4', - '…', - '10' - ].join('')); + result.should.eql( + [ + '1', + '2', + '3', + '4', + '…', + '10' + ].join('') + ); }); it('transform', () => { @@ -249,16 +266,18 @@ describe('paginator', () => { } }); - result.should.eql([ - 'Prev', - 'Page 1', - 'Page 2', - 'Page 3', - 'Page 4', - '…', - 'Page 10', - 'Next' - ].join('')); + result.should.eql( + [ + 'Prev', + 'Page 1', + 'Page 2', + 'Page 3', + 'Page 4', + '…', + 'Page 10', + 'Next' + ].join('') + ); }); it('context', () => { diff --git a/test/scripts/helpers/partial.js b/test/scripts/helpers/partial.js index 6606fd70f2..5456e6c5a5 100644 --- a/test/scripts/helpers/partial.js +++ b/test/scripts/helpers/partial.js @@ -7,7 +7,9 @@ const Promise = require('bluebird'); describe('partial', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'partial_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'partial_test'), { + silent: true + }); const themeDir = pathFn.join(hexo.base_dir, 'themes', 'test'); const viewDir = pathFn.join(themeDir, 'layout') + pathFn.sep; const viewName = 'article.swig'; @@ -21,18 +23,26 @@ describe('partial', () => { cache: true }; - ctx.fragment_cache = require('../../../lib/plugins/helper/fragment_cache')(hexo); + ctx.fragment_cache = require('../../../lib/plugins/helper/fragment_cache')( + hexo + ); hexo.env.init = true; - const partial = require('../../../lib/plugins/helper/partial')(hexo).bind(ctx); - - before(() => Promise.all([ - fs.mkdirs(themeDir), - fs.writeFile(hexo.config_path, 'theme: test') - ]).then(() => hexo.init()).then(() => { - hexo.theme.setView('widget/tag.swig', 'tag widget'); - })); + const partial = require('../../../lib/plugins/helper/partial')(hexo).bind( + ctx + ); + + before(() => + Promise.all([ + fs.mkdirs(themeDir), + fs.writeFile(hexo.config_path, 'theme: test') + ]) + .then(() => hexo.init()) + .then(() => { + hexo.theme.setView('widget/tag.swig', 'tag widget'); + }) + ); after(() => fs.rmdir(hexo.base_dir)); @@ -57,20 +67,20 @@ describe('partial', () => { it('locals', () => { hexo.theme.setView('test.swig', '{{ foo }}'); - partial('test', {foo: 'bar'}).should.eql('bar'); + partial('test', { foo: 'bar' }).should.eql('bar'); }); it('cache', () => { hexo.theme.setView('test.swig', '{{ foo }}'); - partial('test', {foo: 'bar'}, {cache: true}).should.eql('bar'); - partial('test', {}, {cache: true}).should.eql('bar'); + partial('test', { foo: 'bar' }, { cache: true }).should.eql('bar'); + partial('test', {}, { cache: true }).should.eql('bar'); }); it('only', () => { hexo.theme.setView('test.swig', '{{ foo }}{{ bar }}'); - partial('test', {bar: 'bar'}, {only: true}).should.eql('bar'); + partial('test', { bar: 'bar' }, { only: true }).should.eql('bar'); }); it('a partial in another partial', () => { diff --git a/test/scripts/helpers/relative_url.js b/test/scripts/helpers/relative_url.js index 8f511747b4..9753a563e4 100644 --- a/test/scripts/helpers/relative_url.js +++ b/test/scripts/helpers/relative_url.js @@ -12,14 +12,20 @@ describe('relative_url', () => { relativeURL('foo/', 'foo/style.css').should.eql('style.css'); relativeURL('foo/index.html', 'foo/style.css').should.eql('style.css'); relativeURL('foo/bar/', 'foo/bar/style.css').should.eql('style.css'); - relativeURL('foo/bar/index.html', 'foo/bar/style.css').should.eql('style.css'); + relativeURL('foo/bar/index.html', 'foo/bar/style.css').should.eql( + 'style.css' + ); }); it('from different root', () => { relativeURL('foo/', 'css/style.css').should.eql('../css/style.css'); - relativeURL('foo/index.html', 'css/style.css').should.eql('../css/style.css'); + relativeURL('foo/index.html', 'css/style.css').should.eql( + '../css/style.css' + ); relativeURL('foo/bar/', 'css/style.css').should.eql('../../css/style.css'); - relativeURL('foo/bar/index.html', 'css/style.css').should.eql('../../css/style.css'); + relativeURL('foo/bar/index.html', 'css/style.css').should.eql( + '../../css/style.css' + ); }); it('to root', () => { diff --git a/test/scripts/helpers/render.js b/test/scripts/helpers/render.js index 568af34c0f..f0016f238d 100644 --- a/test/scripts/helpers/render.js +++ b/test/scripts/helpers/render.js @@ -8,11 +8,7 @@ describe('render', () => { before(() => hexo.init()); it('default', () => { - const body = [ - 'foo: 1', - 'bar:', - '\tbaz: 3' - ].join('\n'); + const body = ['foo: 1', 'bar:', '\tbaz: 3'].join('\n'); const result = render(body, 'yaml'); diff --git a/test/scripts/helpers/search_form.js b/test/scripts/helpers/search_form.js index b297c6cf93..7fc5c671a4 100644 --- a/test/scripts/helpers/search_form.js +++ b/test/scripts/helpers/search_form.js @@ -2,43 +2,53 @@ describe('search_form', () => { const searchForm = require('../../../lib/plugins/helper/search_form').bind({ - config: {url: 'https://hexo.io'} + config: { url: 'https://hexo.io' } }); it('default', () => { - searchForm().should.eql(''); + searchForm().should.eql( + '' + ); }); it('class', () => { - searchForm({class: 'foo'}).should.eql(''); + searchForm({ class: 'foo' }).should.eql( + '' + ); }); it('text', () => { - searchForm({text: 'Find'}).should.eql(''); + searchForm({ text: 'Find' }).should.eql( + '' + ); }); it('button enabled', () => { - searchForm({button: true, text: 'Find'}).should.eql(''); + searchForm({ button: true, text: 'Find' }).should.eql( + '' + ); }); it('button text', () => { - searchForm({button: 'Go', text: 'Find'}).should.eql(''); + searchForm({ button: 'Go', text: 'Find' }).should.eql( + '' + ); }); }); diff --git a/test/scripts/helpers/tagcloud.js b/test/scripts/helpers/tagcloud.js index 605e75189b..6cda237828 100644 --- a/test/scripts/helpers/tagcloud.js +++ b/test/scripts/helpers/tagcloud.js @@ -16,42 +16,62 @@ describe('tagcloud', () => { const tagcloud = require('../../../lib/plugins/helper/tagcloud').bind(ctx); - before(() => hexo.init().then(() => Post.insert([ - {source: 'foo', slug: 'foo'}, - {source: 'bar', slug: 'bar'}, - {source: 'baz', slug: 'baz'}, - {source: 'boo', slug: 'boo'} - ])).then(posts => // TODO: Warehouse needs to add a mutex lock when writing data to avoid data sync problem - Promise.each([ - ['bcd'], - ['bcd', 'cde'], - ['bcd', 'cde', 'abc'], - ['bcd', 'cde', 'abc', 'def'] - ], (tags, i) => posts[i].setTags(tags))).then(() => { - hexo.locals.invalidate(); - ctx.site = hexo.locals.toObject(); - })); + before(() => + hexo + .init() + .then(() => + Post.insert([ + { source: 'foo', slug: 'foo' }, + { source: 'bar', slug: 'bar' }, + { source: 'baz', slug: 'baz' }, + { source: 'boo', slug: 'boo' } + ]) + ) + .then(( + posts // TODO: Warehouse needs to add a mutex lock when writing data to avoid data sync problem + ) => + Promise.each( + [ + ['bcd'], + ['bcd', 'cde'], + ['bcd', 'cde', 'abc'], + ['bcd', 'cde', 'abc', 'def'] + ], + (tags, i) => posts[i].setTags(tags) + ) + ) + .then(() => { + hexo.locals.invalidate(); + ctx.site = hexo.locals.toObject(); + }) + ); it('default', () => { const result = tagcloud(); - result.should.eql([ - 'abc', - 'bcd', - 'cde', - 'def' - ].join(' ')); + result.should.eql( + [ + 'abc', + 'bcd', + 'cde', + 'def' + ].join(' ') + ); }); it('specified collection', () => { - const result = tagcloud(Tag.find({ - name: /bc/ - })); - - result.should.eql([ - 'abc', - 'bcd' - ].join(' ')); + const result = tagcloud( + Tag.find({ + name: /bc/ + }) + ); + + result.should.eql( + [ + 'abc', + 'bcd' + ].join(' ') + ); }); it('font size', () => { @@ -60,25 +80,30 @@ describe('tagcloud', () => { max_font: 30 }); - result.should.eql([ - 'abc', - 'bcd', - 'cde', - 'def' - ].join(' ')); + result.should.eql( + [ + 'abc', + 'bcd', + 'cde', + 'def' + ].join(' ') + ); }); it('font size - when every tag has the same number of posts, font-size should be minimum.', () => { - const result = tagcloud(Tag.find({ - name: /abc/ - }), { - min_font: 15, - max_font: 30 - }); + const result = tagcloud( + Tag.find({ + name: /abc/ + }), + { + min_font: 15, + max_font: 30 + } + ); - result.should.eql([ - 'abc' - ].join(' ')); + result.should.eql( + ['abc'].join(' ') + ); }); it('font unit', () => { @@ -86,12 +111,14 @@ describe('tagcloud', () => { unit: 'em' }); - result.should.eql([ - 'abc', - 'bcd', - 'cde', - 'def' - ].join(' ')); + result.should.eql( + [ + 'abc', + 'bcd', + 'cde', + 'def' + ].join(' ') + ); }); it('orderby', () => { @@ -99,12 +126,14 @@ describe('tagcloud', () => { orderby: 'length' }); - result.should.eql([ - 'def', - 'abc', - 'cde', - 'bcd' - ].join(' ')); + result.should.eql( + [ + 'def', + 'abc', + 'cde', + 'bcd' + ].join(' ') + ); }); it('order', () => { @@ -112,12 +141,14 @@ describe('tagcloud', () => { order: -1 }); - result.should.eql([ - 'def', - 'cde', - 'bcd', - 'abc' - ].join(' ')); + result.should.eql( + [ + 'def', + 'cde', + 'bcd', + 'abc' + ].join(' ') + ); }); it('amount', () => { @@ -125,10 +156,12 @@ describe('tagcloud', () => { amount: 2 }); - result.should.eql([ - 'abc', - 'bcd' - ].join(' ')); + result.should.eql( + [ + 'abc', + 'bcd' + ].join(' ') + ); }); it('transform', () => { @@ -138,12 +171,14 @@ describe('tagcloud', () => { } }); - result.should.eql([ - 'ABC', - 'BCD', - 'CDE', - 'DEF' - ].join(' ')); + result.should.eql( + [ + 'ABC', + 'BCD', + 'CDE', + 'DEF' + ].join(' ') + ); }); it('color: name', () => { @@ -153,12 +188,14 @@ describe('tagcloud', () => { end_color: 'pink' }); - result.should.eql([ - 'abc', - 'bcd', - 'cde', - 'def' - ].join(' ')); + result.should.eql( + [ + 'abc', + 'bcd', + 'cde', + 'def' + ].join(' ') + ); }); it('color: hex', () => { @@ -168,12 +205,14 @@ describe('tagcloud', () => { end_color: '#ffc0cb' // pink }); - result.should.eql([ - 'abc', - 'bcd', - 'cde', - 'def' - ].join(' ')); + result.should.eql( + [ + 'abc', + 'bcd', + 'cde', + 'def' + ].join(' ') + ); }); it('color: RGBA', () => { @@ -183,12 +222,14 @@ describe('tagcloud', () => { end_color: 'rgb(70, 130, 180)' }); - result.should.eql([ - 'abc', - 'bcd', - 'cde', - 'def' - ].join(' ')); + result.should.eql( + [ + 'abc', + 'bcd', + 'cde', + 'def' + ].join(' ') + ); }); it('color: HSLA', () => { @@ -198,26 +239,33 @@ describe('tagcloud', () => { end_color: 'hsl(207, 44%, 49%)' // rgb(70, 130, 180) }); - result.should.eql([ - 'abc', - 'bcd', - 'cde', - 'def' - ].join(' ')); + result.should.eql( + [ + 'abc', + 'bcd', + 'cde', + 'def' + ].join(' ') + ); }); it('color - when every tag has the same number of posts, start_color should be used.', () => { - const result = tagcloud(Tag.find({ - name: /abc/ - }), { - color: true, - start_color: 'red', - end_color: 'pink' - }); + const result = tagcloud( + Tag.find({ + name: /abc/ + }), + { + color: true, + start_color: 'red', + end_color: 'pink' + } + ); - result.should.eql([ - 'abc' - ].join(' ')); + result.should.eql( + [ + 'abc' + ].join(' ') + ); }); it('separator', () => { @@ -225,11 +273,13 @@ describe('tagcloud', () => { separator: ', ' }); - result.should.eql([ - 'abc', - 'bcd', - 'cde', - 'def' - ].join(', ')); + result.should.eql( + [ + 'abc', + 'bcd', + 'cde', + 'def' + ].join(', ') + ); }); }); diff --git a/test/scripts/helpers/toc.js b/test/scripts/helpers/toc.js index 02c2cd17f6..29e753eab9 100644 --- a/test/scripts/helpers/toc.js +++ b/test/scripts/helpers/toc.js @@ -21,11 +21,14 @@ describe('toc', () => { ].join(''); const genResult = options => { - options = Object.assign({ - class: 'toc', - list_number: true, - max_depth: 6 - }, options); + options = Object.assign( + { + class: 'toc', + list_number: true, + max_depth: 6 + }, + options + ); const className = options.class; const listNumber = options.list_number; @@ -35,7 +38,11 @@ describe('toc', () => { '', '
- ', '', - ifTrue(listNumber, '1.1.1. ', ''), + ifTrue( + listNumber, + '1.1.1. ', + '' + ), 'Title 1.1.1', '', '
', @@ -46,7 +53,11 @@ describe('toc', () => { '', '
- ', '', - ifTrue(listNumber, '1.3.1. ', ''), + ifTrue( + listNumber, + '1.3.1. ', + '' + ), 'Title 1.3.1', '', '
', @@ -57,20 +68,32 @@ describe('toc', () => { '', '
- ', '', - ifTrue(listNumber, '1.1. ', ''), + ifTrue( + listNumber, + '1.1. ', + '' + ), 'Title 1.1', '', ifTrue(maxDepth >= 3, resultTitle_1_1_1, ''), '
', '- ', '', - ifTrue(listNumber, '1.2. ', ''), + ifTrue( + listNumber, + '1.2. ', + '' + ), 'Title 1.2', '', '
', '- ', '', - ifTrue(listNumber, '1.3. ', ''), + ifTrue( + listNumber, + '1.3. ', + '' + ), 'Title 1.3', '', ifTrue(maxDepth >= 3, resultTitle_1_3_1, ''), @@ -82,7 +105,11 @@ describe('toc', () => { '
', '
- ', '', - ifTrue(listNumber, '2.1. ', ''), + ifTrue( + listNumber, + '2.1. ', + '' + ), 'Title 2.1', '', '
', @@ -92,28 +119,48 @@ describe('toc', () => { const resultAllTitles_Level1 = [ '- ', '', - ifTrue(listNumber, '1. ', ''), + ifTrue( + listNumber, + '1. ', + '' + ), 'Title 1', '', ifTrue(maxDepth >= 2, resultTitle_1_1, ''), '
', '- ', '', - ifTrue(listNumber, '2. ', ''), + ifTrue( + listNumber, + '2. ', + '' + ), 'Title 2', '', ifTrue(maxDepth >= 2, resultTitle_2_1, ''), '
', '- ', '', - ifTrue(listNumber, '3. ', ''), - 'Title should escape &, <, ', and "', + ifTrue( + listNumber, + '3. ', + '' + ), + 'Title should escape &, <, ', and "', '', '
', '- ', '', - ifTrue(listNumber, '4. ', ''), - 'Chapter 1 should be printed to toc', + ifTrue( + listNumber, + '4. ', + '' + ), + 'Chapter 1 should be printed to toc', '', '
' ].join(''); diff --git a/test/scripts/helpers/url_for.js b/test/scripts/helpers/url_for.js index 0195805d9f..dc5a3903d8 100644 --- a/test/scripts/helpers/url_for.js +++ b/test/scripts/helpers/url_for.js @@ -35,18 +35,15 @@ describe('url_for', () => { it('internal url (options.relative)', () => { ctx.path = ''; - urlFor('index.html', {relative: true}).should.eql('index.html'); + urlFor('index.html', { relative: true }).should.eql('index.html'); ctx.config.relative_link = true; - urlFor('index.html', {relative: false}).should.eql('/index.html'); + urlFor('index.html', { relative: false }).should.eql('/index.html'); ctx.config.relative_link = false; }); it('external url', () => { - [ - 'https://hexo.io/', - '//google.com/' - ].forEach(url => { + ['https://hexo.io/', '//google.com/'].forEach(url => { urlFor(url).should.eql(url); }); }); diff --git a/test/scripts/hexo/hexo.js b/test/scripts/hexo/hexo.js index de3290fb98..5c89225b40 100644 --- a/test/scripts/hexo/hexo.js +++ b/test/scripts/hexo/hexo.js @@ -10,7 +10,7 @@ const testUtil = require('../../util'); describe('Hexo', () => { const base_dir = pathFn.join(__dirname, 'hexo_test'); const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(base_dir, {silent: true}); + const hexo = new Hexo(base_dir, { silent: true }); const coreDir = pathFn.join(__dirname, '../../..'); const version = require('../../../package.json').version; const Post = hexo.model('Post'); @@ -25,7 +25,10 @@ describe('Hexo', () => { } function loadAssetGenerator() { - hexo.extend.generator.register('asset', require('../../../lib/plugins/generator/asset')); + hexo.extend.generator.register( + 'asset', + require('../../../lib/plugins/generator/asset') + ); } before(() => fs.mkdirs(hexo.base_dir).then(() => hexo.init())); @@ -68,20 +71,24 @@ describe('Hexo', () => { }); it('constructs mutli-config', () => { - const configs = ['../../../fixtures/_config.json', '../../../fixtures/_config.json']; + const configs = [ + '../../../fixtures/_config.json', + '../../../fixtures/_config.json' + ]; const args = { _: [], config: configs.join(',') }; const hexo = new Hexo(base_dir, args); hexo.config_path.should.eql(pathFn.join(base_dir, '_multiconfig.yml')); }); - it('call()', () => hexo.call('test', {foo: 'bar'}).then(data => { - data.should.eql({foo: 'bar'}); - })); + it('call()', () => + hexo.call('test', { foo: 'bar' }).then(data => { + data.should.eql({ foo: 'bar' }); + })); it('call() - callback', callback => { - hexo.call('test', {foo: 'bar'}, (err, data) => { + hexo.call('test', { foo: 'bar' }, (err, data) => { should.not.exist(err); - data.should.eql({foo: 'bar'}); + data.should.eql({ foo: 'bar' }); callback(); }); @@ -98,16 +105,24 @@ describe('Hexo', () => { it('call() - console not registered', () => { const errorCallback = sinon.spy(err => { - err.should.have.property('message', 'Console `nothing` has not been registered yet!'); + err.should.have.property( + 'message', + 'Console `nothing` has not been registered yet!' + ); }); - return hexo.call('nothing').catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + return hexo + .call('nothing') + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); it('init()', () => { - const hexo = new Hexo(pathFn.join(__dirname, 'hexo_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'hexo_test'), { + silent: true + }); const hook = sinon.spy(); hexo.extend.filter.register('after_init', hook); @@ -141,7 +156,11 @@ describe('Hexo', () => { loadAssetGenerator(); - return fs.writeFile(target, body).then(() => hexo.load()).then(() => checkStream(route.get('test.txt'), body)).then(() => fs.unlink(target)); + return fs + .writeFile(target, body) + .then(() => hexo.load()) + .then(() => checkStream(route.get('test.txt'), body)) + .then(() => fs.unlink(target)); } it('load() - source', () => testLoad(hexo.source_dir)); @@ -155,12 +174,30 @@ describe('Hexo', () => { loadAssetGenerator(); - return fs.writeFile(target, body).then(() => hexo.watch()).then(() => // Test for first generation - checkStream(route.get('test.txt'), body)).then(() => // Update the file - fs.writeFile(target, newBody)).delay(300).then(() => // Check the new route - checkStream(route.get('test.txt'), newBody)).then(() => // Stop watching - hexo.unwatch()).then(() => // Delete the file - fs.unlink(target)); + return fs + .writeFile(target, body) + .then(() => hexo.watch()) + .then(() => + // Test for first generation + checkStream(route.get('test.txt'), body) + ) + .then(() => + // Update the file + fs.writeFile(target, newBody) + ) + .delay(300) + .then(() => + // Check the new route + checkStream(route.get('test.txt'), newBody) + ) + .then(() => + // Stop watching + hexo.unwatch() + ) + .then(() => + // Delete the file + fs.unlink(target) + ); } it('watch() - source', () => testWatch(hexo.source_dir)); @@ -184,20 +221,20 @@ describe('Hexo', () => { it('exit() - error handling - callback', callback => { hexo.once('exit', err => { - err.should.eql({foo: 'bar'}); + err.should.eql({ foo: 'bar' }); callback(); }); - hexo.exit({foo: 'bar'}); + hexo.exit({ foo: 'bar' }); }); it('exit() - error handling - promise', () => { return Promise.all([ - hexo.exit({foo: 'bar'}), + hexo.exit({ foo: 'bar' }), new Promise((resolve, reject) => { hexo.once('exit', err => { try { - err.should.eql({foo: 'bar'}); + err.should.eql({ foo: 'bar' }); resolve(); } catch (e) { reject(e); @@ -207,76 +244,106 @@ describe('Hexo', () => { ]); }); - it('draft visibility', () => Post.insert([ - {source: 'foo', slug: 'foo', published: true}, - {source: 'bar', slug: 'bar', published: false} - ]).then(posts => { - hexo.locals.invalidate(); - hexo.locals.get('posts').toArray().should.eql(posts.slice(0, 1)); - - // draft visible - hexo.config.render_drafts = true; - hexo.locals.invalidate(); - hexo.locals.get('posts').toArray().should.eql(posts); - hexo.config.render_drafts = false; - - return posts; - }).map(post => Post.removeById(post._id))); - - it('future posts', () => Post.insert([ - {source: 'foo', slug: 'foo', date: Date.now() - 3600}, - {source: 'bar', slug: 'bar', date: Date.now() + 3600} - ]).then(posts => { - function mapper(post) { - return post._id; - } - - // future on - hexo.config.future = true; - hexo.locals.invalidate(); - hexo.locals.get('posts').map(mapper).should.eql(posts.map(mapper)); - - // future off - hexo.config.future = false; - hexo.locals.invalidate(); - hexo.locals.get('posts').map(mapper).should.eql([posts[0]._id]); - - return posts; - }).map(post => Post.removeById(post._id))); - - it('future pages', () => Page.insert([ - {source: 'foo', path: 'foo', date: Date.now() - 3600}, - {source: 'bar', path: 'bar', date: Date.now() + 3600} - ]).then(pages => { - function mapper(page) { - return page._id; - } - - // future on - hexo.config.future = true; - hexo.locals.invalidate(); - hexo.locals.get('pages').map(mapper).should.eql(pages.map(mapper)); - - // future off - hexo.config.future = false; - hexo.locals.invalidate(); - hexo.locals.get('pages').map(mapper).should.eql([pages[0]._id]); - - return pages; - }).map(page => Page.removeById(page._id))); - - it('locals.data', () => Data.insert([ - {_id: 'users', data: {foo: 1}}, - {_id: 'comments', data: {bar: 2}} - ]).then(data => { - hexo.locals.invalidate(); - hexo.locals.get('data').should.eql({ - users: {foo: 1}, - comments: {bar: 2} - }); + it('draft visibility', () => + Post.insert([ + { source: 'foo', slug: 'foo', published: true }, + { source: 'bar', slug: 'bar', published: false } + ]) + .then(posts => { + hexo.locals.invalidate(); + hexo.locals + .get('posts') + .toArray() + .should.eql(posts.slice(0, 1)); + + // draft visible + hexo.config.render_drafts = true; + hexo.locals.invalidate(); + hexo.locals + .get('posts') + .toArray() + .should.eql(posts); + hexo.config.render_drafts = false; + + return posts; + }) + .map(post => Post.removeById(post._id))); + + it('future posts', () => + Post.insert([ + { source: 'foo', slug: 'foo', date: Date.now() - 3600 }, + { source: 'bar', slug: 'bar', date: Date.now() + 3600 } + ]) + .then(posts => { + function mapper(post) { + return post._id; + } + + // future on + hexo.config.future = true; + hexo.locals.invalidate(); + hexo.locals + .get('posts') + .map(mapper) + .should.eql(posts.map(mapper)); + + // future off + hexo.config.future = false; + hexo.locals.invalidate(); + hexo.locals + .get('posts') + .map(mapper) + .should.eql([posts[0]._id]); + + return posts; + }) + .map(post => Post.removeById(post._id))); + + it('future pages', () => + Page.insert([ + { source: 'foo', path: 'foo', date: Date.now() - 3600 }, + { source: 'bar', path: 'bar', date: Date.now() + 3600 } + ]) + .then(pages => { + function mapper(page) { + return page._id; + } + + // future on + hexo.config.future = true; + hexo.locals.invalidate(); + hexo.locals + .get('pages') + .map(mapper) + .should.eql(pages.map(mapper)); + + // future off + hexo.config.future = false; + hexo.locals.invalidate(); + hexo.locals + .get('pages') + .map(mapper) + .should.eql([pages[0]._id]); + + return pages; + }) + .map(page => Page.removeById(page._id))); + + it('locals.data', () => + Data.insert([ + { _id: 'users', data: { foo: 1 } }, + { _id: 'comments', data: { bar: 2 } } + ]) + .then(data => { + hexo.locals.invalidate(); + hexo.locals.get('data').should.eql({ + users: { foo: 1 }, + comments: { bar: 2 } + }); - return data; - }).map(data => data.remove())); + return data; + }) + .map(data => data.remove())); it('_generate()', () => { // object @@ -293,10 +360,7 @@ describe('Hexo', () => { hexo.extend.generator.register('test_arr', locals => { locals.test.should.eql('foo'); - return [ - {path: 'bar', data: 'bar'}, - {path: 'baz', data: 'baz'} - ]; + return [{ path: 'bar', data: 'bar' }, { path: 'baz', data: 'baz' }]; }); const beforeListener = sinon.spy(); @@ -329,12 +393,15 @@ describe('Hexo', () => { }); it('_generate() - layout', () => { - hexo.theme.setView('test.swig', [ - '{{ config.title }}', - '{{ page.foo }}', - '{{ layout }}', - '{{ view_dir }}' - ].join('\n')); + hexo.theme.setView( + 'test.swig', + [ + '{{ config.title }}', + '{{ page.foo }}', + '{{ layout }}', + '{{ view_dir }}' + ].join('\n') + ); hexo.extend.generator.register('test', () => ({ path: 'test', @@ -352,7 +419,9 @@ describe('Hexo', () => { pathFn.join(hexo.theme_dir, 'layout') + pathFn.sep ].join('\n'); - return hexo._generate().then(() => checkStream(route.get('test'), expected)); + return hexo + ._generate() + .then(() => checkStream(route.get('test'), expected)); }); it('_generate() - layout array', () => { @@ -407,25 +476,31 @@ describe('Hexo', () => { }); it('_generate() - validate locals', () => { - hexo.theme.setView('test.swig', [ - '{{ path }}', - '{{ url }}', - '{{ view_dir }}' - ].join('\n')); + hexo.theme.setView( + 'test.swig', + ['{{ path }}', '{{ url }}', '{{ view_dir }}'].join('\n') + ); hexo.extend.generator.register('test', () => ({ path: 'test', layout: 'test' })); - return hexo._generate().then(() => checkStream(route.get('test'), [ - 'test', - hexo.config.url + '/test', - pathFn.join(hexo.theme_dir, 'layout') + pathFn.sep - ].join('\n'))); + return hexo + ._generate() + .then(() => + checkStream( + route.get('test'), + [ + 'test', + hexo.config.url + '/test', + pathFn.join(hexo.theme_dir, 'layout') + pathFn.sep + ].join('\n') + ) + ); }); - it('_generate() - do nothing if it\'s generating', () => { + it("_generate() - do nothing if it's generating", () => { const spy = sinon.spy(); hexo.extend.generator.register('test', spy); @@ -443,12 +518,18 @@ describe('Hexo', () => { hexo.extend.generator.register('test', () => ({ path: 'test', layout: 'test', - data: {count: count++} + data: { count: count++ } })); // First generation - return hexo._generate({cache: true}).then(() => checkStream(route.get('test'), '0')).then(() => // Second generation - hexo._generate({cache: true})).then(() => checkStream(route.get('test'), '1')); + return hexo + ._generate({ cache: true }) + .then(() => checkStream(route.get('test'), '0')) + .then(() => + // Second generation + hexo._generate({ cache: true }) + ) + .then(() => checkStream(route.get('test'), '1')); }); it('_generate() - cache disabled & update template', () => { @@ -459,10 +540,13 @@ describe('Hexo', () => { layout: 'test' })); - return hexo._generate({cache: false}).then(() => checkStream(route.get('test'), '0')).then(() => { - hexo.theme.setView('test.swig', '1'); - return checkStream(route.get('test'), '1'); - }); + return hexo + ._generate({ cache: false }) + .then(() => checkStream(route.get('test'), '0')) + .then(() => { + hexo.theme.setView('test.swig', '1'); + return checkStream(route.get('test'), '1'); + }); }); it('execFilter()', () => { diff --git a/test/scripts/hexo/load_config.js b/test/scripts/hexo/load_config.js index 5c68e9c1ae..0073f45220 100644 --- a/test/scripts/hexo/load_config.js +++ b/test/scripts/hexo/load_config.js @@ -6,7 +6,9 @@ const cloneDeep = require('lodash/cloneDeep'); describe('Load config', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'config_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'config_test'), { + silent: true + }); const loadConfig = require('../../../lib/hexo/load_config'); const defaultConfig = require('../../../lib/hexo/default_config'); @@ -20,94 +22,143 @@ describe('Load config', () => { hexo.config = cloneDeep(defaultConfig); }); - it('config file does not exist', () => loadConfig(hexo).then(() => { - hexo.config.should.eql(defaultConfig); - })); + it('config file does not exist', () => + loadConfig(hexo).then(() => { + hexo.config.should.eql(defaultConfig); + })); it('_config.yml exists', () => { const configPath = pathFn.join(hexo.base_dir, '_config.yml'); - return fs.writeFile(configPath, 'foo: 1').then(() => loadConfig(hexo)).then(() => { - hexo.config.foo.should.eql(1); - }).finally(() => fs.unlink(configPath)); + return fs + .writeFile(configPath, 'foo: 1') + .then(() => loadConfig(hexo)) + .then(() => { + hexo.config.foo.should.eql(1); + }) + .finally(() => fs.unlink(configPath)); }); it('_config.json exists', () => { const configPath = pathFn.join(hexo.base_dir, '_config.json'); - return fs.writeFile(configPath, '{"baz": 3}').then(() => loadConfig(hexo)).then(() => { - hexo.config.baz.should.eql(3); - }).finally(() => fs.unlink(configPath)); + return fs + .writeFile(configPath, '{"baz": 3}') + .then(() => loadConfig(hexo)) + .then(() => { + hexo.config.baz.should.eql(3); + }) + .finally(() => fs.unlink(configPath)); }); it('_config.txt exists', () => { const configPath = pathFn.join(hexo.base_dir, '_config.txt'); - return fs.writeFile(configPath, 'foo: 1').then(() => loadConfig(hexo)).then(() => { - hexo.config.should.eql(defaultConfig); - }).finally(() => fs.unlink(configPath)); + return fs + .writeFile(configPath, 'foo: 1') + .then(() => loadConfig(hexo)) + .then(() => { + hexo.config.should.eql(defaultConfig); + }) + .finally(() => fs.unlink(configPath)); }); it('custom config path', () => { - const configPath = hexo.config_path = pathFn.join(__dirname, 'werwerwer.yml'); - - return fs.writeFile(configPath, 'foo: 1').then(() => loadConfig(hexo)).then(() => { - hexo.config.foo.should.eql(1); - }).finally(() => { - hexo.config_path = pathFn.join(hexo.base_dir, '_config.yml'); - return fs.unlink(configPath); - }); + const configPath = (hexo.config_path = pathFn.join( + __dirname, + 'werwerwer.yml' + )); + + return fs + .writeFile(configPath, 'foo: 1') + .then(() => loadConfig(hexo)) + .then(() => { + hexo.config.foo.should.eql(1); + }) + .finally(() => { + hexo.config_path = pathFn.join(hexo.base_dir, '_config.yml'); + return fs.unlink(configPath); + }); }); it('custom config path with different extension name', () => { const realPath = pathFn.join(__dirname, 'werwerwer.json'); hexo.config_path = pathFn.join(__dirname, 'werwerwer.yml'); - return fs.writeFile(realPath, '{"foo": 2}').then(() => loadConfig(hexo)).then(() => { - hexo.config.foo.should.eql(2); - hexo.config_path.should.eql(realPath); - }).finally(() => { - hexo.config_path = pathFn.join(hexo.base_dir, '_config.yml'); - return fs.unlink(realPath); - }); + return fs + .writeFile(realPath, '{"foo": 2}') + .then(() => loadConfig(hexo)) + .then(() => { + hexo.config.foo.should.eql(2); + hexo.config_path.should.eql(realPath); + }) + .finally(() => { + hexo.config_path = pathFn.join(hexo.base_dir, '_config.yml'); + return fs.unlink(realPath); + }); }); it('handle trailing "/" of url', () => { - const content = [ - 'root: foo', - 'url: https://hexo.io/' - ].join('\n'); - - return fs.writeFile(hexo.config_path, content).then(() => loadConfig(hexo)).then(() => { - hexo.config.root.should.eql('foo/'); - hexo.config.url.should.eql('https://hexo.io'); - }).finally(() => fs.unlink(hexo.config_path)); + const content = ['root: foo', 'url: https://hexo.io/'].join('\n'); + + return fs + .writeFile(hexo.config_path, content) + .then(() => loadConfig(hexo)) + .then(() => { + hexo.config.root.should.eql('foo/'); + hexo.config.url.should.eql('https://hexo.io'); + }) + .finally(() => fs.unlink(hexo.config_path)); }); - it('custom public_dir', () => fs.writeFile(hexo.config_path, 'public_dir: foo').then(() => loadConfig(hexo)).then(() => { - hexo.public_dir.should.eql(pathFn.resolve(hexo.base_dir, 'foo') + pathFn.sep); - }).finally(() => fs.unlink(hexo.config_path))); - - it('custom source_dir', () => fs.writeFile(hexo.config_path, 'source_dir: bar').then(() => loadConfig(hexo)).then(() => { - hexo.source_dir.should.eql(pathFn.resolve(hexo.base_dir, 'bar') + pathFn.sep); - }).finally(() => fs.unlink(hexo.config_path))); - - it('custom theme', () => fs.writeFile(hexo.config_path, 'theme: test').then(() => loadConfig(hexo)).then(() => { - hexo.config.theme.should.eql('test'); - hexo.theme_dir.should.eql(pathFn.join(hexo.base_dir, 'themes', 'test') + pathFn.sep); - hexo.theme_script_dir.should.eql(pathFn.join(hexo.theme_dir, 'scripts') + pathFn.sep); - hexo.theme.base.should.eql(hexo.theme_dir); - }).finally(() => fs.unlink(hexo.config_path))); + it('custom public_dir', () => + fs + .writeFile(hexo.config_path, 'public_dir: foo') + .then(() => loadConfig(hexo)) + .then(() => { + hexo.public_dir.should.eql( + pathFn.resolve(hexo.base_dir, 'foo') + pathFn.sep + ); + }) + .finally(() => fs.unlink(hexo.config_path))); + + it('custom source_dir', () => + fs + .writeFile(hexo.config_path, 'source_dir: bar') + .then(() => loadConfig(hexo)) + .then(() => { + hexo.source_dir.should.eql( + pathFn.resolve(hexo.base_dir, 'bar') + pathFn.sep + ); + }) + .finally(() => fs.unlink(hexo.config_path))); + + it('custom theme', () => + fs + .writeFile(hexo.config_path, 'theme: test') + .then(() => loadConfig(hexo)) + .then(() => { + hexo.config.theme.should.eql('test'); + hexo.theme_dir.should.eql( + pathFn.join(hexo.base_dir, 'themes', 'test') + pathFn.sep + ); + hexo.theme_script_dir.should.eql( + pathFn.join(hexo.theme_dir, 'scripts') + pathFn.sep + ); + hexo.theme.base.should.eql(hexo.theme_dir); + }) + .finally(() => fs.unlink(hexo.config_path))); it('merge config', () => { - const content = [ - 'highlight:', - ' tab_replace: yoooo' - ].join('\n'); - - return fs.writeFile(hexo.config_path, content).then(() => loadConfig(hexo)).then(() => { - hexo.config.highlight.enable.should.be.true; - hexo.config.highlight.tab_replace.should.eql('yoooo'); - }).finally(() => fs.unlink(hexo.config_path)); + const content = ['highlight:', ' tab_replace: yoooo'].join('\n'); + + return fs + .writeFile(hexo.config_path, content) + .then(() => loadConfig(hexo)) + .then(() => { + hexo.config.highlight.enable.should.be.true; + hexo.config.highlight.tab_replace.should.eql('yoooo'); + }) + .finally(() => fs.unlink(hexo.config_path)); }); }); diff --git a/test/scripts/hexo/load_database.js b/test/scripts/hexo/load_database.js index 770e30fe35..5550a70c54 100644 --- a/test/scripts/hexo/load_database.js +++ b/test/scripts/hexo/load_database.js @@ -5,7 +5,7 @@ const fs = require('hexo-fs'); describe('Load database', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'db_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'db_test'), { silent: true }); const loadDatabase = require('../../../lib/hexo/load_database'); const dbPath = hexo.database.options.path; @@ -15,11 +15,7 @@ describe('Load database', () => { warehouse: require('warehouse').version }, models: { - Test: [ - {_id: 'A'}, - {_id: 'B'}, - {_id: 'C'} - ] + Test: [{ _id: 'A' }, { _id: 'B' }, { _id: 'C' }] } }; @@ -33,29 +29,44 @@ describe('Load database', () => { it('database does not exist', () => loadDatabase(hexo)); - it('database load success', () => fs.writeFile(dbPath, JSON.stringify(fixture)).then(() => loadDatabase(hexo)).then(() => { - hexo._dbLoaded.should.be.true; - hexo.model('Test').toArray({lean: true}).should.eql(fixture.models.Test); - hexo.model('Test').destroy(); + it('database load success', () => + fs + .writeFile(dbPath, JSON.stringify(fixture)) + .then(() => loadDatabase(hexo)) + .then(() => { + hexo._dbLoaded.should.be.true; + hexo + .model('Test') + .toArray({ lean: true }) + .should.eql(fixture.models.Test); + hexo.model('Test').destroy(); - return fs.unlink(dbPath); - })); + return fs.unlink(dbPath); + })); - it('don\'t load database if loaded', () => { + it("don't load database if loaded", () => { hexo._dbLoaded = true; - return fs.writeFile(dbPath, JSON.stringify(fixture)).then(() => loadDatabase(hexo)).then(() => { - hexo.model('Test').length.should.eql(0); - return fs.unlink(dbPath); - }); + return fs + .writeFile(dbPath, JSON.stringify(fixture)) + .then(() => loadDatabase(hexo)) + .then(() => { + hexo.model('Test').length.should.eql(0); + return fs.unlink(dbPath); + }); }); // I don't know why this test case can't pass on Windows // It always throws EPERM error - it.skip('database load failed', () => fs.writeFile(dbPath, '{1423432: 324').then(() => loadDatabase(hexo)).then(() => { - hexo._dbLoaded.should.be.false; - return fs.exists(dbPath); - }).then(exist => { - exist.should.be.false; - })); + it.skip('database load failed', () => + fs + .writeFile(dbPath, '{1423432: 324') + .then(() => loadDatabase(hexo)) + .then(() => { + hexo._dbLoaded.should.be.false; + return fs.exists(dbPath); + }) + .then(exist => { + exist.should.be.false; + })); }); diff --git a/test/scripts/hexo/load_plugins.js b/test/scripts/hexo/load_plugins.js index cdf8aef921..10ad609d7f 100644 --- a/test/scripts/hexo/load_plugins.js +++ b/test/scripts/hexo/load_plugins.js @@ -6,7 +6,9 @@ const Promise = require('bluebird'); describe('Load plugins', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'plugin_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'plugin_test'), { + silent: true + }); const loadPlugins = require('../../../lib/hexo/load_plugins'); const script = [ @@ -41,7 +43,10 @@ describe('Load plugins', () => { pkg.dependencies[args[i]] = '*'; } - return fs.writeFile(pathFn.join(hexo.base_dir, 'package.json'), JSON.stringify(pkg, null, ' ')); + return fs.writeFile( + pathFn.join(hexo.base_dir, 'package.json'), + JSON.stringify(pkg, null, ' ') + ); } function createPackageFileWithDevDeps(...args) { @@ -57,11 +62,19 @@ describe('Load plugins', () => { pkg.devDependencies[args[i]] = '*'; } - return fs.writeFile(pathFn.join(hexo.base_dir, 'package.json'), JSON.stringify(pkg, null, ' ')); + return fs.writeFile( + pathFn.join(hexo.base_dir, 'package.json'), + JSON.stringify(pkg, null, ' ') + ); } hexo.env.init = true; - hexo.theme_script_dir = pathFn.join(hexo.base_dir, 'themes', 'test', 'scripts'); + hexo.theme_script_dir = pathFn.join( + hexo.base_dir, + 'themes', + 'test', + 'scripts' + ); before(() => fs.mkdir(hexo.base_dir)); @@ -71,26 +84,24 @@ describe('Load plugins', () => { const name = 'hexo-plugin-test'; const path = pathFn.join(hexo.plugin_dir, name, 'index.js'); - return Promise.all([ - createPackageFile(name), - fs.writeFile(path, script) - ]).then(() => loadPlugins(hexo)).then(() => { - validate(path); - return fs.unlink(path); - }); + return Promise.all([createPackageFile(name), fs.writeFile(path, script)]) + .then(() => loadPlugins(hexo)) + .then(() => { + validate(path); + return fs.unlink(path); + }); }); it('load scoped plugins', () => { const name = '@some-scope/hexo-plugin-test'; const path = pathFn.join(hexo.plugin_dir, name, 'index.js'); - return Promise.all([ - createPackageFile(name), - fs.writeFile(path, script) - ]).then(() => loadPlugins(hexo)).then(() => { - validate(path); - return fs.unlink(path); - }); + return Promise.all([createPackageFile(name), fs.writeFile(path, script)]) + .then(() => loadPlugins(hexo)) + .then(() => { + validate(path); + return fs.unlink(path); + }); }); it('load devDep plugins', () => { @@ -100,32 +111,38 @@ describe('Load plugins', () => { return Promise.all([ createPackageFileWithDevDeps(name), fs.writeFile(path, script) - ]).then(() => loadPlugins(hexo)).then(() => { - validate(path); - return fs.unlink(path); - }); + ]) + .then(() => loadPlugins(hexo)) + .then(() => { + validate(path); + return fs.unlink(path); + }); }); it('specify plugin list in config', () => { const names = ['hexo-plugin-test', 'another-plugin']; - const paths = names.map(name => pathFn.join(hexo.plugin_dir, name, 'index.js')); + const paths = names.map(name => + pathFn.join(hexo.plugin_dir, name, 'index.js') + ); return Promise.all([ createPackageFile(...names), fs.writeFile(paths[0], 'hexo._script_test0 = true'), fs.writeFile(paths[1], 'hexo._script_test1 = true') - ]).then(() => { - hexo.config.plugins = [names[1]]; - return loadPlugins(hexo); - }).then(() => { - should.not.exist(hexo._script_test0); - hexo._script_test1.should.be.true; - - delete hexo.config.plugins; - delete hexo._script_test1; - - return Promise.map(paths, path => fs.unlink(path)); - }); + ]) + .then(() => { + hexo.config.plugins = [names[1]]; + return loadPlugins(hexo); + }) + .then(() => { + should.not.exist(hexo._script_test0); + hexo._script_test1.should.be.true; + + delete hexo.config.plugins; + delete hexo._script_test1; + + return Promise.map(paths, path => fs.unlink(path)); + }); }); it('ignore plugins whose name is not started with "hexo-"', () => { @@ -133,46 +150,55 @@ describe('Load plugins', () => { const name = 'another-plugin'; const path = pathFn.join(hexo.plugin_dir, name, 'index.js'); - return Promise.all([ - createPackageFile(name), - fs.writeFile(path, script) - ]).then(() => loadPlugins(hexo)).then(() => { - should.not.exist(hexo._script_test); - return fs.unlink(path); - }); + return Promise.all([createPackageFile(name), fs.writeFile(path, script)]) + .then(() => loadPlugins(hexo)) + .then(() => { + should.not.exist(hexo._script_test); + return fs.unlink(path); + }); }); - it('ignore plugins which are in package.json but not exist actually', () => createPackageFile('hexo-plugin-test').then(() => loadPlugins(hexo))); + it('ignore plugins which are in package.json but not exist actually', () => + createPackageFile('hexo-plugin-test').then(() => loadPlugins(hexo))); it('load scripts', () => { const path = pathFn.join(hexo.script_dir, 'test.js'); - return fs.writeFile(path, script).then(() => loadPlugins(hexo)).then(() => { - validate(path); - return fs.unlink(path); - }); + return fs + .writeFile(path, script) + .then(() => loadPlugins(hexo)) + .then(() => { + validate(path); + return fs.unlink(path); + }); }); it('load theme scripts', () => { const path = pathFn.join(hexo.theme_script_dir, 'test.js'); - return fs.writeFile(path, script).then(() => loadPlugins(hexo)).then(() => { - validate(path); - return fs.unlink(path); - }); + return fs + .writeFile(path, script) + .then(() => loadPlugins(hexo)) + .then(() => { + validate(path); + return fs.unlink(path); + }); }); - it('don\'t load plugins in safe mode', () => { + it("don't load plugins in safe mode", () => { const script = 'hexo._script_test = true'; const path = pathFn.join(hexo.script_dir, 'test.js'); - return fs.writeFile(path, script).then(() => { - hexo.env.safe = true; - return loadPlugins(hexo); - }).then(() => { - hexo.env.safe = false; - should.not.exist(hexo._script_test); - return fs.unlink(path); - }); + return fs + .writeFile(path, script) + .then(() => { + hexo.env.safe = true; + return loadPlugins(hexo); + }) + .then(() => { + hexo.env.safe = false; + should.not.exist(hexo._script_test); + return fs.unlink(path); + }); }); }); diff --git a/test/scripts/hexo/locals.js b/test/scripts/hexo/locals.js index f1addb2469..097b45fd98 100644 --- a/test/scripts/hexo/locals.js +++ b/test/scripts/hexo/locals.js @@ -92,7 +92,7 @@ describe('Locals', () => { locals.set('foo', 'foo'); locals.set('bar', 'bar'); locals.remove('bar'); - locals.toObject().should.eql({foo: 'foo'}); + locals.toObject().should.eql({ foo: 'foo' }); }); it('invalidate()', () => { diff --git a/test/scripts/hexo/multi_config_path.js b/test/scripts/hexo/multi_config_path.js index 3247c5a3c9..4cbefad3fa 100644 --- a/test/scripts/hexo/multi_config_path.js +++ b/test/scripts/hexo/multi_config_path.js @@ -17,7 +17,7 @@ describe('config flag handling', () => { this.d = function(...args) { const type = 'debug'; let message = ''; - for (let i = 0; i < args.length;) { + for (let i = 0; i < args.length; ) { message += args[i]; if (++i < args.length) { message += ' '; @@ -33,7 +33,7 @@ describe('config flag handling', () => { this.i = function(...args) { const type = 'info'; let message = ''; - for (let i = 0; i < args.length;) { + for (let i = 0; i < args.length; ) { message += args[i]; if (++i < args.length) { message += ' '; @@ -49,7 +49,7 @@ describe('config flag handling', () => { this.w = function(...args) { const type = 'warning'; let message = ''; - for (let i = 0; i < args.length;) { + for (let i = 0; i < args.length; ) { message += args[i]; if (++i < args.length) { message += ' '; @@ -65,7 +65,7 @@ describe('config flag handling', () => { this.e = function(...args) { const type = 'error'; let message = ''; - for (let i = 0; i < args.length;) { + for (let i = 0; i < args.length; ) { message += args[i]; if (++i < args.length) { message += ' '; @@ -148,11 +148,9 @@ describe('config flag handling', () => { }); it('1 file', () => { - mcp(base, 'test1.yml').should.eql( - pathFn.resolve(base + 'test1.yml')); + mcp(base, 'test1.yml').should.eql(pathFn.resolve(base + 'test1.yml')); - mcp(base, 'test1.json').should.eql( - pathFn.resolve(base + 'test1.json')); + mcp(base, 'test1.json').should.eql(pathFn.resolve(base + 'test1.json')); mcp(base, '/tmp/test3.json').should.eql('/tmp/test3.json'); }); @@ -162,8 +160,9 @@ describe('config flag handling', () => { mcp(base, notFile).should.eql(pathFn.join(base, '_config.yml')); hexo.log.reader[0].type.should.eql('warning'); - hexo.log.reader[0].msg.should.eql('Config file ' + notFile - + ' not found, using default.'); + hexo.log.reader[0].msg.should.eql( + 'Config file ' + notFile + ' not found, using default.' + ); }); it('1 not found file warning absolute', () => { @@ -171,8 +170,9 @@ describe('config flag handling', () => { mcp(base, notFile).should.eql(pathFn.join(base, '_config.yml')); hexo.log.reader[0].type.should.eql('warning'); - hexo.log.reader[0].msg.should.eql('Config file ' + notFile - + ' not found, using default.'); + hexo.log.reader[0].msg.should.eql( + 'Config file ' + notFile + ' not found, using default.' + ); }); it('combined config output', () => { @@ -194,8 +194,9 @@ describe('config flag handling', () => { mcp(base, 'notafile.yml,alsonotafile.json').should.not.eql(combinedPath); hexo.log.reader[11].type.should.eql('error'); - hexo.log.reader[11].msg.should.eql('No config files found.' - + ' Using _config.yml.'); + hexo.log.reader[11].msg.should.eql( + 'No config files found. Using _config.yml.' + ); }); it('combine config output with absolute paths', () => { @@ -264,10 +265,14 @@ describe('config flag handling', () => { mcp(base, 'test1.yml,test1.json', outputPath).should.eql(combinedPath); mcp(base, 'test1.json,test2.json', outputPath).should.eql(combinedPath); mcp(base, 'notafile.yml,test1.json', outputPath).should.eql(combinedPath); - mcp(base, 'notafile.yml,alsonotafile.json', outputPath).should.not.eql(combinedPath); + mcp(base, 'notafile.yml,alsonotafile.json', outputPath).should.not.eql( + combinedPath + ); hexo.log.reader[1].type.should.eql('debug'); - hexo.log.reader[1].msg.should.eql(`Writing _multiconfig.yml to ${combinedPath}`); + hexo.log.reader[1].msg.should.eql( + `Writing _multiconfig.yml to ${combinedPath}` + ); hexo.log.reader[2].type.should.eql('info'); hexo.log.reader[2].msg.should.eql('Config based on 2 files'); hexo.log.reader[6].type.should.eql('warning'); @@ -275,7 +280,8 @@ describe('config flag handling', () => { hexo.log.reader[7].type.should.eql('info'); hexo.log.reader[7].msg.should.eql('Config based on 1 files'); hexo.log.reader[11].type.should.eql('error'); - hexo.log.reader[11].msg.should.eql('No config files found.' - + ' Using _config.yml.'); + hexo.log.reader[11].msg.should.eql( + 'No config files found. Using _config.yml.' + ); }); }); diff --git a/test/scripts/hexo/post.js b/test/scripts/hexo/post.js index c65ec59d98..c3781ade12 100644 --- a/test/scripts/hexo/post.js +++ b/test/scripts/hexo/post.js @@ -19,19 +19,30 @@ describe('Post', () => { before(() => { clock = sinon.useFakeTimers(now); - return fs.mkdirs(hexo.base_dir, () => hexo.init()).then(() => // Load marked renderer for testing - hexo.loadPlugin(require.resolve('hexo-renderer-marked'))).then(() => hexo.scaffold.set('post', [ - '---', - 'title: {{ title }}', - 'date: {{ date }}', - 'tags:', - '---' - ].join('\n'))).then(() => hexo.scaffold.set('draft', [ - '---', - 'title: {{ title }}', - 'tags:', - '---' - ].join('\n'))); + return fs + .mkdirs(hexo.base_dir, () => hexo.init()) + .then(() => + // Load marked renderer for testing + hexo.loadPlugin(require.resolve('hexo-renderer-marked')) + ) + .then(() => + hexo.scaffold.set( + 'post', + [ + '---', + 'title: {{ title }}', + 'date: {{ date }}', + 'tags:', + '---' + ].join('\n') + ) + ) + .then(() => + hexo.scaffold.set( + 'draft', + ['---', 'title: {{ title }}', 'tags:', '---'].join('\n') + ) + ); }); after(() => { @@ -44,54 +55,62 @@ describe('Post', () => { const date = moment(now); const listener = sinon.spy(); - const content = [ - '---', - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; + const content = + [ + '---', + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; hexo.once('new', listener); - return post.create({ - title: 'Hello World' - }).then(post => { - post.path.should.eql(path); - post.content.should.eql(content); - listener.calledOnce.should.be.true; - - return fs.readFile(path); - }).then(data => { - data.should.eql(content); - return fs.unlink(path); - }); + return post + .create({ + title: 'Hello World' + }) + .then(post => { + post.path.should.eql(path); + post.content.should.eql(content); + listener.calledOnce.should.be.true; + + return fs.readFile(path); + }) + .then(data => { + data.should.eql(content); + return fs.unlink(path); + }); }); it('create() - slug', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'foo.md'); const date = moment(now); - const content = [ - '---', - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; - - return post.create({ - title: 'Hello World', - slug: 'foo' - }).then(post => { - post.path.should.eql(path); - post.content.should.eql(content); - - return fs.readFile(path); - }).then(data => { - data.should.eql(content); - return fs.unlink(path); - }); + const content = + [ + '---', + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; + + return post + .create({ + title: 'Hello World', + slug: 'foo' + }) + .then(post => { + post.path.should.eql(path); + post.content.should.eql(content); + + return fs.readFile(path); + }) + .then(data => { + data.should.eql(content); + return fs.unlink(path); + }); }); it('create() - filename_case', () => { @@ -100,113 +119,139 @@ describe('Post', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'hello-world.md'); const date = moment(now); - const content = [ - '---', - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; - - return post.create({ - title: 'Hello World' - }).then(post => { - post.path.should.eql(path); - post.content.should.eql(content); - hexo.config.filename_case = 0; - - return fs.readFile(path); - }).then(data => { - data.should.eql(content); - return fs.unlink(path); - }); + const content = + [ + '---', + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; + + return post + .create({ + title: 'Hello World' + }) + .then(post => { + post.path.should.eql(path); + post.content.should.eql(content); + hexo.config.filename_case = 0; + + return fs.readFile(path); + }) + .then(data => { + data.should.eql(content); + return fs.unlink(path); + }); }); it('create() - layout', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); const date = moment(now); - const content = [ - '---', - 'layout: photo', - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; - - return post.create({ - title: 'Hello World', - layout: 'photo' - }).then(post => { - post.path.should.eql(path); - post.content.should.eql(content); - - return fs.readFile(path); - }).then(data => { - data.should.eql(content); - return fs.unlink(path); - }); + const content = + [ + '---', + 'layout: photo', + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; + + return post + .create({ + title: 'Hello World', + layout: 'photo' + }) + .then(post => { + post.path.should.eql(path); + post.content.should.eql(content); + + return fs.readFile(path); + }) + .then(data => { + data.should.eql(content); + return fs.unlink(path); + }); }); it('create() - extra data', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); const date = moment(now); - const content = [ - '---', - 'title: Hello World', - 'foo: bar', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; - - return post.create({ - title: 'Hello World', - foo: 'bar' - }).then(post => { - post.path.should.eql(path); - post.content.should.eql(content); - - return fs.readFile(path); - }).then(data => { - data.should.eql(content); - return fs.unlink(path); - }); + const content = + [ + '---', + 'title: Hello World', + 'foo: bar', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; + + return post + .create({ + title: 'Hello World', + foo: 'bar' + }) + .then(post => { + post.path.should.eql(path); + post.content.should.eql(content); + + return fs.readFile(path); + }) + .then(data => { + data.should.eql(content); + return fs.unlink(path); + }); }); it('create() - rename if target existed', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World-1.md'); - return post.create({ - title: 'Hello World' - }).then(() => post.create({ - title: 'Hello World' - })).then(post => { - post.path.should.eql(path); - return fs.exists(path); - }).then(exist => { - exist.should.be.true; - - return Promise.all([ - fs.unlink(path), - fs.unlink(pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md')) - ]); - }); + return post + .create({ + title: 'Hello World' + }) + .then(() => + post.create({ + title: 'Hello World' + }) + ) + .then(post => { + post.path.should.eql(path); + return fs.exists(path); + }) + .then(exist => { + exist.should.be.true; + + return Promise.all([ + fs.unlink(path), + fs.unlink(pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md')) + ]); + }); }); it('create() - replace existing files', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); - return post.create({ - title: 'Hello World' - }).then(() => post.create({ - title: 'Hello World' - }, true)).then(post => { - post.path.should.eql(path); - return fs.unlink(path); - }); + return post + .create({ + title: 'Hello World' + }) + .then(() => + post.create( + { + title: 'Hello World' + }, + true + ) + ) + .then(post => { + post.path.should.eql(path); + return fs.unlink(path); + }); }); it('create() - asset folder', () => { @@ -214,90 +259,99 @@ describe('Post', () => { hexo.config.post_asset_folder = true; - return post.create({ - title: 'Hello World' - }).then(post => { - hexo.config.post_asset_folder = false; - return fs.stat(path); - }).then(stats => { - stats.isDirectory().should.be.true; - return fs.unlink(path + '.md'); - }); + return post + .create({ + title: 'Hello World' + }) + .then(post => { + hexo.config.post_asset_folder = false; + return fs.stat(path); + }) + .then(stats => { + stats.isDirectory().should.be.true; + return fs.unlink(path + '.md'); + }); }); it('create() - follow the separator style in the scaffold', () => { - const scaffold = [ - '---', - 'title: {{ title }}', - '---' - ].join('\n'); - - return hexo.scaffold.set('test', scaffold).then(() => post.create({ - title: 'Hello World', - layout: 'test' - })).then(post => { - post.content.should.eql([ - '---', - 'title: Hello World', - '---' - ].join('\n') + '\n'); - - return Promise.all([ - fs.unlink(post.path), - hexo.scaffold.remove('test') - ]); - }); + const scaffold = ['---', 'title: {{ title }}', '---'].join('\n'); + + return hexo.scaffold + .set('test', scaffold) + .then(() => + post.create({ + title: 'Hello World', + layout: 'test' + }) + ) + .then(post => { + post.content.should.eql( + ['---', 'title: Hello World', '---'].join('\n') + '\n' + ); + + return Promise.all([ + fs.unlink(post.path), + hexo.scaffold.remove('test') + ]); + }); }); it('create() - JSON front-matter', () => { - const scaffold = [ - '"title": {{ title }}', - ';;;' - ].join('\n'); - - return hexo.scaffold.set('test', scaffold).then(() => post.create({ - title: 'Hello World', - layout: 'test', - lang: 'en' - })).then(post => { - post.content.should.eql([ - '"title": "Hello World",', - '"lang": "en"', - ';;;' - ].join('\n') + '\n'); - - return Promise.all([ - fs.unlink(post.path), - hexo.scaffold.remove('test') - ]); - }); + const scaffold = ['"title": {{ title }}', ';;;'].join('\n'); + + return hexo.scaffold + .set('test', scaffold) + .then(() => + post.create({ + title: 'Hello World', + layout: 'test', + lang: 'en' + }) + ) + .then(post => { + post.content.should.eql( + ['"title": "Hello World",', '"lang": "en"', ';;;'].join('\n') + '\n' + ); + + return Promise.all([ + fs.unlink(post.path), + hexo.scaffold.remove('test') + ]); + }); }); // https://github.com/hexojs/hexo/issues/1100 it('create() - non-string title', () => { const path = pathFn.join(hexo.source_dir, '_posts', '12345.md'); - return post.create({ - title: 12345 - }).then(data => { - data.path.should.eql(path); - return fs.unlink(path); - }); + return post + .create({ + title: 12345 + }) + .then(data => { + data.path.should.eql(path); + return fs.unlink(path); + }); }); - it('create() - escape title', () => post.create({ - title: 'Foo: Bar' - }).then(data => { - data.content.should.eql([ - // js-yaml use single-quotation for dumping since 3.3 - '---', - 'title: \'Foo: Bar\'', - 'date: ' + moment(now).format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'); - return fs.unlink(data.path); - })); + it('create() - escape title', () => + post + .create({ + title: 'Foo: Bar' + }) + .then(data => { + data.content.should.eql( + [ + // js-yaml use single-quotation for dumping since 3.3 + '---', + "title: 'Foo: Bar'", + 'date: ' + moment(now).format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n' + ); + return fs.unlink(data.path); + })); it('create() - with content', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); @@ -313,46 +367,56 @@ describe('Post', () => { 'Hello hexo' ].join('\n'); - return post.create({ - title: 'Hello World', - content: 'Hello hexo' - }).then(post => { - post.path.should.eql(path); - post.content.should.eql(content); - - return fs.readFile(path); - }).then(data => { - data.should.eql(content); - return fs.unlink(path); - }); + return post + .create({ + title: 'Hello World', + content: 'Hello hexo' + }) + .then(post => { + post.path.should.eql(path); + post.content.should.eql(content); + + return fs.readFile(path); + }) + .then(data => { + data.should.eql(content); + return fs.unlink(path); + }); }); it('create() - with callback', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); const date = moment(now); - const content = [ - '---', - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; + const content = + [ + '---', + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; const callback = sinon.spy(post => { post.path.should.eql(path); post.content.should.eql(content); }); - return post.create({ - title: 'Hello World' - }, callback).then(post => { - callback.calledOnce.should.be.true; - return fs.readFile(path); - }).then(data => { - data.should.eql(content); - return fs.unlink(path); - }); + return post + .create( + { + title: 'Hello World' + }, + callback + ) + .then(post => { + callback.calledOnce.should.be.true; + return fs.readFile(path); + }) + .then(data => { + data.should.eql(content); + return fs.unlink(path); + }); }); it('publish()', () => { @@ -360,100 +424,119 @@ describe('Post', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); const date = moment(now); - const content = [ - '---', - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; - - return post.create({ - title: 'Hello World', - layout: 'draft' - }).then(data => { - draftPath = data.path; - - return post.publish({ - slug: 'Hello-World' + const content = + [ + '---', + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; + + return post + .create({ + title: 'Hello World', + layout: 'draft' + }) + .then(data => { + draftPath = data.path; + + return post.publish({ + slug: 'Hello-World' + }); + }) + .then(post => { + post.path.should.eql(path); + post.content.should.eql(content); + + return Promise.all([fs.exists(draftPath), fs.readFile(path)]); + }) + .spread((exist, data) => { + exist.should.be.false; + data.should.eql(content); + + return fs.unlink(path); }); - }).then(post => { - post.path.should.eql(path); - post.content.should.eql(content); - - return Promise.all([ - fs.exists(draftPath), - fs.readFile(path) - ]); - }).spread((exist, data) => { - exist.should.be.false; - data.should.eql(content); - - return fs.unlink(path); - }); }); it('publish() - layout', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); const date = moment(now); - const content = [ - '---', - 'layout: photo', - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; - - return post.create({ - title: 'Hello World', - layout: 'draft' - }).then(data => post.publish({ - slug: 'Hello-World', - layout: 'photo' - })).then(post => { - post.path.should.eql(path); - post.content.should.eql(content); - - return fs.readFile(path); - }).then(data => { - data.should.eql(content); - - return fs.unlink(path); - }); + const content = + [ + '---', + 'layout: photo', + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; + + return post + .create({ + title: 'Hello World', + layout: 'draft' + }) + .then(data => + post.publish({ + slug: 'Hello-World', + layout: 'photo' + }) + ) + .then(post => { + post.path.should.eql(path); + post.content.should.eql(content); + + return fs.readFile(path); + }) + .then(data => { + data.should.eql(content); + + return fs.unlink(path); + }); }); it('publish() - rename if target existed', () => { const paths = [pathFn.join(hexo.source_dir, '_posts', 'Hello-World-1.md')]; return Promise.all([ - post.create({title: 'Hello World', layout: 'draft'}), - post.create({title: 'Hello World'}) - ]).then(data => { - paths.push(data[1].path); - - return post.publish({ - slug: 'Hello-World' - }); - }).then(data => { - data.path.should.eql(paths[0]); - return paths; - }).map(item => fs.unlink(item)); + post.create({ title: 'Hello World', layout: 'draft' }), + post.create({ title: 'Hello World' }) + ]) + .then(data => { + paths.push(data[1].path); + + return post.publish({ + slug: 'Hello-World' + }); + }) + .then(data => { + data.path.should.eql(paths[0]); + return paths; + }) + .map(item => fs.unlink(item)); }); it('publish() - replace existing files', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); return Promise.all([ - post.create({title: 'Hello World', layout: 'draft'}), - post.create({title: 'Hello World'}) - ]).then(data => post.publish({ - slug: 'Hello-World' - }, true)).then(data => { - data.path.should.eql(path); - return fs.unlink(path); - }); + post.create({ title: 'Hello World', layout: 'draft' }), + post.create({ title: 'Hello World' }) + ]) + .then(data => + post.publish( + { + slug: 'Hello-World' + }, + true + ) + ) + .then(data => { + data.path.should.eql(path); + return fs.unlink(path); + }); }); it('publish() - asset folder', () => { @@ -461,40 +544,57 @@ describe('Post', () => { const newAssetDir = pathFn.join(hexo.source_dir, '_posts', 'Hello-World'); hexo.config.post_asset_folder = true; - return post.create({ - title: 'Hello World', - layout: 'draft' - }).then(data => // Put some files into the asset folder - Promise.all([ - fs.writeFile(pathFn.join(assetDir, 'a.txt'), 'a'), - fs.writeFile(pathFn.join(assetDir, 'b.txt'), 'b') - ])).then(() => post.publish({ - slug: 'Hello-World' - })).then(post => Promise.all([ - fs.exists(assetDir), - fs.listDir(newAssetDir), - fs.unlink(post.path) - ])).spread((exist, files) => { - hexo.config.post_asset_folder = false; - exist.should.be.false; - files.should.have.members(['a.txt', 'b.txt']); - return fs.rmdir(newAssetDir); - }); + return post + .create({ + title: 'Hello World', + layout: 'draft' + }) + .then(( + data // Put some files into the asset folder + ) => + Promise.all([ + fs.writeFile(pathFn.join(assetDir, 'a.txt'), 'a'), + fs.writeFile(pathFn.join(assetDir, 'b.txt'), 'b') + ]) + ) + .then(() => + post.publish({ + slug: 'Hello-World' + }) + ) + .then(post => + Promise.all([ + fs.exists(assetDir), + fs.listDir(newAssetDir), + fs.unlink(post.path) + ]) + ) + .spread((exist, files) => { + hexo.config.post_asset_folder = false; + exist.should.be.false; + files.should.have.members(['a.txt', 'b.txt']); + return fs.rmdir(newAssetDir); + }); }); // https://github.com/hexojs/hexo/issues/1100 it('publish() - non-string title', () => { const path = pathFn.join(hexo.source_dir, '_posts', '12345.md'); - return post.create({ - title: 12345, - layout: 'draft' - }).then(data => post.publish({ - slug: 12345 - })).then(data => { - data.path.should.eql(path); - return fs.unlink(path); - }); + return post + .create({ + title: 12345, + layout: 'draft' + }) + .then(data => + post.publish({ + slug: 12345 + }) + ) + .then(data => { + data.path.should.eql(path); + return fs.unlink(path); + }); }); it('publish() - with callback', () => { @@ -502,55 +602,66 @@ describe('Post', () => { const path = pathFn.join(hexo.source_dir, '_posts', 'Hello-World.md'); const date = moment(now); - const content = [ - '---', - 'title: Hello World', - 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), - 'tags:', - '---' - ].join('\n') + '\n'; + const content = + [ + '---', + 'title: Hello World', + 'date: ' + date.format('YYYY-MM-DD HH:mm:ss'), + 'tags:', + '---' + ].join('\n') + '\n'; const callback = sinon.spy(post => { post.path.should.eql(path); post.content.should.eql(content); }); - return post.create({ - title: 'Hello World', - layout: 'draft' - }).then(data => { - draftPath = data.path; - - return post.publish({ - slug: 'Hello-World' - }, callback); - }).then(post => { - callback.calledOnce.should.be.true; - - return Promise.all([ - fs.exists(draftPath), - fs.readFile(path) - ]); - }).spread((exist, data) => { - exist.should.be.false; - data.should.eql(content); - - return fs.unlink(path); - }); + return post + .create({ + title: 'Hello World', + layout: 'draft' + }) + .then(data => { + draftPath = data.path; + + return post.publish( + { + slug: 'Hello-World' + }, + callback + ); + }) + .then(post => { + callback.calledOnce.should.be.true; + + return Promise.all([fs.exists(draftPath), fs.readFile(path)]); + }) + .spread((exist, data) => { + exist.should.be.false; + data.should.eql(content); + + return fs.unlink(path); + }); }); // https://github.com/hexojs/hexo/issues/1139 - it('publish() - preserve non-null data in drafts', () => post.create({ - title: 'foo', - layout: 'draft', - tags: ['tag', 'test'] - }).then(data => post.publish({ - slug: 'foo' - })).then(data => { - const meta = frontMatter(data.content); - meta.tags.should.eql(['tag', 'test']); - return fs.unlink(data.path); - })); + it('publish() - preserve non-null data in drafts', () => + post + .create({ + title: 'foo', + layout: 'draft', + tags: ['tag', 'test'] + }) + .then(data => + post.publish({ + slug: 'foo' + }) + ) + .then(data => { + const meta = frontMatter(data.content); + meta.tags.should.eql(['tag', 'test']); + return fs.unlink(data.path); + })); it('render()', () => { // TODO: validate data @@ -560,62 +671,79 @@ describe('Post', () => { hexo.extend.filter.register('before_post_render', beforeHook); hexo.extend.filter.register('after_post_render', afterHook); - return post.render(null, { - content: fixture.content, - engine: 'markdown' - }).then(data => { - data.content.trim().should.eql(fixture.expected); - beforeHook.calledOnce.should.be.true; - afterHook.calledOnce.should.be.true; - }); + return post + .render(null, { + content: fixture.content, + engine: 'markdown' + }) + .then(data => { + data.content.trim().should.eql(fixture.expected); + beforeHook.calledOnce.should.be.true; + afterHook.calledOnce.should.be.true; + }); }); it('render() - callback', done => { - post.render(null, { - content: fixture.content, - engine: 'markdown' - }, err => { - done(err); - }); + post.render( + null, + { + content: fixture.content, + engine: 'markdown' + }, + err => { + done(err); + } + ); }); it('render() - file', () => { const content = '**file test**'; const path = pathFn.join(hexo.base_dir, 'render_test.md'); - return fs.writeFile(path, content).then(() => post.render(path)).then(data => { - data.content.trim().should.eql('file test
'); - return fs.unlink(path); - }); + return fs + .writeFile(path, content) + .then(() => post.render(path)) + .then(data => { + data.content.trim().should.eql('file test
'); + return fs.unlink(path); + }); }); it('render() - toString', () => { const content = 'foo: 1'; - return post.render(null, { - content, - engine: 'yaml' - }).then(data => { - data.content.should.eql('{"foo":1}'); - }); + return post + .render(null, { + content, + engine: 'yaml' + }) + .then(data => { + data.content.should.eql('{"foo":1}'); + }); }); - it('render() - skip render phase if it\'s swig file', () => { + it("render() - skip render phase if it's swig file", () => { const content = [ '{% quote Hello World %}', 'quote content', '{% endquote %}' ].join('\n'); - return post.render(null, { - content, - engine: 'swig' - }).then(data => { - data.content.trim().should.eql([ - '' - ].join('')); - }); + return post + .render(null, { + content, + engine: 'swig' + }) + .then(data => { + data.content + .trim() + .should.eql( + [ + 'quote content
\n', - '' + ].join('') + ); + }); }); it('render() - escaping swig blocks with similar names', () => { @@ -632,26 +760,28 @@ describe('Post', () => { '{% endcode %}' ].join('\n'); - return post.render(null, { - content - }).then(data => { - data.content.trim().should.eql([ - highlighted, - '', - highlighted - ].join('\n')); - }); + return post + .render(null, { + content + }) + .then(data => { + data.content + .trim() + .should.eql([highlighted, '', highlighted].join('\n')); + }); }); it('render() - recover escaped swig blocks which is html escaped', () => { const content = '`{% raw %}{{ test }}{% endraw %}`'; - return post.render(null, { - content, - engine: 'markdown' - }).then(data => { - data.content.trim().should.eql('quote content
\n', + ''); - }); + return post + .render(null, { + content, + engine: 'markdown' + }) + .then(data => { + data.content.trim().should.eql('
{{ test }}
'); + }); }); it('render() - recover escaped swig blocks which is html escaped before post_render', () => { @@ -663,13 +793,15 @@ describe('Post', () => { hexo.extend.filter.register('after_render:html', filter); - return post.render(null, { - content, - engine: 'markdown' - }).then(data => { - filter.calledOnce.should.be.true; - hexo.extend.filter.unregister('after_render:html', filter); - }); + return post + .render(null, { + content, + engine: 'markdown' + }) + .then(data => { + filter.calledOnce.should.be.true; + hexo.extend.filter.unregister('after_render:html', filter); + }); }); it('render() - callback - not path and file', callback => { @@ -692,14 +824,17 @@ describe('Post', () => { const renderer = hexo.render.renderer.get('markdown'); renderer.disableNunjucks = true; - return post.render(null, { - content: fixture.content, - engine: 'markdown' - }).then(data => { - data.content.trim().should.eql(fixture.expected_disable_nunjucks); - }).then(data => { - renderer.disableNunjucks = false; - }); + return post + .render(null, { + content: fixture.content, + engine: 'markdown' + }) + .then(data => { + data.content.trim().should.eql(fixture.expected_disable_nunjucks); + }) + .then(data => { + renderer.disableNunjucks = false; + }); }); // test for PR [#3573](https://github.com/hexojs/hexo/pull/3573) @@ -707,14 +842,16 @@ describe('Post', () => { const renderer = hexo.render.renderer.get('markdown'); renderer.disableNunjucks = false; - return post.render(null, { - content: fixture.content, - engine: 'markdown' - }).then(data => { - data.content.trim().should.eql(fixture.expected); - }).then(data => { - renderer.disableNunjucks = false; - }); + return post + .render(null, { + content: fixture.content, + engine: 'markdown' + }) + .then(data => { + data.content.trim().should.eql(fixture.expected); + }) + .then(data => { + renderer.disableNunjucks = false; + }); }); - }); diff --git a/test/scripts/hexo/render.js b/test/scripts/hexo/render.js index 0c29203314..13fa115b2c 100644 --- a/test/scripts/hexo/render.js +++ b/test/scripts/hexo/render.js @@ -75,61 +75,78 @@ describe('Render', () => { hexo.render.getOutput('test.yaml').should.eql('json'); }); - it('render() - path', () => hexo.render.render({path}).then(result => { - result.should.eql(obj); - })); + it('render() - path', () => + hexo.render.render({ path }).then(result => { + result.should.eql(obj); + })); - it('render() - text (without engine)', () => hexo.render.render({text: body}).then(result => { - result.should.eql(body); - })); + it('render() - text (without engine)', () => + hexo.render.render({ text: body }).then(result => { + result.should.eql(body); + })); - it('render() - text (with engine)', () => hexo.render.render({text: body, engine: 'yaml'}).then(result => { - result.should.eql(obj); - })); + it('render() - text (with engine)', () => + hexo.render.render({ text: body, engine: 'yaml' }).then(result => { + result.should.eql(obj); + })); it('render() - no path and text', () => { const errorCallback = sinon.spy(err => { err.should.have.property('message', 'No input file or string!'); }); - return hexo.render.render().catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + return hexo.render + .render() + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); - it('render() - options', () => hexo.render.render({ - text: [ - '
{{ test }}
{{ title }} ', - '{{ content }}' - ].join('\n'), - engine: 'swig' - }, { - title: 'Hello world', - content: 'foobar' - }).then(result => { - result.should.eql([ - 'Hello world ', - 'foobar' - ].join('\n')); - })); - - it('render() - toString', () => hexo.render.render({ - text: body, - engine: 'yaml', - toString: true - }).then(content => { - content.should.eql(JSON.stringify(obj)); - })); - - it('render() - custom toString method', () => hexo.render.render({ - text: body, - engine: 'yaml', - toString(data) { - return JSON.stringify(data, null, ' '); - } - }).then(content => { - content.should.eql(JSON.stringify(obj, null, ' ')); - })); + it('render() - options', () => + hexo.render + .render( + { + text: [ + '{{ title }} ', + '{{ content }}' + ].join('\n'), + engine: 'swig' + }, + { + title: 'Hello world', + content: 'foobar' + } + ) + .then(result => { + result.should.eql( + ['Hello world ', 'foobar'].join('\n') + ); + })); + + it('render() - toString', () => + hexo.render + .render({ + text: body, + engine: 'yaml', + toString: true + }) + .then(content => { + content.should.eql(JSON.stringify(obj)); + })); + + it('render() - custom toString method', () => + hexo.render + .render({ + text: body, + engine: 'yaml', + toString(data) { + return JSON.stringify(data, null, ' '); + } + }) + .then(content => { + content.should.eql(JSON.stringify(obj, null, ' ')); + })); it('render() - after_render filter', () => { const data = { @@ -192,17 +209,17 @@ describe('Render', () => { }); it('renderSync() - path', () => { - const result = hexo.render.renderSync({path}); + const result = hexo.render.renderSync({ path }); result.should.eql(obj); }); it('renderSync() - text (without engine)', () => { - const result = hexo.render.renderSync({text: body}); + const result = hexo.render.renderSync({ text: body }); result.should.eql(body); }); it('renderSync() - text (with engine)', () => { - const result = hexo.render.renderSync({text: body, engine: 'yaml'}); + const result = hexo.render.renderSync({ text: body, engine: 'yaml' }); result.should.eql(obj); }); @@ -221,21 +238,22 @@ describe('Render', () => { }); it('renderSync() - options', () => { - const result = hexo.render.renderSync({ - text: [ - '{{ title }} ', - '{{ content }}' - ].join('\n'), - engine: 'swig' - }, { - title: 'Hello world', - content: 'foobar' - }); + const result = hexo.render.renderSync( + { + text: ['{{ title }} ', '{{ content }}'].join( + '\n' + ), + engine: 'swig' + }, + { + title: 'Hello world', + content: 'foobar' + } + ); - result.should.eql([ - 'Hello world ', - 'foobar' - ].join('\n')); + result.should.eql( + ['Hello world ', 'foobar'].join('\n') + ); }); it('renderSync() - toString', () => { diff --git a/test/scripts/hexo/router.js b/test/scripts/hexo/router.js index eb46e74fd4..a572d93153 100644 --- a/test/scripts/hexo/router.js +++ b/test/scripts/hexo/router.js @@ -22,15 +22,18 @@ describe('Router', () => { return new Promise((resolve, reject) => { const hash = crypto.createHash('sha1'); - stream.on('readable', () => { - let chunk; - - while ((chunk = stream.read()) !== null) { - hash.update(chunk); - } - }).on('end', () => { - resolve(hash.digest('hex')); - }).on('error', reject); + stream + .on('readable', () => { + let chunk; + + while ((chunk = stream.read()) !== null) { + hash.update(chunk); + } + }) + .on('end', () => { + resolve(hash.digest('hex')); + }) + .on('error', reject); }); } @@ -156,15 +159,16 @@ describe('Router', () => { err.should.have.property('message', 'error test'); }); - return testUtil.stream.read(router.get('test')).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + return testUtil.stream + .read(router.get('test')) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); it('get() - no data', () => { - router.set('test', () => { - - }); + router.set('test', () => {}); return checkStream(router.get('test'), ''); }); @@ -206,7 +210,7 @@ describe('Router', () => { }); it('get() - export stringified JSON object', () => { - const obj = {foo: 1, bar: 2}; + const obj = { foo: 1, bar: 2 }; router.set('test', () => obj); diff --git a/test/scripts/hexo/scaffold.js b/test/scripts/hexo/scaffold.js index 26b0fe93a3..c651985b48 100644 --- a/test/scripts/hexo/scaffold.js +++ b/test/scripts/hexo/scaffold.js @@ -23,44 +23,48 @@ describe('Scaffold', () => { after(() => fs.rmdir(scaffoldDir)); - it('get() - file exists', () => scaffold.get('test').then(data => { - data.should.eql(testContent); - })); + it('get() - file exists', () => + scaffold.get('test').then(data => { + data.should.eql(testContent); + })); - it('get() - normal scaffold', () => scaffold.get('normal').then(data => { - data.should.eql(scaffold.defaults.normal); - })); + it('get() - normal scaffold', () => + scaffold.get('normal').then(data => { + data.should.eql(scaffold.defaults.normal); + })); - it('set() - file exists', () => scaffold.set('test', 'foo').then(() => Promise.all([ - fs.readFile(testPath), - scaffold.get('test') - ])).spread((file, data) => { - file.should.eql('foo'); - data.should.eql('foo'); - return fs.writeFile(testPath, testContent); - })); + it('set() - file exists', () => + scaffold + .set('test', 'foo') + .then(() => Promise.all([fs.readFile(testPath), scaffold.get('test')])) + .spread((file, data) => { + file.should.eql('foo'); + data.should.eql('foo'); + return fs.writeFile(testPath, testContent); + })); it('set() - file does not exist', () => { const testPath = pathFn.join(scaffoldDir, 'foo.md'); - return scaffold.set('foo', 'bar').then(() => Promise.all([ - fs.readFile(testPath), - scaffold.get('foo') - ])).spread((file, data) => { - file.should.eql('bar'); - data.should.eql('bar'); - return fs.unlink(testPath); - }); + return scaffold + .set('foo', 'bar') + .then(() => Promise.all([fs.readFile(testPath), scaffold.get('foo')])) + .spread((file, data) => { + file.should.eql('bar'); + data.should.eql('bar'); + return fs.unlink(testPath); + }); }); - it('remove() - file exist', () => scaffold.remove('test').then(() => Promise.all([ - fs.exists(testPath), - scaffold.get('test') - ])).spread((exist, data) => { - exist.should.be.false; - should.not.exist(data); - return fs.writeFile(testPath, testContent); - })); + it('remove() - file exist', () => + scaffold + .remove('test') + .then(() => Promise.all([fs.exists(testPath), scaffold.get('test')])) + .spread((exist, data) => { + exist.should.be.false; + should.not.exist(data); + return fs.writeFile(testPath, testContent); + })); it('remove() - file does not exist', () => scaffold.remove('foo')); }); diff --git a/test/scripts/hexo/update_package.js b/test/scripts/hexo/update_package.js index 66f027b478..52dc80904a 100644 --- a/test/scripts/hexo/update_package.js +++ b/test/scripts/hexo/update_package.js @@ -5,7 +5,7 @@ const fs = require('hexo-fs'); describe('Update package.json', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(__dirname, {silent: true}); + const hexo = new Hexo(__dirname, { silent: true }); const updatePkg = require('../../../lib/hexo/update_package'); const packagePath = pathFn.join(hexo.base_dir, 'package.json'); @@ -13,38 +13,47 @@ describe('Update package.json', () => { hexo.env.init = false; }); - it('package.json does not exist', () => updatePkg(hexo).then(() => { - hexo.env.init.should.be.false; - })); + it('package.json does not exist', () => + updatePkg(hexo).then(() => { + hexo.env.init.should.be.false; + })); - it('package.json exists, but the version doesn\'t match', () => { + it("package.json exists, but the version doesn't match", () => { const pkg = { hexo: { version: '0.0.1' } }; - return fs.writeFile(packagePath, JSON.stringify(pkg)).then(() => updatePkg(hexo)).then(() => fs.readFile(packagePath)).then(content => { - JSON.parse(content).hexo.version.should.eql(hexo.version); - hexo.env.init.should.be.true; + return fs + .writeFile(packagePath, JSON.stringify(pkg)) + .then(() => updatePkg(hexo)) + .then(() => fs.readFile(packagePath)) + .then(content => { + JSON.parse(content).hexo.version.should.eql(hexo.version); + hexo.env.init.should.be.true; - return fs.unlink(packagePath); - }); + return fs.unlink(packagePath); + }); }); - it('package.json exists, but don\'t have hexo data', () => { + it("package.json exists, but don't have hexo data", () => { const pkg = { name: 'hexo', version: '0.0.1' }; - return fs.writeFile(packagePath, JSON.stringify(pkg)).then(() => updatePkg(hexo)).then(() => fs.readFile(packagePath)).then(content => { - // Don't change the original package.json - JSON.parse(content).should.eql(pkg); - hexo.env.init.should.be.false; + return fs + .writeFile(packagePath, JSON.stringify(pkg)) + .then(() => updatePkg(hexo)) + .then(() => fs.readFile(packagePath)) + .then(content => { + // Don't change the original package.json + JSON.parse(content).should.eql(pkg); + hexo.env.init.should.be.false; - return fs.unlink(packagePath); - }); + return fs.unlink(packagePath); + }); }); it('package.json exists and everything is ok', () => { @@ -54,11 +63,15 @@ describe('Update package.json', () => { } }; - return fs.writeFile(packagePath, JSON.stringify(pkg)).then(() => updatePkg(hexo)).then(() => fs.readFile(packagePath)).then(content => { - JSON.parse(content).should.eql(pkg); - hexo.env.init.should.be.true; + return fs + .writeFile(packagePath, JSON.stringify(pkg)) + .then(() => updatePkg(hexo)) + .then(() => fs.readFile(packagePath)) + .then(content => { + JSON.parse(content).should.eql(pkg); + hexo.env.init.should.be.true; - return fs.unlink(packagePath); - }); + return fs.unlink(packagePath); + }); }); }); diff --git a/test/scripts/models/asset.js b/test/scripts/models/asset.js index 0182dbe464..d5a65607b5 100644 --- a/test/scripts/models/asset.js +++ b/test/scripts/models/asset.js @@ -8,22 +8,25 @@ describe('Asset', () => { const hexo = new Hexo(); const Asset = hexo.model('Asset'); - it('default values', () => Asset.insert({ - _id: 'foo', - path: 'bar' - }).then(data => { - data.modified.should.be.true; - return Asset.removeById(data._id); - })); + it('default values', () => + Asset.insert({ + _id: 'foo', + path: 'bar' + }).then(data => { + data.modified.should.be.true; + return Asset.removeById(data._id); + })); it('_id - required', () => { const errorCallback = sinon.spy(err => { err.should.have.property('message', 'ID is not defined'); }); - return Asset.insert({}).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + return Asset.insert({}) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); it('path - required', () => { @@ -33,16 +36,19 @@ describe('Asset', () => { return Asset.insert({ _id: 'foo' - }).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + }) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); - it('source - virtual', () => Asset.insert({ - _id: 'foo', - path: 'bar' - }).then(data => { - data.source.should.eql(pathFn.join(hexo.base_dir, data._id)); - return Asset.removeById(data._id); - })); + it('source - virtual', () => + Asset.insert({ + _id: 'foo', + path: 'bar' + }).then(data => { + data.source.should.eql(pathFn.join(hexo.base_dir, data._id)); + return Asset.removeById(data._id); + })); }); diff --git a/test/scripts/models/cache.js b/test/scripts/models/cache.js index 6a3c00d4c0..4e5718800c 100644 --- a/test/scripts/models/cache.js +++ b/test/scripts/models/cache.js @@ -12,8 +12,10 @@ describe('Cache', () => { err.should.have.property('message', 'ID is not defined'); }); - return Cache.insert({}).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + return Cache.insert({}) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); }); diff --git a/test/scripts/models/category.js b/test/scripts/models/category.js index 80dbb7f634..aee2b1ef0d 100644 --- a/test/scripts/models/category.js +++ b/test/scripts/models/category.js @@ -17,19 +17,22 @@ describe('Category', () => { err.should.have.property('message', '`name` is required!'); }); - return Category.insert({}).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + return Category.insert({}) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); it.skip('parent - reference'); - it('slug - virtual', () => Category.insert({ - name: 'foo' - }).then(data => { - data.slug.should.eql('foo'); - return Category.removeById(data._id); - })); + it('slug - virtual', () => + Category.insert({ + name: 'foo' + }).then(data => { + data.slug.should.eql('foo'); + return Category.removeById(data._id); + })); it('slug - category_map', () => { hexo.config.category_map = { @@ -45,12 +48,13 @@ describe('Category', () => { }); }); - it('slug - filename_case: 0', () => Category.insert({ - name: 'WahAHa' - }).then(data => { - data.slug.should.eql('WahAHa'); - return Category.removeById(data._id); - })); + it('slug - filename_case: 0', () => + Category.insert({ + name: 'WahAHa' + }).then(data => { + data.slug.should.eql('WahAHa'); + return Category.removeById(data._id); + })); it('slug - filename_case: 1', () => { hexo.config.filename_case = 1; @@ -76,158 +80,195 @@ describe('Category', () => { }); }); - it('slug - parent', () => Category.insert({ - name: 'parent' - }).then(cat => Category.insert({ - name: 'child', - parent: cat._id - })).then(cat => { - cat.slug.should.eql('parent/child'); - - return Promise.all([ - Category.removeById(cat._id), - Category.removeById(cat.parent) - ]); - })); - - it('path - virtual', () => Category.insert({ - name: 'foo' - }).then(data => { - data.path.should.eql(hexo.config.category_dir + '/' + data.slug + '/'); - return Category.removeById(data._id); - })); - - it('permalink - virtual', () => Category.insert({ - name: 'foo' - }).then(data => { - data.permalink.should.eql(hexo.config.url + '/' + data.path); - return Category.removeById(data._id); - })); - - it('posts - virtual', () => Post.insert([ - {source: 'foo.md', slug: 'foo'}, - {source: 'bar.md', slug: 'bar'}, - {source: 'baz.md', slug: 'baz'} - ]).each(post => post.setCategories(['foo'])).then(posts => { - const cat = Category.findOne({name: 'foo'}); - - function mapper(post) { - return post._id; - } - - hexo.locals.invalidate(); - cat.posts.map(mapper).should.eql(posts.map(mapper)); - cat.length.should.eql(posts.length); - - return cat.remove().thenReturn(posts); - }).map(post => post.remove())); - - it('posts - draft', () => Post.insert([ - {source: 'foo.md', slug: 'foo', published: true}, - {source: 'bar.md', slug: 'bar', published: false}, - {source: 'baz.md', slug: 'baz', published: true} - ]).each(post => post.setCategories(['foo'])).then(posts => { - let cat = Category.findOne({name: 'foo'}); - - function mapper(post) { - return post._id; - } - - // draft off - hexo.locals.invalidate(); - cat.posts.eq(0)._id.should.eql(posts[0]._id); - cat.posts.eq(1)._id.should.eql(posts[2]._id); - cat.length.should.eql(2); - - // draft on - hexo.config.render_drafts = true; - hexo.locals.invalidate(); - cat = Category.findOne({name: 'foo'}); - cat.posts.map(mapper).should.eql(posts.map(mapper)); - cat.length.should.eql(posts.length); - hexo.config.render_drafts = false; - - return cat.remove().thenReturn(posts); - }).map(post => post.remove())); + it('slug - parent', () => + Category.insert({ + name: 'parent' + }) + .then(cat => + Category.insert({ + name: 'child', + parent: cat._id + }) + ) + .then(cat => { + cat.slug.should.eql('parent/child'); + + return Promise.all([ + Category.removeById(cat._id), + Category.removeById(cat.parent) + ]); + })); + + it('path - virtual', () => + Category.insert({ + name: 'foo' + }).then(data => { + data.path.should.eql(hexo.config.category_dir + '/' + data.slug + '/'); + return Category.removeById(data._id); + })); + + it('permalink - virtual', () => + Category.insert({ + name: 'foo' + }).then(data => { + data.permalink.should.eql(hexo.config.url + '/' + data.path); + return Category.removeById(data._id); + })); + + it('posts - virtual', () => + Post.insert([ + { source: 'foo.md', slug: 'foo' }, + { source: 'bar.md', slug: 'bar' }, + { source: 'baz.md', slug: 'baz' } + ]) + .each(post => post.setCategories(['foo'])) + .then(posts => { + const cat = Category.findOne({ name: 'foo' }); + + function mapper(post) { + return post._id; + } + + hexo.locals.invalidate(); + cat.posts.map(mapper).should.eql(posts.map(mapper)); + cat.length.should.eql(posts.length); + + return cat.remove().thenReturn(posts); + }) + .map(post => post.remove())); + + it('posts - draft', () => + Post.insert([ + { source: 'foo.md', slug: 'foo', published: true }, + { source: 'bar.md', slug: 'bar', published: false }, + { source: 'baz.md', slug: 'baz', published: true } + ]) + .each(post => post.setCategories(['foo'])) + .then(posts => { + let cat = Category.findOne({ name: 'foo' }); + + function mapper(post) { + return post._id; + } + + // draft off + hexo.locals.invalidate(); + cat.posts.eq(0)._id.should.eql(posts[0]._id); + cat.posts.eq(1)._id.should.eql(posts[2]._id); + cat.length.should.eql(2); + + // draft on + hexo.config.render_drafts = true; + hexo.locals.invalidate(); + cat = Category.findOne({ name: 'foo' }); + cat.posts.map(mapper).should.eql(posts.map(mapper)); + cat.length.should.eql(posts.length); + hexo.config.render_drafts = false; + + return cat.remove().thenReturn(posts); + }) + .map(post => post.remove())); it('posts - future', () => { const now = Date.now(); return Post.insert([ - {source: 'foo.md', slug: 'foo', date: now - 3600}, - {source: 'bar.md', slug: 'bar', date: now + 3600}, - {source: 'baz.md', slug: 'baz', date: now} - ]).each(post => post.setCategories(['foo'])).then(posts => { - let cat = Category.findOne({name: 'foo'}); - - function mapper(post) { - return post._id; - } - - // future on - hexo.config.future = true; - hexo.locals.invalidate(); - cat.posts.map(mapper).should.eql(posts.map(mapper)); - cat.length.should.eql(posts.length); - - // future off - hexo.config.future = false; - hexo.locals.invalidate(); - cat = Category.findOne({name: 'foo'}); - cat.posts.eq(0)._id.should.eql(posts[0]._id); - cat.posts.eq(1)._id.should.eql(posts[2]._id); - cat.length.should.eql(2); - - return cat.remove().thenReturn(posts); - }).map(post => post.remove()); + { source: 'foo.md', slug: 'foo', date: now - 3600 }, + { source: 'bar.md', slug: 'bar', date: now + 3600 }, + { source: 'baz.md', slug: 'baz', date: now } + ]) + .each(post => post.setCategories(['foo'])) + .then(posts => { + let cat = Category.findOne({ name: 'foo' }); + + function mapper(post) { + return post._id; + } + + // future on + hexo.config.future = true; + hexo.locals.invalidate(); + cat.posts.map(mapper).should.eql(posts.map(mapper)); + cat.length.should.eql(posts.length); + + // future off + hexo.config.future = false; + hexo.locals.invalidate(); + cat = Category.findOne({ name: 'foo' }); + cat.posts.eq(0)._id.should.eql(posts[0]._id); + cat.posts.eq(1)._id.should.eql(posts[2]._id); + cat.length.should.eql(2); + + return cat.remove().thenReturn(posts); + }) + .map(post => post.remove()); }); it('check whether a category exists', () => { const errorCallback = sinon.spy(err => { - err.should.have.property('message', 'Category `foo` has already existed!'); + err.should.have.property( + 'message', + 'Category `foo` has already existed!' + ); }); return Category.insert({ name: 'foo' - }).then(data => { - Category.insert({ - name: 'foo' - }).catch(errorCallback); - - return Category.removeById(data._id); - }).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + }) + .then(data => { + Category.insert({ + name: 'foo' + }).catch(errorCallback); + + return Category.removeById(data._id); + }) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); - it('check whether a category exists (with parent)', () => Category.insert({ - name: 'foo' - }).then(data => Category.insert({ - name: 'foo', - parent: data._id - })).then(data => Promise.all([ - Category.removeById(data._id), - Category.removeById(data.parent) - ]))); + it('check whether a category exists (with parent)', () => + Category.insert({ + name: 'foo' + }) + .then(data => + Category.insert({ + name: 'foo', + parent: data._id + }) + ) + .then(data => + Promise.all([ + Category.removeById(data._id), + Category.removeById(data.parent) + ]) + )); it('remove PostCategory references when a category is removed', () => { let cat; return Post.insert([ - {source: 'foo.md', slug: 'foo'}, - {source: 'bar.md', slug: 'bar'}, - {source: 'baz.md', slug: 'baz'} - ]).then(posts => // One item a time - Promise.map( - posts, - post => post.setCategories(['foo']).thenReturn(post), - {concurrency: 1} - )).then(posts => { - cat = Category.findOne({name: 'foo'}); - return Category.removeById(cat._id).thenReturn(posts); - }).then(posts => { - PostCategory.find({category_id: cat._id}).length.should.eql(0); - return posts; - }).map(post => Post.removeById(post._id)); + { source: 'foo.md', slug: 'foo' }, + { source: 'bar.md', slug: 'bar' }, + { source: 'baz.md', slug: 'baz' } + ]) + .then(( + posts // One item a time + ) => + Promise.map( + posts, + post => post.setCategories(['foo']).thenReturn(post), + { concurrency: 1 } + ) + ) + .then(posts => { + cat = Category.findOne({ name: 'foo' }); + return Category.removeById(cat._id).thenReturn(posts); + }) + .then(posts => { + PostCategory.find({ category_id: cat._id }).length.should.eql(0); + return posts; + }) + .map(post => Post.removeById(post._id)); }); }); diff --git a/test/scripts/models/moment.js b/test/scripts/models/moment.js index 14781b9ca5..ef576730f2 100644 --- a/test/scripts/models/moment.js +++ b/test/scripts/models/moment.js @@ -9,48 +9,73 @@ describe('SchemaTypeMoment', () => { it('cast()', () => { type.cast(1e8).should.eql(moment(1e8)); type.cast(new Date(2014, 1, 1)).should.eql(moment(new Date(2014, 1, 1))); - type.cast('2014-11-03T07:45:41.237Z').should.eql(moment('2014-11-03T07:45:41.237Z')); - type.cast(moment(1e8)).valueOf().should.eql(1e8); + type + .cast('2014-11-03T07:45:41.237Z') + .should.eql(moment('2014-11-03T07:45:41.237Z')); + type + .cast(moment(1e8)) + .valueOf() + .should.eql(1e8); }); it('cast() - default', () => { - const type = new SchemaTypeMoment('test', {default: moment}); + const type = new SchemaTypeMoment('test', { default: moment }); moment.isMoment(type.cast()).should.be.true; }); it('cast() - language', () => { const lang = 'zh-tw'; const format = 'LLLL'; - const type = new SchemaTypeMoment('test', {language: lang}); + const type = new SchemaTypeMoment('test', { language: lang }); const now = Date.now(); - type.cast(now).format(format).should.eql(moment(now).locale(lang).format(format)); + type + .cast(now) + .format(format) + .should.eql( + moment(now) + .locale(lang) + .format(format) + ); }); it('cast() - timezone', () => { const timezone = 'Etc/UTC'; const format = 'LLLL'; - const type = new SchemaTypeMoment('test', {timezone}); + const type = new SchemaTypeMoment('test', { timezone }); const now = Date.now(); - type.cast(now).format(format).should.eql(moment(now).tz(timezone).format(format)); + type + .cast(now) + .format(format) + .should.eql( + moment(now) + .tz(timezone) + .format(format) + ); }); function shouldThrowError(value) { try { type.validate(value); } catch (err) { - err.should.have.property('message', '`' + value + '` is not a valid date!'); + err.should.have.property( + 'message', + '`' + value + '` is not a valid date!' + ); } } it('validate()', () => { - type.validate(moment(1e8)).valueOf().should.eql(1e8); + type + .validate(moment(1e8)) + .valueOf() + .should.eql(1e8); shouldThrowError(moment.invalid()); }); it('validate() - required', () => { - const type = new SchemaTypeMoment('test', {required: true}); + const type = new SchemaTypeMoment('test', { required: true }); try { type.validate(); @@ -75,12 +100,16 @@ describe('SchemaTypeMoment', () => { }); it('parse()', () => { - type.parse('2014-11-03T07:45:41.237Z').should.eql(moment('2014-11-03T07:45:41.237Z')); + type + .parse('2014-11-03T07:45:41.237Z') + .should.eql(moment('2014-11-03T07:45:41.237Z')); should.not.exist(type.parse()); }); it('value()', () => { - type.value(moment('2014-11-03T07:45:41.237Z')).should.eql('2014-11-03T07:45:41.237Z'); + type + .value(moment('2014-11-03T07:45:41.237Z')) + .should.eql('2014-11-03T07:45:41.237Z'); should.not.exist(type.value()); }); @@ -103,12 +132,18 @@ describe('SchemaTypeMoment', () => { }); it('u$inc()', () => { - type.u$inc(moment(1e8), 1).valueOf().should.eql(1e8 + 1); + type + .u$inc(moment(1e8), 1) + .valueOf() + .should.eql(1e8 + 1); should.not.exist(undefined, 1); }); it('u$dec()', () => { - type.u$dec(moment(1e8), 1).valueOf().should.eql(1e8 - 1); + type + .u$dec(moment(1e8), 1) + .valueOf() + .should.eql(1e8 - 1); should.not.exist(undefined, 1); }); }); diff --git a/test/scripts/models/page.js b/test/scripts/models/page.js index a4efe34781..d06a9da2e2 100644 --- a/test/scripts/models/page.js +++ b/test/scripts/models/page.js @@ -35,9 +35,11 @@ describe('Page', () => { err.should.have.property('message', '`source` is required!'); }); - return Page.insert({}).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + return Page.insert({}) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); it('path - required', () => { @@ -47,24 +49,28 @@ describe('Page', () => { return Page.insert({ source: 'foo' - }).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + }) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); - it('permalink - virtual', () => Page.insert({ - source: 'foo', - path: 'bar' - }).then(data => { - data.permalink.should.eql(hexo.config.url + '/' + data.path); - return Page.removeById(data._id); - })); + it('permalink - virtual', () => + Page.insert({ + source: 'foo', + path: 'bar' + }).then(data => { + data.permalink.should.eql(hexo.config.url + '/' + data.path); + return Page.removeById(data._id); + })); - it('full_source - virtual', () => Page.insert({ - source: 'foo', - path: 'bar' - }).then(data => { - data.full_source.should.eql(pathFn.join(hexo.source_dir, data.source)); - return Page.removeById(data._id); - })); + it('full_source - virtual', () => + Page.insert({ + source: 'foo', + path: 'bar' + }).then(data => { + data.full_source.should.eql(pathFn.join(hexo.source_dir, data.source)); + return Page.removeById(data._id); + })); }); diff --git a/test/scripts/models/post.js b/test/scripts/models/post.js index 0b05b83014..21d2bde49a 100644 --- a/test/scripts/models/post.js +++ b/test/scripts/models/post.js @@ -48,9 +48,11 @@ describe('Post', () => { err.should.have.property('message', '`source` is required!'); }); - return Post.insert({}).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + return Post.insert({}) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); it('slug - required', () => { @@ -60,18 +62,21 @@ describe('Post', () => { return Post.insert({ source: 'foo.md' - }).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + }) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); - it('path - virtual', () => Post.insert({ - source: 'foo.md', - slug: 'bar' - }).then(data => { - data.path.should.eql(data.slug); - return Post.removeById(data._id); - })); + it('path - virtual', () => + Post.insert({ + source: 'foo.md', + slug: 'bar' + }).then(data => { + data.path.should.eql(data.slug); + return Post.removeById(data._id); + })); it('permalink - virtual', () => { hexo.config.root = '/'; @@ -121,53 +126,71 @@ describe('Post', () => { }); }); - it('full_source - virtual', () => Post.insert({ - source: 'foo.md', - slug: 'bar' - }).then(data => { - data.full_source.should.eql(pathFn.join(hexo.source_dir, data.source)); - return Post.removeById(data._id); - })); - - it('asset_dir - virtual', () => Post.insert({ - source: 'foo.md', - slug: 'bar' - }).then(data => { - data.asset_dir.should.eql(pathFn.join(hexo.source_dir, 'foo') + pathFn.sep); - return Post.removeById(data._id); - })); - - it('tags - virtual', () => Post.insert({ - source: 'foo.md', - slug: 'bar' - }).then(post => post.setTags(['foo', 'bar', 'baz']) - .thenReturn(Post.findById(post._id))).then(post => { - post.tags.map(tag => tag.name).should.have.members(['bar', 'baz', 'foo']); - - return Post.removeById(post._id); - })); - - it('categories - virtual', () => Post.insert({ - source: 'foo.md', - slug: 'bar' - }).then(post => post.setCategories(['foo', 'bar', 'baz']) - .thenReturn(Post.findById(post._id))).then(post => { - const cats = post.categories; - - // Make sure the order of categories is correct - cats.map((cat, i) => { - // Make sure the parent reference is correct - if (i) { - cat.parent.should.eql(cats.eq(i - 1)._id); - } else { - should.not.exist(cat.parent); - } - - return cat.name; - }).should.eql(['foo', 'bar', 'baz']); - - return Post.removeById(post._id); - })); + it('full_source - virtual', () => + Post.insert({ + source: 'foo.md', + slug: 'bar' + }).then(data => { + data.full_source.should.eql(pathFn.join(hexo.source_dir, data.source)); + return Post.removeById(data._id); + })); + + it('asset_dir - virtual', () => + Post.insert({ + source: 'foo.md', + slug: 'bar' + }).then(data => { + data.asset_dir.should.eql( + pathFn.join(hexo.source_dir, 'foo') + pathFn.sep + ); + return Post.removeById(data._id); + })); + + it('tags - virtual', () => + Post.insert({ + source: 'foo.md', + slug: 'bar' + }) + .then(post => + post.setTags(['foo', 'bar', 'baz']).thenReturn(Post.findById(post._id)) + ) + .then(post => { + post.tags + .map(tag => tag.name) + .should.have.members(['bar', 'baz', 'foo']); + + return Post.removeById(post._id); + })); + + it('categories - virtual', () => + Post.insert({ + source: 'foo.md', + slug: 'bar' + }) + .then(post => + post + .setCategories(['foo', 'bar', 'baz']) + .thenReturn(Post.findById(post._id)) + ) + .then(post => { + const cats = post.categories; + + // Make sure the order of categories is correct + cats + .map((cat, i) => { + // Make sure the parent reference is correct + if (i) { + cat.parent.should.eql(cats.eq(i - 1)._id); + } else { + should.not.exist(cat.parent); + } + + return cat.name; + }) + .should.eql(['foo', 'bar', 'baz']); + + return Post.removeById(post._id); + })); it('setTags() - old tags should be removed', () => { let id; @@ -175,32 +198,41 @@ describe('Post', () => { return Post.insert({ source: 'foo.md', slug: 'foo' - }).then(post => { - id = post._id; - return post.setTags(['foo', 'bar']); - }).then(() => { - const post = Post.findById(id); - return post.setTags(['bar', 'baz']); - }).then(() => { - const post = Post.findById(id); - - post.tags.map(tag => tag.name).should.eql(['bar', 'baz']); - - return Post.removeById(id); - }); + }) + .then(post => { + id = post._id; + return post.setTags(['foo', 'bar']); + }) + .then(() => { + const post = Post.findById(id); + return post.setTags(['bar', 'baz']); + }) + .then(() => { + const post = Post.findById(id); + + post.tags.map(tag => tag.name).should.eql(['bar', 'baz']); + + return Post.removeById(id); + }); }); - it('setTags() - sync problem', () => Post.insert([ - {source: 'foo.md', slug: 'foo'}, - {source: 'bar.md', slug: 'bar'} - ]).then(posts => Promise.all([ - posts[0].setTags(['foo', 'bar']), - posts[1].setTags(['bar', 'baz']) - ]).thenReturn(posts)).then(posts => { - Tag.map(tag => tag.name).should.have.members(['foo', 'bar', 'baz']); - - return posts; - }).map(post => Post.removeById(post._id))); + it('setTags() - sync problem', () => + Post.insert([ + { source: 'foo.md', slug: 'foo' }, + { source: 'bar.md', slug: 'bar' } + ]) + .then(posts => + Promise.all([ + posts[0].setTags(['foo', 'bar']), + posts[1].setTags(['bar', 'baz']) + ]).thenReturn(posts) + ) + .then(posts => { + Tag.map(tag => tag.name).should.have.members(['foo', 'bar', 'baz']); + + return posts; + }) + .map(post => Post.removeById(post._id))); it('setTags() - empty tag', () => { let id; @@ -208,14 +240,17 @@ describe('Post', () => { return Post.insert({ source: 'foo.md', slug: 'foo' - }).then(post => { - id = post._id; - return post.setTags(['', undefined, null, false, 0, 'normal']); - }).then(() => { - const post = Post.findById(id); - - post.tags.map(tag => tag.name).should.eql(['false', '0', 'normal']); - }).finally(() => Post.removeById(id)); + }) + .then(post => { + id = post._id; + return post.setTags(['', undefined, null, false, 0, 'normal']); + }) + .then(() => { + const post = Post.findById(id); + + post.tags.map(tag => tag.name).should.eql(['false', '0', 'normal']); + }) + .finally(() => Post.removeById(id)); }); it('setCategories() - old categories should be removed', () => { @@ -224,19 +259,22 @@ describe('Post', () => { return Post.insert({ source: 'foo.md', slug: 'foo' - }).then(post => { - id = post._id; - return post.setCategories(['foo', 'bar']); - }).then(() => { - const post = Post.findById(id); - return post.setCategories(['foo', 'baz']); - }).then(() => { - const post = Post.findById(id); - - post.categories.map(cat => cat.name).should.eql(['foo', 'baz']); - - return Post.removeById(id); - }); + }) + .then(post => { + id = post._id; + return post.setCategories(['foo', 'bar']); + }) + .then(() => { + const post = Post.findById(id); + return post.setCategories(['foo', 'baz']); + }) + .then(() => { + const post = Post.findById(id); + + post.categories.map(cat => cat.name).should.eql(['foo', 'baz']); + + return Post.removeById(id); + }); }); it('setCategories() - shared category should be same', () => { @@ -245,26 +283,33 @@ describe('Post', () => { return Post.insert({ source: 'foo.md', slug: 'foo' - }).then(post => { - postIdA = post._id; - return post.setCategories(['foo', 'bar']); - }).then(() => Post.insert({ - source: 'bar.md', - slug: 'bar' - }).then(post => { - postIdB = post._id; - return post.setCategories(['foo', 'bar']); - })).then(() => { - const postA = Post.findById(postIdA); - const postB = Post.findById(postIdB); - - postA.categories.map(cat => cat._id).should.eql(postB.categories.map(cat => cat._id)); - - return Promise.all([ - Post.removeById(postIdA), - Post.removeById(postIdB) - ]); - }); + }) + .then(post => { + postIdA = post._id; + return post.setCategories(['foo', 'bar']); + }) + .then(() => + Post.insert({ + source: 'bar.md', + slug: 'bar' + }).then(post => { + postIdB = post._id; + return post.setCategories(['foo', 'bar']); + }) + ) + .then(() => { + const postA = Post.findById(postIdA); + const postB = Post.findById(postIdB); + + postA.categories + .map(cat => cat._id) + .should.eql(postB.categories.map(cat => cat._id)); + + return Promise.all([ + Post.removeById(postIdA), + Post.removeById(postIdB) + ]); + }); }); it('setCategories() - category not shared should be different', () => { @@ -273,36 +318,41 @@ describe('Post', () => { return Post.insert({ source: 'foo.md', slug: 'foo' - }).then(post => { - postIdA = post._id; - return post.setCategories(['foo', 'bar']); - }).then(() => Post.insert({ - source: 'bar.md', - slug: 'bar' - }).then(post => { - postIdB = post._id; - return post.setCategories(['baz', 'bar']); - })).then(() => { - const postA = Post.findById(postIdA); - const postB = Post.findById(postIdB); - - const postCategoriesA = postA.categories.map(cat => cat._id); - - const postCategoriesB = postB.categories.map(cat => cat._id); - - postCategoriesA.forEach(catId => { - postCategoriesB.should.not.include(catId); - }); - - postCategoriesB.forEach(catId => { - postCategoriesA.should.not.include(catId); + }) + .then(post => { + postIdA = post._id; + return post.setCategories(['foo', 'bar']); + }) + .then(() => + Post.insert({ + source: 'bar.md', + slug: 'bar' + }).then(post => { + postIdB = post._id; + return post.setCategories(['baz', 'bar']); + }) + ) + .then(() => { + const postA = Post.findById(postIdA); + const postB = Post.findById(postIdB); + + const postCategoriesA = postA.categories.map(cat => cat._id); + + const postCategoriesB = postB.categories.map(cat => cat._id); + + postCategoriesA.forEach(catId => { + postCategoriesB.should.not.include(catId); + }); + + postCategoriesB.forEach(catId => { + postCategoriesA.should.not.include(catId); + }); + + return Promise.all([ + Post.removeById(postIdA), + Post.removeById(postIdB) + ]); }); - - return Promise.all([ - Post.removeById(postIdA), - Post.removeById(postIdB) - ]); - }); }); it('setCategories() - empty category', () => { @@ -311,14 +361,17 @@ describe('Post', () => { return Post.insert({ source: 'foo.md', slug: 'foo' - }).then(post => { - id = post._id; - return post.setCategories(['test', null]); - }).then(() => { - const post = Post.findById(id); - - post.categories.map(cat => cat.name).should.eql(['test']); - }).finally(() => Post.removeById(id)); + }) + .then(post => { + id = post._id; + return post.setCategories(['test', null]); + }) + .then(() => { + const post = Post.findById(id); + + post.categories.map(cat => cat.name).should.eql(['test']); + }) + .finally(() => Post.removeById(id)); }); it('setCategories() - empty category in middle', () => { @@ -327,84 +380,117 @@ describe('Post', () => { return Post.insert({ source: 'foo.md', slug: 'foo' - }).then(post => { - id = post._id; - return post.setCategories(['foo', null, 'bar']); - }).then(() => { - const post = Post.findById(id); - - post.categories.map(cat => cat.name).should.eql(['foo', 'bar']); - }).finally(() => Post.removeById(id)); + }) + .then(post => { + id = post._id; + return post.setCategories(['foo', null, 'bar']); + }) + .then(() => { + const post = Post.findById(id); + + post.categories.map(cat => cat.name).should.eql(['foo', 'bar']); + }) + .finally(() => Post.removeById(id)); }); - it('setCategories() - multiple hierarchies', () => Post.insert({ - source: 'foo.md', - slug: 'bar' - }).then(post => post.setCategories([['foo', '', 'bar'], '', 'baz']) - .thenReturn(Post.findById(post._id))).then(post => { - const cats = post.categories.toArray(); - - // There should have been 3 categories set; blanks eliminated - cats.should.have.lengthOf(3); - - // Category 1 should be foo, no parent - cats[0].name.should.eql('foo'); - should.not.exist(cats[0].parent); - - // Category 2 should be bar, foo as parent - cats[1].name.should.eql('bar'); - cats[1].parent.should.eql(cats[0]._id); - - // Category 3 should be baz, no parent - cats[2].name.should.eql('baz'); - should.not.exist(cats[2].parent); - - return Post.removeById(post._id); - })); - - it('setCategories() - multiple hierarchies (dedupes repeated parent)', () => Post.insert({ - source: 'foo.md', - slug: 'bar' - }).then(post => post.setCategories([['foo', 'bar'], ['foo', 'baz']]) - .thenReturn(Post.findById(post._id))).then(post => { - const cats = post.categories.toArray(); - - // There should have been 3 categories set (foo is dupe) - cats.should.have.lengthOf(3); - - return Post.removeById(post._id); - })); - - it('remove PostTag references when a post is removed', () => Post.insert({ - source: 'foo.md', - slug: 'bar' - }).then(post => post.setTags(['foo', 'bar', 'baz']) - .thenReturn(Post.findById(post._id))).then(post => Post.removeById(post._id)).then(post => { - PostTag.find({post_id: post._id}).length.should.eql(0); - Tag.findOne({name: 'foo'}).posts.length.should.eql(0); - Tag.findOne({name: 'bar'}).posts.length.should.eql(0); - Tag.findOne({name: 'baz'}).posts.length.should.eql(0); - })); - - it('remove PostCategory references when a post is removed', () => Post.insert({ - source: 'foo.md', - slug: 'bar' - }).then(post => post.setCategories(['foo', 'bar', 'baz']) - .thenReturn(Post.findById(post._id))).then(post => Post.removeById(post._id)).then(post => { - PostCategory.find({post_id: post._id}).length.should.eql(0); - Category.findOne({name: 'foo'}).posts.length.should.eql(0); - Category.findOne({name: 'bar'}).posts.length.should.eql(0); - Category.findOne({name: 'baz'}).posts.length.should.eql(0); - })); - - it('remove related assets when a post is removed', () => Post.insert({ - source: 'foo.md', - slug: 'bar' - }).then(post => Promise.all([ - Asset.insert({_id: 'foo', path: 'foo'}), - Asset.insert({_id: 'bar', path: 'bar'}), - Asset.insert({_id: 'baz', path: 'bar'}) - ]).thenReturn(post)).then(post => Post.removeById(post._id)).then(post => { - Asset.find({post: post._id}).length.should.eql(0); - })); + it('setCategories() - multiple hierarchies', () => + Post.insert({ + source: 'foo.md', + slug: 'bar' + }) + .then(post => + post + .setCategories([['foo', '', 'bar'], '', 'baz']) + .thenReturn(Post.findById(post._id)) + ) + .then(post => { + const cats = post.categories.toArray(); + + // There should have been 3 categories set; blanks eliminated + cats.should.have.lengthOf(3); + + // Category 1 should be foo, no parent + cats[0].name.should.eql('foo'); + should.not.exist(cats[0].parent); + + // Category 2 should be bar, foo as parent + cats[1].name.should.eql('bar'); + cats[1].parent.should.eql(cats[0]._id); + + // Category 3 should be baz, no parent + cats[2].name.should.eql('baz'); + should.not.exist(cats[2].parent); + + return Post.removeById(post._id); + })); + + it('setCategories() - multiple hierarchies (dedupes repeated parent)', () => + Post.insert({ + source: 'foo.md', + slug: 'bar' + }) + .then(post => + post + .setCategories([['foo', 'bar'], ['foo', 'baz']]) + .thenReturn(Post.findById(post._id)) + ) + .then(post => { + const cats = post.categories.toArray(); + + // There should have been 3 categories set (foo is dupe) + cats.should.have.lengthOf(3); + + return Post.removeById(post._id); + })); + + it('remove PostTag references when a post is removed', () => + Post.insert({ + source: 'foo.md', + slug: 'bar' + }) + .then(post => + post.setTags(['foo', 'bar', 'baz']).thenReturn(Post.findById(post._id)) + ) + .then(post => Post.removeById(post._id)) + .then(post => { + PostTag.find({ post_id: post._id }).length.should.eql(0); + Tag.findOne({ name: 'foo' }).posts.length.should.eql(0); + Tag.findOne({ name: 'bar' }).posts.length.should.eql(0); + Tag.findOne({ name: 'baz' }).posts.length.should.eql(0); + })); + + it('remove PostCategory references when a post is removed', () => + Post.insert({ + source: 'foo.md', + slug: 'bar' + }) + .then(post => + post + .setCategories(['foo', 'bar', 'baz']) + .thenReturn(Post.findById(post._id)) + ) + .then(post => Post.removeById(post._id)) + .then(post => { + PostCategory.find({ post_id: post._id }).length.should.eql(0); + Category.findOne({ name: 'foo' }).posts.length.should.eql(0); + Category.findOne({ name: 'bar' }).posts.length.should.eql(0); + Category.findOne({ name: 'baz' }).posts.length.should.eql(0); + })); + + it('remove related assets when a post is removed', () => + Post.insert({ + source: 'foo.md', + slug: 'bar' + }) + .then(post => + Promise.all([ + Asset.insert({ _id: 'foo', path: 'foo' }), + Asset.insert({ _id: 'bar', path: 'bar' }), + Asset.insert({ _id: 'baz', path: 'bar' }) + ]).thenReturn(post) + ) + .then(post => Post.removeById(post._id)) + .then(post => { + Asset.find({ post: post._id }).length.should.eql(0); + })); }); diff --git a/test/scripts/models/post_asset.js b/test/scripts/models/post_asset.js index bea7ccaf83..0aafcb5b8a 100644 --- a/test/scripts/models/post_asset.js +++ b/test/scripts/models/post_asset.js @@ -10,30 +10,40 @@ describe('PostAsset', () => { const Post = hexo.model('Post'); let post; - before(() => hexo.init().then(() => Post.insert({ - source: 'foo.md', - slug: 'bar' - })).then(post_ => { - post = post_; - })); + before(() => + hexo + .init() + .then(() => + Post.insert({ + source: 'foo.md', + slug: 'bar' + }) + ) + .then(post_ => { + post = post_; + }) + ); - it('default values', () => PostAsset.insert({ - _id: 'foo', - slug: 'foo', - post: post._id - }).then(data => { - data.modified.should.be.true; - return PostAsset.removeById(data._id); - })); + it('default values', () => + PostAsset.insert({ + _id: 'foo', + slug: 'foo', + post: post._id + }).then(data => { + data.modified.should.be.true; + return PostAsset.removeById(data._id); + })); it('_id - required', () => { const errorCallback = sinon.spy(err => { err.should.have.property('message', 'ID is not defined'); }); - return PostAsset.insert({}).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + return PostAsset.insert({}) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); it('slug - required', () => { @@ -43,19 +53,22 @@ describe('PostAsset', () => { return PostAsset.insert({ _id: 'foo' - }).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + }) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); - it('path - virtual', () => PostAsset.insert({ - _id: 'source/_posts/test/foo.jpg', - slug: 'foo.jpg', - post: post._id - }).then(data => { - data.path.should.eql(pathFn.join(post.path, data.slug)); - return PostAsset.removeById(data._id); - })); + it('path - virtual', () => + PostAsset.insert({ + _id: 'source/_posts/test/foo.jpg', + slug: 'foo.jpg', + post: post._id + }).then(data => { + data.path.should.eql(pathFn.join(post.path, data.slug)); + return PostAsset.removeById(data._id); + })); it('path - virtual - when permalink is .html', () => { hexo.config.permalink = ':year/:month/:day/:title.html'; @@ -63,12 +76,14 @@ describe('PostAsset', () => { _id: 'source/_posts/test/foo.html', slug: 'foo.htm', post: post._id - }).then(data => { - data.path.should.eql(pathFn.join(post.path, data.slug)); - return PostAsset.removeById(data._id); - }).finally(() => { - hexo.config.permalink = ':year/:month/:day/:title'; - }); + }) + .then(data => { + data.path.should.eql(pathFn.join(post.path, data.slug)); + return PostAsset.removeById(data._id); + }) + .finally(() => { + hexo.config.permalink = ':year/:month/:day/:title'; + }); }); it('path - virtual - when permalink is .htm', () => { @@ -77,12 +92,14 @@ describe('PostAsset', () => { _id: 'source/_posts/test/foo.htm', slug: 'foo.htm', post: post._id - }).then(data => { - data.path.should.eql(pathFn.join(post.path, data.slug)); - return PostAsset.removeById(data._id); - }).finally(() => { - hexo.config.permalink = ':year/:month/:day/:title'; - }); + }) + .then(data => { + data.path.should.eql(pathFn.join(post.path, data.slug)); + return PostAsset.removeById(data._id); + }) + .finally(() => { + hexo.config.permalink = ':year/:month/:day/:title'; + }); }); it('path - virtual - when permalink contains .htm not in the end', () => { @@ -91,20 +108,23 @@ describe('PostAsset', () => { _id: 'source/_posts/test/foo.html', slug: 'foo.html', post: post._id - }).then(data => { - data.path.should.eql(pathFn.join(post.path + '.htm-foo/', data.slug)); - return PostAsset.removeById(data._id); - }).finally(() => { - hexo.config.permalink = ':year/:month/:day/:title'; - }); + }) + .then(data => { + data.path.should.eql(pathFn.join(post.path + '.htm-foo/', data.slug)); + return PostAsset.removeById(data._id); + }) + .finally(() => { + hexo.config.permalink = ':year/:month/:day/:title'; + }); }); - it('source - virtual', () => PostAsset.insert({ - _id: 'source/_posts/test/foo.jpg', - slug: 'foo.jpg', - post: post._id - }).then(data => { - data.source.should.eql(pathFn.join(hexo.base_dir, data._id)); - return PostAsset.removeById(data._id); - })); + it('source - virtual', () => + PostAsset.insert({ + _id: 'source/_posts/test/foo.jpg', + slug: 'foo.jpg', + post: post._id + }).then(data => { + data.source.should.eql(pathFn.join(hexo.base_dir, data._id)); + return PostAsset.removeById(data._id); + })); }); diff --git a/test/scripts/models/tag.js b/test/scripts/models/tag.js index 691a4085fb..924b83eb63 100644 --- a/test/scripts/models/tag.js +++ b/test/scripts/models/tag.js @@ -17,17 +17,20 @@ describe('Tag', () => { err.should.have.property('message', '`name` is required!'); }); - return Tag.insert({}).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + return Tag.insert({}) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); - it('slug - virtual', () => Tag.insert({ - name: 'foo' - }).then(data => { - data.slug.should.eql('foo'); - return Tag.removeById(data._id); - })); + it('slug - virtual', () => + Tag.insert({ + name: 'foo' + }).then(data => { + data.slug.should.eql('foo'); + return Tag.removeById(data._id); + })); it('slug - tag_map', () => { hexo.config.tag_map = { @@ -44,12 +47,13 @@ describe('Tag', () => { }); }); - it('slug - filename_case: 0', () => Tag.insert({ - name: 'WahAHa' - }).then(data => { - data.slug.should.eql('WahAHa'); - return Tag.removeById(data._id); - })); + it('slug - filename_case: 0', () => + Tag.insert({ + name: 'WahAHa' + }).then(data => { + data.slug.should.eql('WahAHa'); + return Tag.removeById(data._id); + })); it('slug - filename_case: 1', () => { hexo.config.filename_case = 1; @@ -75,96 +79,109 @@ describe('Tag', () => { }); }); - it('path - virtual', () => Tag.insert({ - name: 'foo' - }).then(data => { - data.path.should.eql(hexo.config.tag_dir + '/' + data.slug + '/'); - return Tag.removeById(data._id); - })); - - it('permalink - virtual', () => Tag.insert({ - name: 'foo' - }).then(data => { - data.permalink.should.eql(hexo.config.url + '/' + data.path); - return Tag.removeById(data._id); - })); - - it('posts - virtual', () => Post.insert([ - {source: 'foo.md', slug: 'foo'}, - {source: 'bar.md', slug: 'bar'}, - {source: 'baz.md', slug: 'baz'} - ]).each(post => post.setTags(['foo'])).then(posts => { - const tag = Tag.findOne({name: 'foo'}); - - function mapper(post) { - return post._id; - } - - hexo.locals.invalidate(); - tag.posts.map(mapper).should.eql(posts.map(mapper)); - tag.length.should.eql(posts.length); - - return tag.remove().thenReturn(posts); - }).map(post => post.remove())); - - it('posts - draft', () => Post.insert([ - {source: 'foo.md', slug: 'foo', published: true}, - {source: 'bar.md', slug: 'bar', published: false}, - {source: 'baz.md', slug: 'baz', published: true} - ]).each(post => post.setTags(['foo'])).then(posts => { - let tag = Tag.findOne({name: 'foo'}); - - function mapper(post) { - return post._id; - } - - // draft off - hexo.locals.invalidate(); - tag.posts.eq(0)._id.should.eql(posts[0]._id); - tag.posts.eq(1)._id.should.eql(posts[2]._id); - tag.length.should.eql(2); - - // draft on - hexo.config.render_drafts = true; - tag = Tag.findOne({name: 'foo'}); - hexo.locals.invalidate(); - tag.posts.map(mapper).should.eql(posts.map(mapper)); - tag.length.should.eql(posts.length); - hexo.config.render_drafts = false; - - return tag.remove().thenReturn(posts); - }).map(post => post.remove())); + it('path - virtual', () => + Tag.insert({ + name: 'foo' + }).then(data => { + data.path.should.eql(hexo.config.tag_dir + '/' + data.slug + '/'); + return Tag.removeById(data._id); + })); + + it('permalink - virtual', () => + Tag.insert({ + name: 'foo' + }).then(data => { + data.permalink.should.eql(hexo.config.url + '/' + data.path); + return Tag.removeById(data._id); + })); + + it('posts - virtual', () => + Post.insert([ + { source: 'foo.md', slug: 'foo' }, + { source: 'bar.md', slug: 'bar' }, + { source: 'baz.md', slug: 'baz' } + ]) + .each(post => post.setTags(['foo'])) + .then(posts => { + const tag = Tag.findOne({ name: 'foo' }); + + function mapper(post) { + return post._id; + } + + hexo.locals.invalidate(); + tag.posts.map(mapper).should.eql(posts.map(mapper)); + tag.length.should.eql(posts.length); + + return tag.remove().thenReturn(posts); + }) + .map(post => post.remove())); + + it('posts - draft', () => + Post.insert([ + { source: 'foo.md', slug: 'foo', published: true }, + { source: 'bar.md', slug: 'bar', published: false }, + { source: 'baz.md', slug: 'baz', published: true } + ]) + .each(post => post.setTags(['foo'])) + .then(posts => { + let tag = Tag.findOne({ name: 'foo' }); + + function mapper(post) { + return post._id; + } + + // draft off + hexo.locals.invalidate(); + tag.posts.eq(0)._id.should.eql(posts[0]._id); + tag.posts.eq(1)._id.should.eql(posts[2]._id); + tag.length.should.eql(2); + + // draft on + hexo.config.render_drafts = true; + tag = Tag.findOne({ name: 'foo' }); + hexo.locals.invalidate(); + tag.posts.map(mapper).should.eql(posts.map(mapper)); + tag.length.should.eql(posts.length); + hexo.config.render_drafts = false; + + return tag.remove().thenReturn(posts); + }) + .map(post => post.remove())); it('posts - future', () => { const now = Date.now(); return Post.insert([ - {source: 'foo.md', slug: 'foo', date: now - 3600}, - {source: 'bar.md', slug: 'bar', date: now + 3600}, - {source: 'baz.md', slug: 'baz', date: now} - ]).each(post => post.setTags(['foo'])).then(posts => { - let tag = Tag.findOne({name: 'foo'}); - - function mapper(post) { - return post._id; - } - - // future on - hexo.config.future = true; - hexo.locals.invalidate(); - tag.posts.map(mapper).should.eql(posts.map(mapper)); - tag.length.should.eql(posts.length); - - // future off - hexo.config.future = false; - hexo.locals.invalidate(); - tag = Tag.findOne({name: 'foo'}); - tag.posts.eq(0)._id.should.eql(posts[0]._id); - tag.posts.eq(1)._id.should.eql(posts[2]._id); - tag.length.should.eql(2); - - return tag.remove().thenReturn(posts); - }).map(post => post.remove()); + { source: 'foo.md', slug: 'foo', date: now - 3600 }, + { source: 'bar.md', slug: 'bar', date: now + 3600 }, + { source: 'baz.md', slug: 'baz', date: now } + ]) + .each(post => post.setTags(['foo'])) + .then(posts => { + let tag = Tag.findOne({ name: 'foo' }); + + function mapper(post) { + return post._id; + } + + // future on + hexo.config.future = true; + hexo.locals.invalidate(); + tag.posts.map(mapper).should.eql(posts.map(mapper)); + tag.length.should.eql(posts.length); + + // future off + hexo.config.future = false; + hexo.locals.invalidate(); + tag = Tag.findOne({ name: 'foo' }); + tag.posts.eq(0)._id.should.eql(posts[0]._id); + tag.posts.eq(1)._id.should.eql(posts[2]._id); + tag.length.should.eql(2); + + return tag.remove().thenReturn(posts); + }) + .map(post => post.remove()); }); it('check whether a tag exists', () => { @@ -174,31 +191,42 @@ describe('Tag', () => { return Tag.insert({ name: 'foo' - }).then(data => { - Tag.insert({ - name: 'foo' - }).catch(errorCallback); - - return Tag.removeById(data._id); - }).finally(() => { - errorCallback.calledOnce.should.be.true; - }); + }) + .then(data => { + Tag.insert({ + name: 'foo' + }).catch(errorCallback); + + return Tag.removeById(data._id); + }) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }); }); it('remove PostTag references when a tag is removed', () => { let tag; return Post.insert([ - {source: 'foo.md', slug: 'foo'}, - {source: 'bar.md', slug: 'bar'}, - {source: 'baz.md', slug: 'baz'} - ]).then(posts => // One item a time - Promise.map(posts, post => post.setTags(['foo']).thenReturn(post), {concurrency: 1})).then(posts => { - tag = Tag.findOne({name: 'foo'}); - return Tag.removeById(tag._id).thenReturn(posts); - }).then(posts => { - PostTag.find({tag_id: tag._id}).length.should.eql(0); - return posts; - }).map(post => Post.removeById(post._id)); + { source: 'foo.md', slug: 'foo' }, + { source: 'bar.md', slug: 'bar' }, + { source: 'baz.md', slug: 'baz' } + ]) + .then(( + posts // One item a time + ) => + Promise.map(posts, post => post.setTags(['foo']).thenReturn(post), { + concurrency: 1 + }) + ) + .then(posts => { + tag = Tag.findOne({ name: 'foo' }); + return Tag.removeById(tag._id).thenReturn(posts); + }) + .then(posts => { + PostTag.find({ tag_id: tag._id }).length.should.eql(0); + return posts; + }) + .map(post => Post.removeById(post._id)); }); }); diff --git a/test/scripts/processors/asset.js b/test/scripts/processors/asset.js index 3f00bec51c..5ae3ff2e5b 100644 --- a/test/scripts/processors/asset.js +++ b/test/scripts/processors/asset.js @@ -71,17 +71,21 @@ describe('asset', () => { renderable: false }); - return fs.writeFile(file.source, 'foo').then(() => process(file)).then(() => { - const id = 'source/' + file.path; - const asset = Asset.findById(id); - - asset._id.should.eql(id); - asset.path.should.eql(file.path); - asset.modified.should.be.true; - asset.renderable.should.be.false; - - return asset.remove(); - }).finally(() => fs.unlink(file.source)); + return fs + .writeFile(file.source, 'foo') + .then(() => process(file)) + .then(() => { + const id = 'source/' + file.path; + const asset = Asset.findById(id); + + asset._id.should.eql(id); + asset.path.should.eql(file.path); + asset.modified.should.be.true; + asset.renderable.should.be.false; + + return asset.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('asset - type: create (when source path is configed to parent directory)', () => { const file = newFile({ @@ -90,20 +94,24 @@ describe('asset', () => { renderable: false }); - return fs.writeFile(file.source, 'foo').then(() => process(file)).then(() => { - const id = '../source/foo.jpg'; // The id should a relative path,because the 'lib/models/assets.js' use asset path by joining base path with "_id" directly. - const asset = Asset.findById(id); + return fs + .writeFile(file.source, 'foo') + .then(() => process(file)) + .then(() => { + const id = '../source/foo.jpg'; // The id should a relative path,because the 'lib/models/assets.js' use asset path by joining base path with "_id" directly. + const asset = Asset.findById(id); - asset._id.should.eql(id); - asset.path.should.eql(file.path); - asset.modified.should.be.true; - asset.renderable.should.be.false; + asset._id.should.eql(id); + asset.path.should.eql(file.path); + asset.modified.should.be.true; + asset.renderable.should.be.false; - return asset.remove(); - }).finally(() => { - fs.unlink(file.source); - fs.rmdir(pathFn.dirname(file.source)); - }); + return asset.remove(); + }) + .finally(() => { + fs.unlink(file.source); + fs.rmdir(pathFn.dirname(file.source)); + }); }); it('asset - type: update', () => { const file = newFile({ @@ -121,16 +129,19 @@ describe('asset', () => { path: file.path, modified: false }) - ]).then(() => process(file)).then(() => { - const asset = Asset.findById(id); + ]) + .then(() => process(file)) + .then(() => { + const asset = Asset.findById(id); - asset._id.should.eql(id); - asset.path.should.eql(file.path); - asset.modified.should.be.true; - asset.renderable.should.be.false; + asset._id.should.eql(id); + asset.path.should.eql(file.path); + asset.modified.should.be.true; + asset.renderable.should.be.false; - return asset.remove(); - }).finally(() => fs.unlink(file.source)); + return asset.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('asset - type: skip', () => { @@ -149,13 +160,15 @@ describe('asset', () => { path: file.path, modified: false }) - ]).then(() => process(file)).then(() => { - const asset = Asset.findById(id); - asset.modified.should.be.false; - }).finally(() => Promise.all([ - Asset.removeById(id), - fs.unlink(file.source) - ])); + ]) + .then(() => process(file)) + .then(() => { + const asset = Asset.findById(id); + asset.modified.should.be.false; + }) + .finally(() => + Promise.all([Asset.removeById(id), fs.unlink(file.source)]) + ); }); it('asset - type: delete', () => { @@ -170,9 +183,11 @@ describe('asset', () => { return Asset.insert({ _id: id, path: file.path - }).then(() => process(file)).then(() => { - should.not.exist(Asset.findById(id)); - }); + }) + .then(() => process(file)) + .then(() => { + should.not.exist(Asset.findById(id)); + }); }); it('page - type: create', () => { @@ -190,30 +205,27 @@ describe('asset', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const page = Page.findOne({source: file.path}); - - page.title.should.eql('Hello world'); - page.date.format(dateFormat).should.eql('2006-01-02 15:04:05'); - page.updated.format(dateFormat).should.eql('2014-12-13 01:02:03'); - page._content.should.eql('The quick brown fox jumps over the lazy dog'); - page.source.should.eql(file.path); - page.raw.should.eql(body); - page.path.should.eql('hello.html'); - page.layout.should.eql('page'); - - return Promise.all([ - page.remove(), - fs.unlink(file.source) - ]); - }); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const page = Page.findOne({ source: file.path }); + + page.title.should.eql('Hello world'); + page.date.format(dateFormat).should.eql('2006-01-02 15:04:05'); + page.updated.format(dateFormat).should.eql('2014-12-13 01:02:03'); + page._content.should.eql('The quick brown fox jumps over the lazy dog'); + page.source.should.eql(file.path); + page.raw.should.eql(body); + page.path.should.eql('hello.html'); + page.layout.should.eql('page'); + + return Promise.all([page.remove(), fs.unlink(file.source)]); + }); }); it('page - type: update', () => { - const body = [ - 'title: "Hello world"', - '---' - ].join('\n'); + const body = ['title: "Hello world"', '---'].join('\n'); const file = newFile({ path: 'hello.swig', @@ -224,22 +236,21 @@ describe('asset', () => { let id; return Promise.all([ - Page.insert({source: file.path, path: 'hello.html'}), + Page.insert({ source: file.path, path: 'hello.html' }), fs.writeFile(file.source, body) - ]).spread(doc => { - id = doc._id; - return process(file); - }).then(() => { - const page = Page.findOne({source: file.path}); - - page._id.should.eql(id); - page.title.should.eql('Hello world'); - - return Promise.all([ - page.remove(), - fs.unlink(file.source) - ]); - }); + ]) + .spread(doc => { + id = doc._id; + return process(file); + }) + .then(() => { + const page = Page.findOne({ source: file.path }); + + page._id.should.eql(id); + page.title.should.eql('Hello world'); + + return Promise.all([page.remove(), fs.unlink(file.source)]); + }); }); it('page - type: delete', () => { @@ -252,9 +263,11 @@ describe('asset', () => { return Page.insert({ source: file.path, path: 'hello.html' - }).then(() => process(file)).then(() => { - should.not.exist(Page.findOne({source: file.path})); - }); + }) + .then(() => process(file)) + .then(() => { + should.not.exist(Page.findOne({ source: file.path })); + }); }); it('page - use the status of the source file if date not set', () => { @@ -264,28 +277,23 @@ describe('asset', () => { renderable: true }); - return fs.writeFile(file.source, '').then(() => Promise.all([ - fs.stat(file.source), - process(file) - ])).spread(stats => { - const page = Page.findOne({source: file.path}); + return fs + .writeFile(file.source, '') + .then(() => Promise.all([fs.stat(file.source), process(file)])) + .spread(stats => { + const page = Page.findOne({ source: file.path }); - page.date.toDate().should.eql(stats.ctime); - page.updated.toDate().should.eql(stats.mtime); + page.date.toDate().should.eql(stats.ctime); + page.updated.toDate().should.eql(stats.mtime); - return Promise.all([ - page.remove(), - fs.unlink(file.source) - ]); - }); + return Promise.all([page.remove(), fs.unlink(file.source)]); + }); }); it('page - permalink', () => { - const body = [ - 'title: "Hello world"', - 'permalink: foo.html', - '---' - ].join('\n'); + const body = ['title: "Hello world"', 'permalink: foo.html', '---'].join( + '\n' + ); const file = newFile({ path: 'hello.swig', @@ -293,24 +301,20 @@ describe('asset', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const page = Page.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const page = Page.findOne({ source: file.path }); - page.path.should.eql('foo.html'); + page.path.should.eql('foo.html'); - return Promise.all([ - page.remove(), - fs.unlink(file.source) - ]); - }); + return Promise.all([page.remove(), fs.unlink(file.source)]); + }); }); it('page - permalink (without extension name)', () => { - const body = [ - 'title: "Hello world"', - 'permalink: foo', - '---' - ].join('\n'); + const body = ['title: "Hello world"', 'permalink: foo', '---'].join('\n'); const file = newFile({ path: 'hello.swig', @@ -318,24 +322,20 @@ describe('asset', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const page = Page.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const page = Page.findOne({ source: file.path }); - page.path.should.eql('foo.html'); + page.path.should.eql('foo.html'); - return Promise.all([ - page.remove(), - fs.unlink(file.source) - ]); - }); + return Promise.all([page.remove(), fs.unlink(file.source)]); + }); }); it('page - permalink (with trailing slash)', () => { - const body = [ - 'title: "Hello world"', - 'permalink: foo/', - '---' - ].join('\n'); + const body = ['title: "Hello world"', 'permalink: foo/', '---'].join('\n'); const file = newFile({ path: 'hello.swig', @@ -343,16 +343,16 @@ describe('asset', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const page = Page.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const page = Page.findOne({ source: file.path }); - page.path.should.eql('foo/index.html'); + page.path.should.eql('foo/index.html'); - return Promise.all([ - page.remove(), - fs.unlink(file.source) - ]); - }); + return Promise.all([page.remove(), fs.unlink(file.source)]); + }); }); it('page - set layout to false if output is not html', () => { @@ -364,24 +364,20 @@ describe('asset', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const page = Page.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const page = Page.findOne({ source: file.path }); - page.layout.should.eql('false'); + page.layout.should.eql('false'); - return Promise.all([ - page.remove(), - fs.unlink(file.source) - ]); - }); + return Promise.all([page.remove(), fs.unlink(file.source)]); + }); }); - it('page - don\'t set layout to false if layout is set but output is not html', () => { - const body = [ - 'layout: something', - '---', - 'foo: 1' - ].join('\n'); + it("page - don't set layout to false if layout is set but output is not html", () => { + const body = ['layout: something', '---', 'foo: 1'].join('\n'); const file = newFile({ path: 'test.yml', @@ -389,16 +385,16 @@ describe('asset', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const page = Page.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const page = Page.findOne({ source: file.path }); - page.layout.should.eql('something'); + page.layout.should.eql('something'); - return Promise.all([ - page.remove(), - fs.unlink(file.source) - ]); - }); + return Promise.all([page.remove(), fs.unlink(file.source)]); + }); }); it('page - parse date', () => { @@ -415,17 +411,17 @@ describe('asset', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const page = Page.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const page = Page.findOne({ source: file.path }); - page.date.format(dateFormat).should.eql('2014-04-24 00:00:00'); - page.updated.format(dateFormat).should.eql('2015-05-05 00:00:00'); + page.date.format(dateFormat).should.eql('2014-04-24 00:00:00'); + page.updated.format(dateFormat).should.eql('2015-05-05 00:00:00'); - return Promise.all([ - page.remove(), - fs.unlink(file.source) - ]); - }); + return Promise.all([page.remove(), fs.unlink(file.source)]); + }); }); it('page - use file stats instead if date is invalid', () => { @@ -442,23 +438,20 @@ describe('asset', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => Promise.all([ - file.stat(), - process(file) - ])).spread(stats => { - const page = Page.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => Promise.all([file.stat(), process(file)])) + .spread(stats => { + const page = Page.findOne({ source: file.path }); - page.date.toDate().should.eql(stats.ctime); - page.updated.toDate().should.eql(stats.mtime); + page.date.toDate().should.eql(stats.ctime); + page.updated.toDate().should.eql(stats.mtime); - return Promise.all([ - page.remove(), - fs.unlink(file.source) - ]); - }); + return Promise.all([page.remove(), fs.unlink(file.source)]); + }); }); - it('page - don\'t remove extension name', () => { + it("page - don't remove extension name", () => { const body = ''; const file = newFile({ @@ -467,16 +460,16 @@ describe('asset', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const page = Page.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const page = Page.findOne({ source: file.path }); - page.path.should.eql('test.min.js'); + page.path.should.eql('test.min.js'); - return Promise.all([ - page.remove(), - fs.unlink(file.source) - ]); - }); + return Promise.all([page.remove(), fs.unlink(file.source)]); + }); }); it('page - timezone', () => { @@ -495,18 +488,25 @@ describe('asset', () => { hexo.config.timezone = 'UTC'; - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const page = Page.findOne({source: file.path}); - - page.date.utc().format(dateFormat).should.eql('2014-04-24 00:00:00'); - page.updated.utc().format(dateFormat).should.eql('2015-05-05 00:00:00'); - - return Promise.all([ - page.remove(), - fs.unlink(file.source) - ]); - }).finally(() => { - hexo.config.timezone = ''; - }); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const page = Page.findOne({ source: file.path }); + + page.date + .utc() + .format(dateFormat) + .should.eql('2014-04-24 00:00:00'); + page.updated + .utc() + .format(dateFormat) + .should.eql('2015-05-05 00:00:00'); + + return Promise.all([page.remove(), fs.unlink(file.source)]); + }) + .finally(() => { + hexo.config.timezone = ''; + }); }); }); diff --git a/test/scripts/processors/common.js b/test/scripts/processors/common.js index c0930038ca..04e0ebee0a 100644 --- a/test/scripts/processors/common.js +++ b/test/scripts/processors/common.js @@ -39,7 +39,9 @@ describe('common', () => { common.toDate(m).should.eql(m); common.toDate(d).should.eql(d); common.toDate(1e8).should.eql(new Date(1e8)); - common.toDate('2014-04-25T01:32:21.196Z').should.eql(new Date('2014-04-25T01:32:21.196Z')); + common + .toDate('2014-04-25T01:32:21.196Z') + .should.eql(new Date('2014-04-25T01:32:21.196Z')); common.toDate('Apr 24 2014').should.eql(new Date(2014, 3, 24)); should.not.exist(common.toDate('foo')); }); @@ -47,15 +49,23 @@ describe('common', () => { it('timezone() - date', () => { const d = new Date(Date.UTC(1972, 2, 29, 0, 0, 0)); const d_timezone_UTC = common.timezone(d, 'UTC'); - (common.timezone(d, 'Asia/Shanghai') - d_timezone_UTC).should.eql(-8 * 3600 * 1000); - (common.timezone(d, 'Asia/Bangkok') - d_timezone_UTC).should.eql(-7 * 3600 * 1000); - (common.timezone(d, 'America/Los_Angeles') - d_timezone_UTC).should.eql(8 * 3600 * 1000); + (common.timezone(d, 'Asia/Shanghai') - d_timezone_UTC).should.eql( + -8 * 3600 * 1000 + ); + (common.timezone(d, 'Asia/Bangkok') - d_timezone_UTC).should.eql( + -7 * 3600 * 1000 + ); + (common.timezone(d, 'America/Los_Angeles') - d_timezone_UTC).should.eql( + 8 * 3600 * 1000 + ); }); it('timezone() - moment', () => { const d = moment(new Date(Date.UTC(1972, 2, 29, 0, 0, 0))); const d_timezone_UTC = common.timezone(d, 'UTC'); - (common.timezone(d, 'Europe/Moscow') - d_timezone_UTC).should.eql(-3 * 3600 * 1000); + (common.timezone(d, 'Europe/Moscow') - d_timezone_UTC).should.eql( + -3 * 3600 * 1000 + ); }); it('isMatch() - string', () => { @@ -66,8 +76,10 @@ describe('common', () => { // Array common.isMatch('foo/test.html', []).should.be.false; common.isMatch('foo/test.html', ['foo/*.html']).should.be.true; - common.isMatch('foo/test.html', ['bar/*.html', 'foo/*.html']).should.be.true; - common.isMatch('foo/test.html', ['bar/*.html', 'baz/*.html']).should.be.false; + common.isMatch('foo/test.html', ['bar/*.html', 'foo/*.html']).should.be + .true; + common.isMatch('foo/test.html', ['bar/*.html', 'baz/*.html']).should.be + .false; // Undefined common.isMatch('foo/test.html').should.be.false; diff --git a/test/scripts/processors/data.js b/test/scripts/processors/data.js index c980c5ac15..cf504bbe11 100644 --- a/test/scripts/processors/data.js +++ b/test/scripts/processors/data.js @@ -47,13 +47,17 @@ describe('data', () => { type: 'create' }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const data = Data.findById('users'); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const data = Data.findById('users'); - data.data.should.eql({foo: 'bar'}); + data.data.should.eql({ foo: 'bar' }); - return data.remove(); - }).finally(() => fs.unlink(file.source)); + return data.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('type: create - json', () => { @@ -64,13 +68,17 @@ describe('data', () => { type: 'create' }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const data = Data.findById('users'); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const data = Data.findById('users'); - data.data.should.eql({foo: 1}); + data.data.should.eql({ foo: 1 }); - return data.remove(); - }).finally(() => fs.unlink(file.source)); + return data.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('type: create - others', () => { @@ -79,13 +87,17 @@ describe('data', () => { type: 'create' }); - return fs.writeFile(file.source, 'text').then(() => process(file)).then(() => { - const data = Data.findById('users'); + return fs + .writeFile(file.source, 'text') + .then(() => process(file)) + .then(() => { + const data = Data.findById('users'); - data.data.should.eql('text'); + data.data.should.eql('text'); - return data.remove(); - }).finally(() => fs.unlink(file.source)); + return data.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('type: update', () => { @@ -102,13 +114,16 @@ describe('data', () => { _id: 'users', data: {} }) - ]).then(() => process(file)).then(() => { - const data = Data.findById('users'); + ]) + .then(() => process(file)) + .then(() => { + const data = Data.findById('users'); - data.data.should.eql({foo: 'bar'}); + data.data.should.eql({ foo: 'bar' }); - return data.remove(); - }).finally(() => fs.unlink(file.source)); + return data.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('type: delete', () => { @@ -119,9 +134,11 @@ describe('data', () => { return Data.insert({ _id: 'users', - data: {foo: 'bar'} - }).then(() => process(file)).then(() => { - should.not.exist(Data.findById('users')); - }); + data: { foo: 'bar' } + }) + .then(() => process(file)) + .then(() => { + should.not.exist(Data.findById('users')); + }); }); }); diff --git a/test/scripts/processors/post.js b/test/scripts/processors/post.js index 3fa2eb09ff..d7d1fabc5c 100644 --- a/test/scripts/processors/post.js +++ b/test/scripts/processors/post.js @@ -82,7 +82,9 @@ describe('post', () => { // Skip render files hexo.config.skip_render = ['_posts/foo/**']; - pattern.match('_posts/foo/bar.html').should.have.property('renderable', false); + pattern + .match('_posts/foo/bar.html') + .should.have.property('renderable', false); hexo.config.skip_render = []; }); @@ -120,25 +122,25 @@ describe('post', () => { slug: 'foo' }), fs.writeFile(file.source, 'test') - ]).spread(doc => { - postId = doc._id; - return process(file); - }).then(() => { - const id = 'source/' + file.path; - const asset = PostAsset.findById(id); - - asset._id.should.eql(id); - asset.post.should.eql(postId); - asset.modified.should.be.true; - asset.renderable.should.be.false; - }).finally(() => { - hexo.config.post_asset_folder = false; + ]) + .spread(doc => { + postId = doc._id; + return process(file); + }) + .then(() => { + const id = 'source/' + file.path; + const asset = PostAsset.findById(id); + + asset._id.should.eql(id); + asset.post.should.eql(postId); + asset.modified.should.be.true; + asset.renderable.should.be.false; + }) + .finally(() => { + hexo.config.post_asset_folder = false; - return Promise.all([ - Post.removeById(postId), - fs.unlink(file.source) - ]); - }); + return Promise.all([Post.removeById(postId), fs.unlink(file.source)]); + }); }); it('asset - type: update', () => { @@ -160,26 +162,27 @@ describe('post', () => { slug: 'foo' }), fs.writeFile(file.source, 'test') - ]).spread(post => { - postId = post._id; + ]) + .spread(post => { + postId = post._id; + + return PostAsset.insert({ + _id: id, + slug: file.path, + modified: false, + post: postId + }); + }) + .then(() => process(file)) + .then(() => { + const asset = PostAsset.findById(id); + asset.modified.should.be.true; + }) + .finally(() => { + hexo.config.post_asset_folder = false; - return PostAsset.insert({ - _id: id, - slug: file.path, - modified: false, - post: postId + return Promise.all([Post.removeById(postId), fs.unlink(file.source)]); }); - }).then(() => process(file)).then(() => { - const asset = PostAsset.findById(id); - asset.modified.should.be.true; - }).finally(() => { - hexo.config.post_asset_folder = false; - - return Promise.all([ - Post.removeById(postId), - fs.unlink(file.source) - ]); - }); }); it('asset - type: skip', () => { @@ -201,26 +204,27 @@ describe('post', () => { slug: 'foo' }), fs.writeFile(file.source, 'test') - ]).spread(post => { - postId = post._id; + ]) + .spread(post => { + postId = post._id; + + return PostAsset.insert({ + _id: id, + slug: file.path, + modified: false, + post: postId + }); + }) + .then(() => process(file)) + .then(() => { + const asset = PostAsset.findById(id); + asset.modified.should.be.false; + }) + .finally(() => { + hexo.config.post_asset_folder = false; - return PostAsset.insert({ - _id: id, - slug: file.path, - modified: false, - post: postId + return Promise.all([Post.removeById(postId), fs.unlink(file.source)]); }); - }).then(() => process(file)).then(() => { - const asset = PostAsset.findById(id); - asset.modified.should.be.false; - }).finally(() => { - hexo.config.post_asset_folder = false; - - return Promise.all([ - Post.removeById(postId), - fs.unlink(file.source) - ]); - }); }); it('asset - type: delete', () => { @@ -239,24 +243,28 @@ describe('post', () => { return Post.insert({ source: '_posts/foo.html', slug: 'foo' - }).then(post => { - postId = post._id; - - return PostAsset.insert({ - _id: id, - slug: file.path, - modified: false, - post: postId + }) + .then(post => { + postId = post._id; + + return PostAsset.insert({ + _id: id, + slug: file.path, + modified: false, + post: postId + }); + }) + .then(() => process(file)) + .then(() => { + should.not.exist(PostAsset.findById(id)); + }) + .finally(() => { + hexo.config.post_asset_folder = false; + return Post.removeById(postId); }); - }).then(() => process(file)).then(() => { - should.not.exist(PostAsset.findById(id)); - }).finally(() => { - hexo.config.post_asset_folder = false; - return Post.removeById(postId); - }); }); - it('asset - skip if can\'t find a matching post', () => { + it("asset - skip if can't find a matching post", () => { hexo.config.post_asset_folder = true; const file = newFile({ @@ -268,13 +276,17 @@ describe('post', () => { const id = 'source/' + file.path; - return fs.writeFile(file.source, 'test').then(() => process(file)).then(() => { - should.not.exist(PostAsset.findById(id)); - }).finally(() => { - hexo.config.post_asset_folder = false; + return fs + .writeFile(file.source, 'test') + .then(() => process(file)) + .then(() => { + should.not.exist(PostAsset.findById(id)); + }) + .finally(() => { + hexo.config.post_asset_folder = false; - return fs.unlink(file.source); - }); + return fs.unlink(file.source); + }); }); it('asset - the related post has been deleted', () => { @@ -295,13 +307,16 @@ describe('post', () => { _id: id, slug: file.path }) - ]).then(() => process(file)).then(() => { - should.not.exist(PostAsset.findById(id)); - }).finally(() => { - hexo.config.post_asset_folder = false; + ]) + .then(() => process(file)) + .then(() => { + should.not.exist(PostAsset.findById(id)); + }) + .finally(() => { + hexo.config.post_asset_folder = false; - return fs.unlink(file.source); - }); + return fs.unlink(file.source); + }); }); it('post - type: create', () => { @@ -320,27 +335,28 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); - - post.title.should.eql('Hello world'); - post.date.format(dateFormat).should.eql('2006-01-02 15:04:05'); - post.updated.format(dateFormat).should.eql('2014-12-13 01:02:03'); - post._content.should.eql('The quick brown fox jumps over the lazy dog'); - post.source.should.eql(file.path); - post.raw.should.eql(body); - post.slug.should.eql('foo'); - post.published.should.be.true; - - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); + + post.title.should.eql('Hello world'); + post.date.format(dateFormat).should.eql('2006-01-02 15:04:05'); + post.updated.format(dateFormat).should.eql('2014-12-13 01:02:03'); + post._content.should.eql('The quick brown fox jumps over the lazy dog'); + post.source.should.eql(file.path); + post.raw.should.eql(body); + post.slug.should.eql('foo'); + post.published.should.be.true; + + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - type: update', () => { - const body = [ - 'title: "New world"', - '---' - ].join('\n'); + const body = ['title: "New world"', '---'].join('\n'); const file = newFile({ path: 'foo.html', @@ -352,19 +368,22 @@ describe('post', () => { let id; return Promise.all([ - Post.insert({source: file.path, slug: 'foo'}), + Post.insert({ source: file.path, slug: 'foo' }), fs.writeFile(file.source, body) - ]).spread(doc => { - id = doc._id; - return process(file); - }).then(() => { - const post = Post.findOne({source: file.path}); + ]) + .spread(doc => { + id = doc._id; + return process(file); + }) + .then(() => { + const post = Post.findOne({ source: file.path }); - post._id.should.eql(id); - post.title.should.eql('New world'); + post._id.should.eql(id); + post.title.should.eql('New world'); - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - type: delete', () => { @@ -378,16 +397,15 @@ describe('post', () => { return Post.insert({ source: file.path, slug: 'foo' - }).then(() => process(file)).then(() => { - should.not.exist(Post.findOne({source: file.path})); - }); + }) + .then(() => process(file)) + .then(() => { + should.not.exist(Post.findOne({ source: file.path })); + }); }); it('post - parse file name', () => { - const body = [ - 'title: "Hello world"', - '---' - ].join('\n'); + const body = ['title: "Hello world"', '---'].join('\n'); const file = newFile({ path: '2006/01/02/foo.html', @@ -398,24 +416,25 @@ describe('post', () => { hexo.config.new_post_name = ':year/:month/:day/:title'; - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.slug.should.eql('foo'); - post.date.format('YYYY-MM-DD').should.eql('2006-01-02'); + post.slug.should.eql('foo'); + post.date.format('YYYY-MM-DD').should.eql('2006-01-02'); - return post.remove(); - }).finally(() => { - hexo.config.new_post_name = newPostName; - return fs.unlink(file.source); - }); + return post.remove(); + }) + .finally(() => { + hexo.config.new_post_name = newPostName; + return fs.unlink(file.source); + }); }); it('post - extra data in file name', () => { - const body = [ - 'title: "Hello world"', - '---' - ].join('\n'); + const body = ['title: "Hello world"', '---'].join('\n'); const file = newFile({ path: 'zh/foo.html', @@ -426,23 +445,24 @@ describe('post', () => { hexo.config.new_post_name = ':lang/:title'; - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.lang.should.eql('zh'); + post.lang.should.eql('zh'); - return post.remove(); - }).finally(() => { - hexo.config.new_post_name = newPostName; - return fs.unlink(file.source); - }); + return post.remove(); + }) + .finally(() => { + hexo.config.new_post_name = newPostName; + return fs.unlink(file.source); + }); }); it('post - file name does not match to the config', () => { - const body = [ - 'title: "Hello world"', - '---' - ].join('\n'); + const body = ['title: "Hello world"', '---'].join('\n'); const file = newFile({ path: 'foo.html', @@ -453,24 +473,24 @@ describe('post', () => { hexo.config.new_post_name = ':year/:month/:day/:title'; - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.slug.should.eql('foo'); + post.slug.should.eql('foo'); - return post.remove(); - }).finally(() => { - hexo.config.new_post_name = newPostName; - return fs.unlink(file.source); - }); + return post.remove(); + }) + .finally(() => { + hexo.config.new_post_name = newPostName; + return fs.unlink(file.source); + }); }); it('post - published', () => { - const body = [ - 'title: "Hello world"', - 'published: false', - '---' - ].join('\n'); + const body = ['title: "Hello world"', 'published: false', '---'].join('\n'); const file = newFile({ path: 'zh/foo.html', @@ -479,21 +499,21 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.published.should.be.false; + post.published.should.be.false; - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - always set published: false for drafts', () => { - const body = [ - 'title: "Hello world"', - 'published: true', - '---' - ].join('\n'); + const body = ['title: "Hello world"', 'published: true', '---'].join('\n'); const file = newFile({ path: 'foo.html', @@ -502,20 +522,21 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.published.should.be.false; + post.published.should.be.false; - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - use the status of the source file if date not set', () => { - const body = [ - 'title: "Hello world"', - '---' - ].join('\n'); + const body = ['title: "Hello world"', '---'].join('\n'); const file = newFile({ path: 'foo.html', @@ -524,17 +545,24 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => Promise.all([ - file.stat(), - process(file) - ])).spread(stats => { - const post = Post.findOne({source: file.path}); - - post.date.toDate().setMilliseconds(0).should.eql(stats.birthtime.setMilliseconds(0)); - post.updated.toDate().setMilliseconds(0).should.eql(stats.mtime.setMilliseconds(0)); - - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return fs + .writeFile(file.source, body) + .then(() => Promise.all([file.stat(), process(file)])) + .spread(stats => { + const post = Post.findOne({ source: file.path }); + + post.date + .toDate() + .setMilliseconds(0) + .should.eql(stats.birthtime.setMilliseconds(0)); + post.updated + .toDate() + .setMilliseconds(0) + .should.eql(stats.mtime.setMilliseconds(0)); + + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - photo is an alias for photos', () => { @@ -553,18 +581,22 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.photos.should.eql([ - 'https://hexo.io/foo.jpg', - 'https://hexo.io/bar.png' - ]); + post.photos.should.eql([ + 'https://hexo.io/foo.jpg', + 'https://hexo.io/bar.png' + ]); - should.not.exist(post.photo); + should.not.exist(post.photo); - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - photos (not array)', () => { @@ -581,22 +613,21 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.photos.should.eql([ - 'https://hexo.io/foo.jpg' - ]); + post.photos.should.eql(['https://hexo.io/foo.jpg']); - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - link without title', () => { - const body = [ - 'link: https://hexo.io/', - '---' - ].join('\n'); + const body = ['link: https://hexo.io/', '---'].join('\n'); const file = newFile({ path: 'foo.html', @@ -605,17 +636,20 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.link.should.eql('https://hexo.io/'); - post.title.should.eql('hexo.io'); + post.link.should.eql('https://hexo.io/'); + post.title.should.eql('hexo.io'); - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); - it('post - link without title and link', () => { const body = ''; @@ -626,13 +660,17 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.title.should.eql('foo'); + post.title.should.eql('foo'); - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - category is an alias for categories', () => { @@ -651,22 +689,22 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - should.not.exist(post.category); - post.categories.map(item => item.name).should.eql(['foo', 'bar']); + should.not.exist(post.category); + post.categories.map(item => item.name).should.eql(['foo', 'bar']); - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - categories (not array)', () => { - const body = [ - 'title: "Hello world"', - 'categories: foo', - '---' - ].join('\n'); + const body = ['title: "Hello world"', 'categories: foo', '---'].join('\n'); const file = newFile({ path: 'foo.html', @@ -675,13 +713,17 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.categories.map(item => item.name).should.eql(['foo']); + post.categories.map(item => item.name).should.eql(['foo']); - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - categories (multiple hierarchies)', () => { @@ -700,13 +742,19 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.categories.map(item => item.name).should.eql(['foo', 'bar', 'baz']); + post.categories + .map(item => item.name) + .should.eql(['foo', 'bar', 'baz']); - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - tag is an alias for tags', () => { @@ -725,22 +773,22 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - should.not.exist(post.tag); - post.tags.map(item => item.name).should.have.members(['foo', 'bar']); + should.not.exist(post.tag); + post.tags.map(item => item.name).should.have.members(['foo', 'bar']); - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - tags (not array)', () => { - const body = [ - 'title: "Hello world"', - 'tags: foo', - '---' - ].join('\n'); + const body = ['title: "Hello world"', 'tags: foo', '---'].join('\n'); const file = newFile({ path: 'foo.html', @@ -749,22 +797,23 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.tags.map(item => item.name).should.eql(['foo']); + post.tags.map(item => item.name).should.eql(['foo']); - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - post_asset_folder enabled', () => { hexo.config.post_asset_folder = true; - const body = [ - 'title: "Hello world"', - '---' - ].join('\n'); + const body = ['title: "Hello world"', '---'].join('\n'); const file = newFile({ path: 'foo.html', @@ -779,23 +828,23 @@ describe('post', () => { return Promise.all([ fs.writeFile(file.source, body), fs.writeFile(assetPath, '') - ]).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); - const asset = PostAsset.findById(assetId); + ]) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); + const asset = PostAsset.findById(assetId); - asset._id.should.eql(assetId); - asset.post.should.eql(post._id); - asset.modified.should.be.true; + asset._id.should.eql(assetId); + asset.post.should.eql(post._id); + asset.modified.should.be.true; - return post.remove(); - }).finally(() => { - hexo.config.post_asset_folder = false; + return post.remove(); + }) + .finally(() => { + hexo.config.post_asset_folder = false; - return Promise.all([ - fs.unlink(file.source), - fs.unlink(assetPath) - ]); - }); + return Promise.all([fs.unlink(file.source), fs.unlink(assetPath)]); + }); }); it('post - post_asset_folder disabled', () => { @@ -814,15 +863,17 @@ describe('post', () => { return Promise.all([ fs.writeFile(file.source, ''), fs.writeFile(assetPath, '') - ]).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); - should.not.exist(PostAsset.findById(assetId)); + ]) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); + should.not.exist(PostAsset.findById(assetId)); - return post.remove(); - }).finally(() => Promise.all([ - fs.unlink(file.source), - fs.unlink(assetPath) - ])); + return post.remove(); + }) + .finally(() => + Promise.all([fs.unlink(file.source), fs.unlink(assetPath)]) + ); }); it('post - parse date', () => { @@ -840,14 +891,18 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.date.format(dateFormat).should.eql('2014-04-24 00:00:00'); - post.updated.format(dateFormat).should.eql('2015-05-05 00:00:00'); + post.date.format(dateFormat).should.eql('2014-04-24 00:00:00'); + post.updated.format(dateFormat).should.eql('2015-05-05 00:00:00'); - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - use file stats instead if date is invalid', () => { @@ -865,17 +920,24 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => Promise.all([ - file.stat(), - process(file) - ])).spread(stats => { - const post = Post.findOne({source: file.path}); - - post.date.toDate().setMilliseconds(0).should.eql(stats.birthtime.setMilliseconds(0)); - post.updated.toDate().setMilliseconds(0).should.eql(stats.mtime.setMilliseconds(0)); - - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return fs + .writeFile(file.source, body) + .then(() => Promise.all([file.stat(), process(file)])) + .spread(stats => { + const post = Post.findOne({ source: file.path }); + + post.date + .toDate() + .setMilliseconds(0) + .should.eql(stats.birthtime.setMilliseconds(0)); + post.updated + .toDate() + .setMilliseconds(0) + .should.eql(stats.mtime.setMilliseconds(0)); + + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('post - timezone', () => { @@ -895,24 +957,31 @@ describe('post', () => { hexo.config.timezone = 'UTC'; - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); - - post.date.utc().format(dateFormat).should.eql('2014-04-24 00:00:00'); - post.updated.utc().format(dateFormat).should.eql('2015-05-05 00:00:00'); - - return post.remove(); - }).finally(() => { - hexo.config.timezone = ''; - return fs.unlink(file.source); - }); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); + + post.date + .utc() + .format(dateFormat) + .should.eql('2014-04-24 00:00:00'); + post.updated + .utc() + .format(dateFormat) + .should.eql('2015-05-05 00:00:00'); + + return post.remove(); + }) + .finally(() => { + hexo.config.timezone = ''; + return fs.unlink(file.source); + }); }); it('post - new_post_name timezone', () => { - const body = [ - 'title: "Hello world"', - '---' - ].join('\n'); + const body = ['title: "Hello world"', '---'].join('\n'); const file = newFile({ path: '2006/01/02/foo.html', @@ -924,26 +993,29 @@ describe('post', () => { hexo.config.new_post_name = ':year/:month/:day/:title'; hexo.config.timezone = 'UTC'; - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); - post.date.utc().format(dateFormat).should.eql('2006-01-02 00:00:00'); + post.date + .utc() + .format(dateFormat) + .should.eql('2006-01-02 00:00:00'); - return post.remove(); - }).finally(() => { - hexo.config.new_post_name = newPostName; - hexo.config.timezone = ''; + return post.remove(); + }) + .finally(() => { + hexo.config.new_post_name = newPostName; + hexo.config.timezone = ''; - return fs.unlink(file.source); - }); + return fs.unlink(file.source); + }); }); it('post - permalink', () => { - const body = [ - 'title: "Hello world"', - 'permalink: foooo', - '---' - ].join('\n'); + const body = ['title: "Hello world"', 'permalink: foooo', '---'].join('\n'); const file = newFile({ path: 'test.html', @@ -952,11 +1024,15 @@ describe('post', () => { renderable: true }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const post = Post.findOne({source: file.path}); - post.slug.should.eql('foooo'); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const post = Post.findOne({ source: file.path }); + post.slug.should.eql('foooo'); - return post.remove(); - }).finally(() => fs.unlink(file.source)); + return post.remove(); + }) + .finally(() => fs.unlink(file.source)); }); }); diff --git a/test/scripts/renderers/json.js b/test/scripts/renderers/json.js index aa7896229b..ece9c068d8 100644 --- a/test/scripts/renderers/json.js +++ b/test/scripts/renderers/json.js @@ -11,6 +11,6 @@ describe('json', () => { } }; - r({text: JSON.stringify(data)}).should.eql(data); + r({ text: JSON.stringify(data) }).should.eql(data); }); }); diff --git a/test/scripts/renderers/plain.js b/test/scripts/renderers/plain.js index 18d1ec0382..22681383a6 100644 --- a/test/scripts/renderers/plain.js +++ b/test/scripts/renderers/plain.js @@ -4,6 +4,6 @@ describe('plain', () => { const r = require('../../../lib/plugins/renderer/plain'); it('normal', () => { - r({text: '123'}).should.eql('123'); + r({ text: '123' }).should.eql('123'); }); }); diff --git a/test/scripts/renderers/swig.js b/test/scripts/renderers/swig.js index 53727bb163..97d9f3c614 100644 --- a/test/scripts/renderers/swig.js +++ b/test/scripts/renderers/swig.js @@ -4,21 +4,18 @@ describe('swig', () => { const r = require('../../../lib/plugins/renderer/swig'); it('normal', () => { - const body = [ - 'Hello {{ name }}!' - ].join('\n'); + const body = ['Hello {{ name }}!'].join('\n'); - r({text: body}, { - name: 'world' - }).should.eql('Hello world!'); + r( + { text: body }, + { + name: 'world' + } + ).should.eql('Hello world!'); }); it('override "for" tag', () => { - const body = [ - '{% for x in arr %}', - '{{ x }}', - '{% endfor %}' - ].join(''); + const body = ['{% for x in arr %}', '{{ x }}', '{% endfor %}'].join(''); const data = { arr: { @@ -28,13 +25,11 @@ describe('swig', () => { } }; - r({text: body}, data).should.eql('123'); + r({ text: body }, data).should.eql('123'); }); it('compile', () => { - const body = [ - 'Hello {{ name }}!' - ].join('\n'); + const body = ['Hello {{ name }}!'].join('\n'); const render = r.compile({ text: body diff --git a/test/scripts/renderers/yaml.js b/test/scripts/renderers/yaml.js index 3f734d1766..c4b8843226 100644 --- a/test/scripts/renderers/yaml.js +++ b/test/scripts/renderers/yaml.js @@ -4,17 +4,13 @@ describe('yaml', () => { const r = require('../../../lib/plugins/renderer/yaml'); it('normal', () => { - r({text: 'foo: 1'}).should.eql({foo: 1}); + r({ text: 'foo: 1' }).should.eql({ foo: 1 }); }); it('escape', () => { - const body = [ - 'foo: 1', - 'bar:', - '\tbaz: 3' - ].join('\n'); + const body = ['foo: 1', 'bar:', '\tbaz: 3'].join('\n'); - r({text: body}).should.eql({ + r({ text: body }).should.eql({ foo: 1, bar: { baz: 3 diff --git a/test/scripts/tags/asset_img.js b/test/scripts/tags/asset_img.js index 1399654176..8827d8dcbb 100644 --- a/test/scripts/tags/asset_img.js +++ b/test/scripts/tags/asset_img.js @@ -16,48 +16,64 @@ describe('asset_img', () => { return assetImgTag.call(post, args.split(' ')); } - before(() => hexo.init().then(() => Post.insert({ - source: 'foo.md', - slug: 'foo' - })).then(post_ => { - post = post_; + before(() => + hexo + .init() + .then(() => + Post.insert({ + source: 'foo.md', + slug: 'foo' + }) + ) + .then(post_ => { + post = post_; - return Promise.all([ - PostAsset.insert({ - _id: 'bar', - slug: 'bar', - post: post._id - }), - PostAsset.insert({ - _id: 'spaced asset', - slug: 'spaced asset', - post: post._id + return Promise.all([ + PostAsset.insert({ + _id: 'bar', + slug: 'bar', + post: post._id + }), + PostAsset.insert({ + _id: 'spaced asset', + slug: 'spaced asset', + post: post._id + }) + ]); }) - ]); - })); + ); it('default', () => { assetImg('bar').should.eql(''); }); it('default', () => { - assetImg('bar title').should.eql(''); + assetImg('bar title').should.eql( + '' + ); }); it('with space', () => { // {% asset_img "spaced asset" "spaced title" %} - assetImgTag.call(post, ['spaced asset', 'spaced title']) - .should.eql(''); + assetImgTag + .call(post, ['spaced asset', 'spaced title']) + .should.eql( + '' + ); }); it('with alt and title', () => { - assetImgTag.call(post, ['bar', '"title"', '"alt"']) + assetImgTag + .call(post, ['bar', '"title"', '"alt"']) .should.eql(''); }); it('with width height alt and title', () => { - assetImgTag.call(post, ['bar', '100', '200', '"title"', '"alt"']) - .should.eql(''); + assetImgTag + .call(post, ['bar', '100', '200', '"title"', '"alt"']) + .should.eql( + '' + ); }); it('no slug', () => { diff --git a/test/scripts/tags/asset_link.js b/test/scripts/tags/asset_link.js index d95697b724..a500ef5590 100644 --- a/test/scripts/tags/asset_link.js +++ b/test/scripts/tags/asset_link.js @@ -16,38 +16,50 @@ describe('asset_link', () => { return assetLinkTag.call(post, args.split(' ')); } - before(() => hexo.init().then(() => Post.insert({ - source: 'foo.md', - slug: 'foo' - })).then(post_ => { - post = post_; - - return Promise.all([ - PostAsset.insert({ - _id: 'bar', - slug: 'bar', - post: post._id - }), - PostAsset.insert({ - _id: 'spaced asset', - slug: 'spaced asset', - post: post._id + before(() => + hexo + .init() + .then(() => + Post.insert({ + source: 'foo.md', + slug: 'foo' + }) + ) + .then(post_ => { + post = post_; + + return Promise.all([ + PostAsset.insert({ + _id: 'bar', + slug: 'bar', + post: post._id + }), + PostAsset.insert({ + _id: 'spaced asset', + slug: 'spaced asset', + post: post._id + }) + ]); }) - ]); - })); + ); it('default', () => { assetLink('bar').should.eql('bar'); }); it('title', () => { - assetLink('bar Hello world').should.eql('Hello world'); + assetLink('bar Hello world').should.eql( + 'Hello world' + ); }); it('with space', () => { // {% asset_link "spaced asset" "spaced title" %} - assetLinkTag.call(post, ['spaced asset', 'spaced title']) - .should.eql('spaced title'); + assetLinkTag + .call(post, ['spaced asset', 'spaced title']) + .should.eql( + 'spaced title' + ); }); it('no slug', () => { diff --git a/test/scripts/tags/asset_path.js b/test/scripts/tags/asset_path.js index 60c50086fe..74861d1165 100644 --- a/test/scripts/tags/asset_path.js +++ b/test/scripts/tags/asset_path.js @@ -16,25 +16,32 @@ describe('asset_path', () => { return assetPathTag.call(post, args.split(' ')); } - before(() => hexo.init().then(() => Post.insert({ - source: 'foo.md', - slug: 'foo' - })).then(post_ => { - post = post_; - - return Promise.all([ - PostAsset.insert({ - _id: 'bar', - slug: 'bar', - post: post._id - }), - PostAsset.insert({ - _id: 'spaced asset', - slug: 'spaced asset', - post: post._id + before(() => + hexo + .init() + .then(() => + Post.insert({ + source: 'foo.md', + slug: 'foo' + }) + ) + .then(post_ => { + post = post_; + + return Promise.all([ + PostAsset.insert({ + _id: 'bar', + slug: 'bar', + post: post._id + }), + PostAsset.insert({ + _id: 'spaced asset', + slug: 'spaced asset', + post: post._id + }) + ]); }) - ]); - })); + ); it('default', () => { assetPath('bar').should.eql('/foo/bar'); @@ -42,8 +49,7 @@ describe('asset_path', () => { it('with space', () => { // {% asset_path "spaced asset" %} - assetPathTag.call(post, ['spaced asset']) - .should.eql('/foo/spaced%20asset'); + assetPathTag.call(post, ['spaced asset']).should.eql('/foo/spaced%20asset'); }); it('no slug', () => { diff --git a/test/scripts/tags/blockquote.js b/test/scripts/tags/blockquote.js index 09be0d9010..866eb46e83 100644 --- a/test/scripts/tags/blockquote.js +++ b/test/scripts/tags/blockquote.js @@ -5,40 +5,56 @@ describe('blockquote', () => { const hexo = new Hexo(__dirname); const blockquote = require('../../../lib/plugins/tag/blockquote')(hexo); - before(() => hexo.init().then(() => hexo.loadPlugin(require.resolve('hexo-renderer-marked')))); + before(() => + hexo + .init() + .then(() => hexo.loadPlugin(require.resolve('hexo-renderer-marked'))) + ); const bq = (args, content) => blockquote(args.split(' '), content || ''); it('default', () => { const result = bq('', '123456 **bold** and *italic*'); - result.should.eql(''); + result.should.eql( + '123456 bold and italic
\n' + ); }); it('author', () => { const result = bq('John Doe', ''); - result.should.eql(''); + result.should.eql( + '' + ); }); it('source', () => { const result = bq('Jane Austen, Pride and Prejudice'); - result.should.eql(''); + result.should.eql( + '' + ); }); it('link', () => { const result = bq('John Doe https://hexo.io/'); - result.should.eql(''); + result.should.eql( + '' + ); }); it('link title', () => { const result = bq('John Doe https://hexo.io/ Hexo'); - result.should.eql(''); + result.should.eql( + '' + ); }); it('titlecase', () => { hexo.config.titlecase = true; const result = bq('Jane Austen, pride and prejudice'); - result.should.eql(''); + result.should.eql( + '' + ); hexo.config.titlecase = false; }); diff --git a/test/scripts/tags/code.js b/test/scripts/tags/code.js index 2c30d4caae..23e8a3b32d 100644 --- a/test/scripts/tags/code.js +++ b/test/scripts/tags/code.js @@ -9,18 +9,15 @@ describe('code', () => { const codeTag = require('../../../lib/plugins/tag/code')(hexo); const escapeHTML = util.escapeHTML; - const fixture = [ - 'if (tired && night){', - ' sleep();', - '}' - ].join('\n'); + const fixture = ['if (tired && night){', ' sleep();', '}'].join('\n'); function code(args, content) { return codeTag(args.split(' '), content); } function highlight(code, options) { - return util.highlight(code, options || {}) + return util + .highlight(code, options || {}) .replace(/{/g, '{') .replace(/}/g, '}'); } @@ -45,20 +42,26 @@ describe('code', () => { it('lang', () => { const result = code('lang:js', fixture); - result.should.eql(highlight(fixture, { - lang: 'js' - })); + result.should.eql( + highlight(fixture, { + lang: 'js' + }) + ); }); it('line_number', () => { let result = code('line_number:false', fixture); - result.should.eql(highlight(fixture, { - gutter: false - })); + result.should.eql( + highlight(fixture, { + gutter: false + }) + ); result = code('line_number:true', fixture); - result.should.eql(highlight(fixture, { - gutter: true - })); + result.should.eql( + highlight(fixture, { + gutter: true + }) + ); }); it('highlight disable', () => { @@ -68,9 +71,11 @@ describe('code', () => { it('title', () => { const result = code('Hello world', fixture); - result.should.eql(highlight(fixture, { - caption: 'Hello world' - })); + result.should.eql( + highlight(fixture, { + caption: 'Hello world' + }) + ); }); it('link', () => { @@ -102,33 +107,39 @@ describe('code', () => { it('first_line', () => { let result = code('first_line:1234', fixture); - result.should.eql(highlight(fixture, { - firstLine: 1234 - })); + result.should.eql( + highlight(fixture, { + firstLine: 1234 + }) + ); result = code('', fixture); - result.should.eql(highlight(fixture, { - firstLine: 1 - })); + result.should.eql( + highlight(fixture, { + firstLine: 1 + }) + ); }); it('mark', () => { const source = [ - 'const http = require(\'http\');', + "const http = require('http');", '', - 'const hostname = \'127.0.0.1\';', + "const hostname = '127.0.0.1';", 'const port = 1337;', '', 'http.createServer((req, res) => {', - ' res.writeHead(200, { \'Content-Type\': \'text/plain\' });', - ' res.end(\'Hello World\n\');', + " res.writeHead(200, { 'Content-Type': 'text/plain' });", + " res.end('Hello World\n');", '}).listen(port, hostname, () => {', ' console.log(`Server running at http://${hostname}:${port}/`);', '});' ].join('\n'); const result = code('mark:1,7-8,10', source); - result.should.eql(highlight(source, { - mark: [1, 7, 8, 10] - })); + result.should.eql( + highlight(source, { + mark: [1, 7, 8, 10] + }) + ); }); it('# lines', () => { diff --git a/test/scripts/tags/gist.js b/test/scripts/tags/gist.js index 5520e82aeb..a39340078c 100644 --- a/test/scripts/tags/gist.js +++ b/test/scripts/tags/gist.js @@ -7,11 +7,15 @@ describe('gist', () => { it('id', () => { const $ = cheerio.load(gist(['foo'])); - $('script').attr('src').should.eql('//gist.github.com/foo.js'); + $('script') + .attr('src') + .should.eql('//gist.github.com/foo.js'); }); it('file', () => { const $ = cheerio.load(gist(['foo', 'bar'])); - $('script').attr('src').should.eql('//gist.github.com/foo.js?file=bar'); + $('script') + .attr('src') + .should.eql('//gist.github.com/foo.js?file=bar'); }); }); diff --git a/test/scripts/tags/iframe.js b/test/scripts/tags/iframe.js index 41d9a7ded8..328cff64c8 100644 --- a/test/scripts/tags/iframe.js +++ b/test/scripts/tags/iframe.js @@ -8,30 +8,60 @@ describe('iframe', () => { it('url', () => { const $ = cheerio.load(iframe(['https://zespia.tw'])); - $('iframe').attr('src').should.eql('https://zespia.tw'); - $('iframe').attr('width').should.eql('100%'); - $('iframe').attr('height').should.eql('300'); - $('iframe').attr('frameborder').should.eql('0'); - $('iframe').attr('allowfullscreen').should.eql(''); + $('iframe') + .attr('src') + .should.eql('https://zespia.tw'); + $('iframe') + .attr('width') + .should.eql('100%'); + $('iframe') + .attr('height') + .should.eql('300'); + $('iframe') + .attr('frameborder') + .should.eql('0'); + $('iframe') + .attr('allowfullscreen') + .should.eql(''); }); it('width', () => { const $ = cheerio.load(iframe(['https://zespia.tw', '500'])); - $('iframe').attr('src').should.eql('https://zespia.tw'); - $('iframe').attr('width').should.eql('500'); - $('iframe').attr('height').should.eql('300'); - $('iframe').attr('frameborder').should.eql('0'); - $('iframe').attr('allowfullscreen').should.eql(''); + $('iframe') + .attr('src') + .should.eql('https://zespia.tw'); + $('iframe') + .attr('width') + .should.eql('500'); + $('iframe') + .attr('height') + .should.eql('300'); + $('iframe') + .attr('frameborder') + .should.eql('0'); + $('iframe') + .attr('allowfullscreen') + .should.eql(''); }); it('height', () => { const $ = cheerio.load(iframe(['https://zespia.tw', '500', '600'])); - $('iframe').attr('src').should.eql('https://zespia.tw'); - $('iframe').attr('width').should.eql('500'); - $('iframe').attr('height').should.eql('600'); - $('iframe').attr('frameborder').should.eql('0'); - $('iframe').attr('allowfullscreen').should.eql(''); + $('iframe') + .attr('src') + .should.eql('https://zespia.tw'); + $('iframe') + .attr('width') + .should.eql('500'); + $('iframe') + .attr('height') + .should.eql('600'); + $('iframe') + .attr('frameborder') + .should.eql('0'); + $('iframe') + .attr('allowfullscreen') + .should.eql(''); }); }); diff --git a/test/scripts/tags/img.js b/test/scripts/tags/img.js index fd9b54db68..4fe307dd4a 100644 --- a/test/scripts/tags/img.js +++ b/test/scripts/tags/img.js @@ -13,118 +13,222 @@ describe('img', () => { it('src', () => { const $ = cheerio.load(img(['https://placekitten.com/200/300'])); - $('img').attr('src').should.eql('https://placekitten.com/200/300'); + $('img') + .attr('src') + .should.eql('https://placekitten.com/200/300'); }); it('src //', () => { const $ = cheerio.load(img(['//placekitten.com/200/300'])); - $('img').attr('src').should.eql('//placekitten.com/200/300'); + $('img') + .attr('src') + .should.eql('//placekitten.com/200/300'); }); it('internal src', () => { hexo.config.root = '/'; let $ = cheerio.load(img(['/images/test.jpg'])); - $('img').attr('src').should.eql('/images/test.jpg'); + $('img') + .attr('src') + .should.eql('/images/test.jpg'); hexo.config.url = 'http://yoursite.com/root'; hexo.config.root = '/root/'; $ = cheerio.load(img(['/images/test.jpg'])); - $('img').attr('src').should.eql('/root/images/test.jpg'); + $('img') + .attr('src') + .should.eql('/root/images/test.jpg'); }); it('class + src', () => { - const $ = cheerio.load(img('left https://placekitten.com/200/300'.split(' '))); - - $('img').attr('src').should.eql('https://placekitten.com/200/300'); - $('img').attr('class').should.eql('left'); + const $ = cheerio.load( + img('left https://placekitten.com/200/300'.split(' ')) + ); + + $('img') + .attr('src') + .should.eql('https://placekitten.com/200/300'); + $('img') + .attr('class') + .should.eql('left'); }); it('class + internal src', () => { hexo.config.root = '/'; let $ = cheerio.load(img('left /images/test.jpg'.split(' '))); - $('img').attr('src').should.eql('/images/test.jpg'); - $('img').attr('class').should.eql('left'); + $('img') + .attr('src') + .should.eql('/images/test.jpg'); + $('img') + .attr('class') + .should.eql('left'); hexo.config.url = 'http://yoursite.com/root'; hexo.config.root = '/root/'; $ = cheerio.load(img('left /images/test.jpg'.split(' '))); - $('img').attr('src').should.eql('/root/images/test.jpg'); - $('img').attr('class').should.eql('left'); + $('img') + .attr('src') + .should.eql('/root/images/test.jpg'); + $('img') + .attr('class') + .should.eql('left'); }); it('multiple classes + src', () => { - const $ = cheerio.load(img('left top https://placekitten.com/200/300'.split(' '))); - - $('img').attr('src').should.eql('https://placekitten.com/200/300'); - $('img').attr('class').should.eql('left top'); + const $ = cheerio.load( + img('left top https://placekitten.com/200/300'.split(' ')) + ); + + $('img') + .attr('src') + .should.eql('https://placekitten.com/200/300'); + $('img') + .attr('class') + .should.eql('left top'); }); it('multiple classes + internal src', () => { hexo.config.root = '/'; let $ = cheerio.load(img('left top /images/test.jpg'.split(' '))); - $('img').attr('src').should.eql('/images/test.jpg'); - $('img').attr('class').should.eql('left top'); + $('img') + .attr('src') + .should.eql('/images/test.jpg'); + $('img') + .attr('class') + .should.eql('left top'); hexo.config.url = 'http://yoursite.com/root'; hexo.config.root = '/root/'; $ = cheerio.load(img('left top /images/test.jpg'.split(' '))); - $('img').attr('src').should.eql('/root/images/test.jpg'); - $('img').attr('class').should.eql('left top'); + $('img') + .attr('src') + .should.eql('/root/images/test.jpg'); + $('img') + .attr('class') + .should.eql('left top'); }); it('class + src + width', () => { - const $ = cheerio.load(img('left https://placekitten.com/200/300 200'.split(' '))); - - $('img').attr('src').should.eql('https://placekitten.com/200/300'); - $('img').attr('class').should.eql('left'); - $('img').attr('width').should.eql('200'); + const $ = cheerio.load( + img('left https://placekitten.com/200/300 200'.split(' ')) + ); + + $('img') + .attr('src') + .should.eql('https://placekitten.com/200/300'); + $('img') + .attr('class') + .should.eql('left'); + $('img') + .attr('width') + .should.eql('200'); }); it('class + src + width + height', () => { - const $ = cheerio.load(img('left https://placekitten.com/200/300 200 300'.split(' '))); - - $('img').attr('src').should.eql('https://placekitten.com/200/300'); - $('img').attr('class').should.eql('left'); - $('img').attr('width').should.eql('200'); - $('img').attr('height').should.eql('300'); + const $ = cheerio.load( + img('left https://placekitten.com/200/300 200 300'.split(' ')) + ); + + $('img') + .attr('src') + .should.eql('https://placekitten.com/200/300'); + $('img') + .attr('class') + .should.eql('left'); + $('img') + .attr('width') + .should.eql('200'); + $('img') + .attr('height') + .should.eql('300'); }); it('class + src + title', () => { - const $ = cheerio.load(img('left https://placekitten.com/200/300 Place Kitten'.split(' '))); - - $('img').attr('src').should.eql('https://placekitten.com/200/300'); - $('img').attr('class').should.eql('left'); - $('img').attr('title').should.eql('Place Kitten'); + const $ = cheerio.load( + img('left https://placekitten.com/200/300 Place Kitten'.split(' ')) + ); + + $('img') + .attr('src') + .should.eql('https://placekitten.com/200/300'); + $('img') + .attr('class') + .should.eql('left'); + $('img') + .attr('title') + .should.eql('Place Kitten'); }); it('class + src + width + title', () => { - const $ = cheerio.load(img('left https://placekitten.com/200/300 200 Place Kitten'.split(' '))); - - $('img').attr('src').should.eql('https://placekitten.com/200/300'); - $('img').attr('class').should.eql('left'); - $('img').attr('width').should.eql('200'); - $('img').attr('title').should.eql('Place Kitten'); + const $ = cheerio.load( + img('left https://placekitten.com/200/300 200 Place Kitten'.split(' ')) + ); + + $('img') + .attr('src') + .should.eql('https://placekitten.com/200/300'); + $('img') + .attr('class') + .should.eql('left'); + $('img') + .attr('width') + .should.eql('200'); + $('img') + .attr('title') + .should.eql('Place Kitten'); }); it('class + src + width + height + title', () => { - const $ = cheerio.load(img('left https://placekitten.com/200/300 200 300 Place Kitten'.split(' '))); - - $('img').attr('src').should.eql('https://placekitten.com/200/300'); - $('img').attr('class').should.eql('left'); - $('img').attr('width').should.eql('200'); - $('img').attr('height').should.eql('300'); - $('img').attr('title').should.eql('Place Kitten'); + const $ = cheerio.load( + img( + 'left https://placekitten.com/200/300 200 300 Place Kitten'.split(' ') + ) + ); + + $('img') + .attr('src') + .should.eql('https://placekitten.com/200/300'); + $('img') + .attr('class') + .should.eql('left'); + $('img') + .attr('width') + .should.eql('200'); + $('img') + .attr('height') + .should.eql('300'); + $('img') + .attr('title') + .should.eql('Place Kitten'); }); it('class + src + width + height + title + alt', () => { - const $ = cheerio.load(img('left https://placekitten.com/200/300 200 300 "Place Kitten" "A cute kitten"'.split(' '))); - - $('img').attr('src').should.eql('https://placekitten.com/200/300'); - $('img').attr('class').should.eql('left'); - $('img').attr('width').should.eql('200'); - $('img').attr('height').should.eql('300'); - $('img').attr('title').should.eql('Place Kitten'); - $('img').attr('alt').should.eql('A cute kitten'); + const $ = cheerio.load( + img( + 'left https://placekitten.com/200/300 200 300 "Place Kitten" "A cute kitten"'.split( + ' ' + ) + ) + ); + + $('img') + .attr('src') + .should.eql('https://placekitten.com/200/300'); + $('img') + .attr('class') + .should.eql('left'); + $('img') + .attr('width') + .should.eql('200'); + $('img') + .attr('height') + .should.eql('300'); + $('img') + .attr('title') + .should.eql('Place Kitten'); + $('img') + .attr('alt') + .should.eql('A cute kitten'); }); }); diff --git a/test/scripts/tags/include_code.js b/test/scripts/tags/include_code.js index 610a8ee774..ee49382b16 100644 --- a/test/scripts/tags/include_code.js +++ b/test/scripts/tags/include_code.js @@ -8,14 +8,12 @@ const Promise = require('bluebird'); describe('include_code', () => { const Hexo = require('../../../lib/hexo'); const hexo = new Hexo(pathFn.join(__dirname, 'include_code_test')); - const includeCode = Promise.method(require('../../../lib/plugins/tag/include_code')(hexo)); + const includeCode = Promise.method( + require('../../../lib/plugins/tag/include_code')(hexo) + ); const path = pathFn.join(hexo.source_dir, hexo.config.code_dir, 'test.js'); - const fixture = [ - 'if (tired && night){', - ' sleep();', - '}' - ].join('\n'); + const fixture = ['if (tired && night){', ' sleep();', '}'].join('\n'); function code(args) { return includeCode(args.split(' ')); @@ -28,7 +26,8 @@ describe('include_code', () => { it('default', () => { const expected = highlight(fixture, { lang: 'js', - caption: 'test.jsview raw' + caption: + 'test.jsview raw' }); return code('test.js').then(result => { @@ -39,7 +38,8 @@ describe('include_code', () => { it('title', () => { const expected = highlight(fixture, { lang: 'js', - caption: 'Hello worldview raw' + caption: + 'Hello worldview raw' }); return code('Hello world test.js').then(result => { @@ -50,7 +50,8 @@ describe('include_code', () => { it('lang', () => { const expected = highlight(fixture, { lang: 'js', - caption: 'Hello worldview raw' + caption: + 'Hello worldview raw' }); return code('Hello world lang:js test.js').then(result => { @@ -59,12 +60,11 @@ describe('include_code', () => { }); it('from', () => { - const fixture = [ - '}' - ].join('\n'); + const fixture = ['}'].join('\n'); const expected = highlight(fixture, { lang: 'js', - caption: 'Hello worldview raw' + caption: + 'Hello worldview raw' }); return code('Hello world lang:js from:3 test.js').then(result => { @@ -73,13 +73,11 @@ describe('include_code', () => { }); it('to', () => { - const fixture = [ - 'if (tired && night){', - ' sleep();' - ].join('\n'); + const fixture = ['if (tired && night){', ' sleep();'].join('\n'); const expected = highlight(fixture, { lang: 'js', - caption: 'Hello worldview raw' + caption: + 'Hello worldview raw' }); return code('Hello world lang:js to:2 test.js').then(result => { @@ -88,12 +86,11 @@ describe('include_code', () => { }); it('from and to', () => { - const fixture = [ - 'sleep();' - ].join('\n'); + const fixture = ['sleep();'].join('\n'); const expected = highlight(fixture, { lang: 'js', - caption: 'Hello worldview raw' + caption: + 'Hello worldview raw' }); return code('Hello world lang:js from:2 to:2 test.js').then(result => { @@ -101,9 +98,10 @@ describe('include_code', () => { }); }); - it('file not found', () => code('nothing').then(result => { - should.not.exist(result); - })); + it('file not found', () => + code('nothing').then(result => { + should.not.exist(result); + })); it('disabled', () => { hexo.config.highlight.enable = false; diff --git a/test/scripts/tags/jsfiddle.js b/test/scripts/tags/jsfiddle.js index 55a85a5a4f..b964970d5d 100644 --- a/test/scripts/tags/jsfiddle.js +++ b/test/scripts/tags/jsfiddle.js @@ -8,46 +8,74 @@ describe('jsfiddle', () => { it('id', () => { const $ = cheerio.load(jsfiddle(['foo'])); - $('iframe').attr('src').should.eql('//jsfiddle.net/foo/embedded/js,resources,html,css,result/light'); + $('iframe') + .attr('src') + .should.eql( + '//jsfiddle.net/foo/embedded/js,resources,html,css,result/light' + ); }); it('tabs', () => { let $ = cheerio.load(jsfiddle(['foo', 'default'])); - $('iframe').attr('src').should.eql('//jsfiddle.net/foo/embedded/js,resources,html,css,result/light'); + $('iframe') + .attr('src') + .should.eql( + '//jsfiddle.net/foo/embedded/js,resources,html,css,result/light' + ); $ = cheerio.load(jsfiddle(['foo', 'html,css'])); - $('iframe').attr('src').should.eql('//jsfiddle.net/foo/embedded/html,css/light'); + $('iframe') + .attr('src') + .should.eql('//jsfiddle.net/foo/embedded/html,css/light'); }); it('skin', () => { let $ = cheerio.load(jsfiddle(['foo', 'default', 'default'])); - $('iframe').attr('src').should.eql('//jsfiddle.net/foo/embedded/js,resources,html,css,result/light'); + $('iframe') + .attr('src') + .should.eql( + '//jsfiddle.net/foo/embedded/js,resources,html,css,result/light' + ); $ = cheerio.load(jsfiddle(['foo', 'default', 'dark'])); - $('iframe').attr('src').should.eql('//jsfiddle.net/foo/embedded/js,resources,html,css,result/dark'); + $('iframe') + .attr('src') + .should.eql( + '//jsfiddle.net/foo/embedded/js,resources,html,css,result/dark' + ); }); it('width', () => { let $ = cheerio.load(jsfiddle(['foo', 'default', 'default', 'default'])); - $('iframe').attr('width').should.eql('100%'); + $('iframe') + .attr('width') + .should.eql('100%'); $ = cheerio.load(jsfiddle(['foo', 'default', 'default', '500'])); - $('iframe').attr('width').should.eql('500'); + $('iframe') + .attr('width') + .should.eql('500'); }); it('height', () => { - let $ = cheerio.load(jsfiddle(['foo', 'default', 'default', 'default', 'default'])); + let $ = cheerio.load( + jsfiddle(['foo', 'default', 'default', 'default', 'default']) + ); - $('iframe').attr('height').should.eql('300'); + $('iframe') + .attr('height') + .should.eql('300'); $ = cheerio.load(jsfiddle(['foo', 'default', 'default', 'default', '500'])); - $('iframe').attr('height').should.eql('500'); + $('iframe') + .attr('height') + .should.eql('500'); }); }); diff --git a/test/scripts/tags/link.js b/test/scripts/tags/link.js index 07740cceed..b5b163e0d0 100644 --- a/test/scripts/tags/link.js +++ b/test/scripts/tags/link.js @@ -6,48 +6,104 @@ describe('link', () => { const link = require('../../../lib/plugins/tag/link'); it('text + url', () => { - const $ = cheerio.load(link('Click here to Google https://google.com'.split(' '))); + const $ = cheerio.load( + link('Click here to Google https://google.com'.split(' ')) + ); - $('a').attr('href').should.eql('https://google.com'); - $('a').html().should.eql('Click here to Google'); + $('a') + .attr('href') + .should.eql('https://google.com'); + $('a') + .html() + .should.eql('Click here to Google'); }); it('text + url + external', () => { - let $ = cheerio.load(link('Click here to Google https://google.com true'.split(' '))); + let $ = cheerio.load( + link('Click here to Google https://google.com true'.split(' ')) + ); - $('a').attr('href').should.eql('https://google.com'); - $('a').html().should.eql('Click here to Google'); - $('a').attr('target').should.eql('_blank'); + $('a') + .attr('href') + .should.eql('https://google.com'); + $('a') + .html() + .should.eql('Click here to Google'); + $('a') + .attr('target') + .should.eql('_blank'); - $ = cheerio.load(link('Click here to Google https://google.com false'.split(' '))); + $ = cheerio.load( + link('Click here to Google https://google.com false'.split(' ')) + ); - $('a').attr('href').should.eql('https://google.com'); - $('a').html().should.eql('Click here to Google'); - $('a').attr('title').should.eql(''); - $('a').attr('target').should.eql(''); + $('a') + .attr('href') + .should.eql('https://google.com'); + $('a') + .html() + .should.eql('Click here to Google'); + $('a') + .attr('title') + .should.eql(''); + $('a') + .attr('target') + .should.eql(''); }); it('text + url + title', () => { - const $ = cheerio.load(link('Click here to Google https://google.com Google link'.split(' '))); + const $ = cheerio.load( + link('Click here to Google https://google.com Google link'.split(' ')) + ); - $('a').attr('href').should.eql('https://google.com'); - $('a').html().should.eql('Click here to Google'); - $('a').attr('title').should.eql('Google link'); + $('a') + .attr('href') + .should.eql('https://google.com'); + $('a') + .html() + .should.eql('Click here to Google'); + $('a') + .attr('title') + .should.eql('Google link'); }); it('text + url + external + title', () => { - let $ = cheerio.load(link('Click here to Google https://google.com true Google link'.split(' '))); + let $ = cheerio.load( + link( + 'Click here to Google https://google.com true Google link'.split(' ') + ) + ); - $('a').attr('href').should.eql('https://google.com'); - $('a').html().should.eql('Click here to Google'); - $('a').attr('target').should.eql('_blank'); - $('a').attr('title').should.eql('Google link'); + $('a') + .attr('href') + .should.eql('https://google.com'); + $('a') + .html() + .should.eql('Click here to Google'); + $('a') + .attr('target') + .should.eql('_blank'); + $('a') + .attr('title') + .should.eql('Google link'); - $ = cheerio.load(link('Click here to Google https://google.com false Google link'.split(' '))); + $ = cheerio.load( + link( + 'Click here to Google https://google.com false Google link'.split(' ') + ) + ); - $('a').attr('href').should.eql('https://google.com'); - $('a').html().should.eql('Click here to Google'); - $('a').attr('target').should.eql(''); - $('a').attr('title').should.eql('Google link'); + $('a') + .attr('href') + .should.eql('https://google.com'); + $('a') + .html() + .should.eql('Click here to Google'); + $('a') + .attr('target') + .should.eql(''); + $('a') + .attr('title') + .should.eql('Google link'); }); }); diff --git a/test/scripts/tags/post_link.js b/test/scripts/tags/post_link.js index af7db1f435..233cdbd28f 100644 --- a/test/scripts/tags/post_link.js +++ b/test/scripts/tags/post_link.js @@ -8,18 +8,28 @@ describe('post_link', () => { hexo.config.permalink = ':title/'; - before(() => hexo.init().then(() => Post.insert({ - source: 'foo', - slug: 'foo', - title: 'Hello world' - }))); + before(() => + hexo.init().then(() => + Post.insert([ + { + source: 'foo', + slug: 'foo', + title: 'Hello world' + } + ]) + ) + ); it('default', () => { - postLink(['foo']).should.eql('Hello world'); + postLink(['foo']).should.eql( + 'Hello world' + ); }); it('title', () => { - postLink(['foo', 'test']).should.eql('test'); + postLink(['foo', 'test']).should.eql( + 'test' + ); }); it('no slug', () => { diff --git a/test/scripts/tags/post_path.js b/test/scripts/tags/post_path.js index 260a2ec818..9ca72bd150 100644 --- a/test/scripts/tags/post_path.js +++ b/test/scripts/tags/post_path.js @@ -8,10 +8,16 @@ describe('post_path', () => { hexo.config.permalink = ':title/'; - before(() => hexo.init().then(() => Post.insert({ - source: 'foo', - slug: 'foo' - }))); + before(() => + hexo.init().then(() => + Post.insert([ + { + source: 'foo', + slug: 'foo' + } + ]) + ) + ); it('default', () => { postPath(['foo']).should.eql('/foo/'); diff --git a/test/scripts/tags/pullquote.js b/test/scripts/tags/pullquote.js index acc0dc9f62..7476c3db3b 100644 --- a/test/scripts/tags/pullquote.js +++ b/test/scripts/tags/pullquote.js @@ -5,11 +5,17 @@ describe('pullquote', () => { const hexo = new Hexo(__dirname); const pullquote = require('../../../lib/plugins/tag/pullquote')(hexo); - before(() => hexo.init().then(() => hexo.loadPlugin(require.resolve('hexo-renderer-marked')))); + before(() => + hexo + .init() + .then(() => hexo.loadPlugin(require.resolve('hexo-renderer-marked'))) + ); it('default', () => { const result = pullquote([], '123456 **bold** and *italic*'); - result.should.eql('123456 bold and italic
\n'); + result.should.eql( + '123456 bold and italic
\n' + ); }); it('class', () => { diff --git a/test/scripts/tags/vimeo.js b/test/scripts/tags/vimeo.js index 25a0f1fd12..e41ce395aa 100644 --- a/test/scripts/tags/vimeo.js +++ b/test/scripts/tags/vimeo.js @@ -9,8 +9,14 @@ describe('vimeo', () => { const $ = cheerio.load(vimeo(['foo'])); $('.video-container').html().should.be.ok; - $('iframe').attr('src').should.eql('//player.vimeo.com/video/foo'); - $('iframe').attr('frameborder').should.eql('0'); - $('iframe').attr('allowfullscreen').should.eql(''); + $('iframe') + .attr('src') + .should.eql('//player.vimeo.com/video/foo'); + $('iframe') + .attr('frameborder') + .should.eql('0'); + $('iframe') + .attr('allowfullscreen') + .should.eql(''); }); }); diff --git a/test/scripts/tags/youtube.js b/test/scripts/tags/youtube.js index 8e14196359..7b4d605712 100644 --- a/test/scripts/tags/youtube.js +++ b/test/scripts/tags/youtube.js @@ -9,8 +9,14 @@ describe('youtube', () => { const $ = cheerio.load(youtube(['foo'])); $('.video-container').html().should.be.ok; - $('iframe').attr('src').should.eql('//www.youtube.com/embed/foo'); - $('iframe').attr('frameborder').should.eql('0'); - $('iframe').attr('allowfullscreen').should.eql(''); + $('iframe') + .attr('src') + .should.eql('//www.youtube.com/embed/foo'); + $('iframe') + .attr('frameborder') + .should.eql('0'); + $('iframe') + .attr('allowfullscreen') + .should.eql(''); }); }); diff --git a/test/scripts/theme/theme.js b/test/scripts/theme/theme.js index 67bdebae5b..ffd0e7d9c9 100644 --- a/test/scripts/theme/theme.js +++ b/test/scripts/theme/theme.js @@ -6,13 +6,15 @@ const Promise = require('bluebird'); describe('Theme', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'theme_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'theme_test'), { silent: true }); const themeDir = pathFn.join(hexo.base_dir, 'themes', 'test'); - before(() => Promise.all([ - fs.mkdirs(themeDir), - fs.writeFile(hexo.config_path, 'theme: test') - ]).then(() => hexo.init())); + before(() => + Promise.all([ + fs.mkdirs(themeDir), + fs.writeFile(hexo.config_path, 'theme: test') + ]).then(() => hexo.init()) + ); after(() => fs.rmdir(hexo.base_dir)); @@ -34,7 +36,9 @@ describe('Theme', () => { it('getView() - escape backslashes', () => { hexo.theme.setView('foo/bar.swig', ''); - hexo.theme.getView('foo\\bar.swig').should.have.property('path', 'foo/bar.swig'); + hexo.theme + .getView('foo\\bar.swig') + .should.have.property('path', 'foo/bar.swig'); hexo.theme.removeView('foo/bar.swig'); }); diff --git a/test/scripts/theme/view.js b/test/scripts/theme/view.js index a48560ffff..e79158b90e 100644 --- a/test/scripts/theme/view.js +++ b/test/scripts/theme/view.js @@ -17,17 +17,20 @@ describe('View', () => { return new hexo.theme.View(path, data); } - before(() => Promise.all([ - fs.mkdirs(themeDir), - fs.writeFile(hexo.config_path, 'theme: test') - ]).then(() => hexo.init()).then(() => { - // Setup layout - hexo.theme.setView('layout.swig', [ - 'pre', - '{{ body }}', - 'post' - ].join('\n')); - })); + before(() => + Promise.all([ + fs.mkdirs(themeDir), + fs.writeFile(hexo.config_path, 'theme: test') + ]) + .then(() => hexo.init()) + .then(() => { + // Setup layout + hexo.theme.setView( + 'layout.swig', + ['pre', '{{ body }}', 'post'].join('\n') + ); + }) + ); after(() => fs.rmdir(hexo.base_dir)); @@ -43,11 +46,7 @@ describe('View', () => { }); it('parse front-matter', () => { - const body = [ - 'layout: false', - '---', - 'content' - ].join('\n'); + const body = ['layout: false', '---', 'content'].join('\n'); const view = newView('index.swig', body); @@ -61,15 +60,19 @@ describe('View', () => { const body = 'Hello {{ name }}'; const view = newView('index.swig', body); - view._compiledSync({ - name: 'Hexo' - }).should.eql('Hello Hexo'); - - return view._compiled({ - name: 'Hexo' - }).then(result => { - result.should.eql('Hello Hexo'); - }); + view + ._compiledSync({ + name: 'Hexo' + }) + .should.eql('Hello Hexo'); + + return view + ._compiled({ + name: 'Hexo' + }) + .then(result => { + result.should.eql('Hello Hexo'); + }); }); it('generate precompiled function even if renderer does not provide compile function', () => { @@ -80,111 +83,114 @@ describe('View', () => { const body = 'Hello {{ name }}'; const view = newView('index.swig', body); - view._compiledSync({ - name: 'Hexo' - }).should.eql('Hello Hexo'); - - return view._compiled({ - name: 'Hexo' - }).then(result => { - result.should.eql('Hello Hexo'); - }).finally(() => { - hexo.extend.renderer.store.swig.compile = compile; - }); + view + ._compiledSync({ + name: 'Hexo' + }) + .should.eql('Hello Hexo'); + + return view + ._compiled({ + name: 'Hexo' + }) + .then(result => { + result.should.eql('Hello Hexo'); + }) + .finally(() => { + hexo.extend.renderer.store.swig.compile = compile; + }); }); it('render()', () => { - const body = [ - '{{ test }}' - ].join('\n'); + const body = ['{{ test }}'].join('\n'); const view = newView('index.swig', body); - return view.render({ - test: 'foo' - }).then(content => { - content.should.eql('foo'); - }); + return view + .render({ + test: 'foo' + }) + .then(content => { + content.should.eql('foo'); + }); }); it('render() - front-matter', () => { // The priority of front-matter is higher - const body = [ - 'foo: bar', - '---', - '{{ foo }}', - '{{ test }}' - ].join('\n'); + const body = ['foo: bar', '---', '{{ foo }}', '{{ test }}'].join('\n'); const view = newView('index.swig', body); - return view.render({ - foo: 'foo', - test: 'test' - }).then(content => { - content.should.eql('bar\ntest'); - }); + return view + .render({ + foo: 'foo', + test: 'test' + }) + .then(content => { + content.should.eql('bar\ntest'); + }); }); it('render() - helper', () => { - const body = [ - '{{ date() }}' - ].join('\n'); + const body = ['{{ date() }}'].join('\n'); const view = newView('index.swig', body); - return view.render({ - config: hexo.config, - page: {} - }).then(content => { - content.should.eql(moment().format(hexo.config.date_format)); - }); + return view + .render({ + config: hexo.config, + page: {} + }) + .then(content => { + content.should.eql(moment().format(hexo.config.date_format)); + }); }); it('render() - layout', () => { const body = 'content'; const view = newView('index.swig', body); - return view.render({ - layout: 'layout' - }).then(content => { - content.should.eql('pre\n' + body + '\npost'); - }); + return view + .render({ + layout: 'layout' + }) + .then(content => { + content.should.eql('pre\n' + body + '\npost'); + }); }); it('render() - layout not found', () => { const body = 'content'; const view = newView('index.swig', body); - return view.render({ - layout: 'wtf' - }).then(content => { - content.should.eql(body); - }); + return view + .render({ + layout: 'wtf' + }) + .then(content => { + content.should.eql(body); + }); }); it('render() - callback', callback => { - const body = [ - '{{ test }}' - ].join('\n'); + const body = ['{{ test }}'].join('\n'); const view = newView('index.swig', body); - view.render({ - test: 'foo' - }, (err, content) => { - should.not.exist(err); - content.should.eql('foo'); - callback(); - }); + view.render( + { + test: 'foo' + }, + (err, content) => { + should.not.exist(err); + content.should.eql('foo'); + callback(); + } + ); }); it('render() - callback (without options)', callback => { - const body = [ - 'test: foo', - '---', - '{{ test }}' - ].join('\n'); + const body = ['test: foo', '---', '{{ test }}'].join('\n'); const view = newView('index.swig', body); @@ -196,9 +202,7 @@ describe('View', () => { }); it('render() - execute after_render:html', () => { - const body = [ - '{{ test }}' - ].join('\n'); + const body = ['{{ test }}'].join('\n'); const view = newView('index.swig', body); @@ -209,76 +213,76 @@ describe('View', () => { hexo.extend.filter.register('after_render:html', filter); - return view.render({ - test: 'foo' - }).then(content => { - content.should.eql('bar'); - }).finally(() => { - hexo.extend.filter.unregister('after_render:html', filter); - }); + return view + .render({ + test: 'foo' + }) + .then(content => { + content.should.eql('bar'); + }) + .finally(() => { + hexo.extend.filter.unregister('after_render:html', filter); + }); }); it('renderSync()', () => { - const body = [ - '{{ test }}' - ].join('\n'); + const body = ['{{ test }}'].join('\n'); const view = newView('index.swig', body); - view.renderSync({test: 'foo'}).should.eql('foo'); + view.renderSync({ test: 'foo' }).should.eql('foo'); }); it('renderSync() - front-matter', () => { // The priority of front-matter is higher - const body = [ - 'foo: bar', - '---', - '{{ foo }}', - '{{ test }}' - ].join('\n'); + const body = ['foo: bar', '---', '{{ foo }}', '{{ test }}'].join('\n'); const view = newView('index.swig', body); - view.renderSync({ - foo: 'foo', - test: 'test' - }).should.eql('bar\ntest'); + view + .renderSync({ + foo: 'foo', + test: 'test' + }) + .should.eql('bar\ntest'); }); it('renderSync() - helper', () => { - const body = [ - '{{ date() }}' - ].join('\n'); + const body = ['{{ date() }}'].join('\n'); const view = newView('index.swig', body); - view.renderSync({ - config: hexo.config, - page: {} - }).should.eql(moment().format(hexo.config.date_format)); + view + .renderSync({ + config: hexo.config, + page: {} + }) + .should.eql(moment().format(hexo.config.date_format)); }); it('renderSync() - layout', () => { const body = 'content'; const view = newView('index.swig', body); - view.renderSync({ - layout: 'layout' - }).should.eql('pre\n' + body + '\npost'); + view + .renderSync({ + layout: 'layout' + }) + .should.eql('pre\n' + body + '\npost'); }); it('renderSync() - layout not found', () => { const body = 'content'; const view = newView('index.swig', body); - view.renderSync({ - layout: 'wtf' - }).should.eql(body); + view + .renderSync({ + layout: 'wtf' + }) + .should.eql(body); }); it('renderSync() - execute after_render:html', () => { - const body = [ - '{{ test }}' - ].join('\n'); + const body = ['{{ test }}'].join('\n'); const view = newView('index.swig', body); @@ -288,7 +292,7 @@ describe('View', () => { }); hexo.extend.filter.register('after_render:html', filter); - view.renderSync({test: 'foo'}).should.eql('bar'); + view.renderSync({ test: 'foo' }).should.eql('bar'); hexo.extend.filter.unregister('after_render:html', filter); }); @@ -296,7 +300,9 @@ describe('View', () => { const view = newView('partials/header.swig', 'header'); // Relative path - view._resolveLayout('../layout').should.have.property('path', 'layout.swig'); + view + ._resolveLayout('../layout') + .should.have.property('path', 'layout.swig'); // Absolute path view._resolveLayout('layout').should.have.property('path', 'layout.swig'); diff --git a/test/scripts/theme_processors/config.js b/test/scripts/theme_processors/config.js index 5e8dd68d62..45fe0a1078 100644 --- a/test/scripts/theme_processors/config.js +++ b/test/scripts/theme_processors/config.js @@ -7,7 +7,9 @@ const Promise = require('bluebird'); describe('config', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'config_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'config_test'), { + silent: true + }); const processor = require('../../../lib/theme/processors/config'); const process = Promise.method(processor.process.bind(hexo)); const themeDir = pathFn.join(hexo.base_dir, 'themes', 'test'); @@ -17,10 +19,12 @@ describe('config', () => { return new hexo.theme.File(options); } - before(() => Promise.all([ - fs.mkdirs(themeDir), - fs.writeFile(hexo.config_path, 'theme: test') - ]).then(() => hexo.init())); + before(() => + Promise.all([ + fs.mkdirs(themeDir), + fs.writeFile(hexo.config_path, 'theme: test') + ]).then(() => hexo.init()) + ); after(() => fs.rmdir(hexo.base_dir)); @@ -34,11 +38,7 @@ describe('config', () => { }); it('type: create', () => { - const body = [ - 'name:', - ' first: John', - ' last: Doe' - ].join('\n'); + const body = ['name:', ' first: John', ' last: Doe'].join('\n'); const file = newFile({ path: '_config.yml', @@ -46,14 +46,18 @@ describe('config', () => { content: body }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - hexo.theme.config.should.eql({ - name: {first: 'John', last: 'Doe'} + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + hexo.theme.config.should.eql({ + name: { first: 'John', last: 'Doe' } + }); + }) + .finally(() => { + hexo.theme.config = {}; + return fs.unlink(file.source); }); - }).finally(() => { - hexo.theme.config = {}; - return fs.unlink(file.source); - }); }); it('type: delete', () => { @@ -62,7 +66,7 @@ describe('config', () => { type: 'delete' }); - hexo.theme.config = {foo: 'bar'}; + hexo.theme.config = { foo: 'bar' }; return process(file).then(() => { hexo.theme.config.should.eql({}); @@ -79,8 +83,11 @@ describe('config', () => { err.should.have.property('message', 'Theme config load failed.'); }); - return process(file).catch(errorCallback).finally(() => { - errorCallback.calledOnce.should.be.true; - }).catch(() => {}); // Catch again because it throws error + return process(file) + .catch(errorCallback) + .finally(() => { + errorCallback.calledOnce.should.be.true; + }) + .catch(() => {}); // Catch again because it throws error }); }); diff --git a/test/scripts/theme_processors/i18n.js b/test/scripts/theme_processors/i18n.js index 24859babd6..10b9699ec8 100644 --- a/test/scripts/theme_processors/i18n.js +++ b/test/scripts/theme_processors/i18n.js @@ -6,7 +6,9 @@ const Promise = require('bluebird'); describe('i18n', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'config_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'config_test'), { + silent: true + }); const processor = require('../../../lib/theme/processors/i18n'); const process = Promise.method(processor.process.bind(hexo)); const themeDir = pathFn.join(hexo.base_dir, 'themes', 'test'); @@ -24,10 +26,12 @@ describe('i18n', () => { return new hexo.theme.File(options); } - before(() => Promise.all([ - fs.mkdirs(themeDir), - fs.writeFile(hexo.config_path, 'theme: test') - ]).then(() => hexo.init())); + before(() => + Promise.all([ + fs.mkdirs(themeDir), + fs.writeFile(hexo.config_path, 'theme: test') + ]).then(() => hexo.init()) + ); after(() => fs.rmdir(hexo.base_dir)); @@ -40,23 +44,23 @@ describe('i18n', () => { }); it('type: create', () => { - const body = [ - 'ok: OK', - 'index:', - ' title: Home' - ].join('\n'); + const body = ['ok: OK', 'index:', ' title: Home'].join('\n'); const file = newFile({ path: 'en.yml', type: 'create' }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const __ = hexo.theme.i18n.__('en'); + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const __ = hexo.theme.i18n.__('en'); - __('ok').should.eql('OK'); - __('index.title').should.eql('Home'); - }).finally(() => fs.unlink(file.source)); + __('ok').should.eql('OK'); + __('index.title').should.eql('Home'); + }) + .finally(() => fs.unlink(file.source)); }); it('type: delete', () => { diff --git a/test/scripts/theme_processors/source.js b/test/scripts/theme_processors/source.js index b351d3d83a..2893f64b90 100644 --- a/test/scripts/theme_processors/source.js +++ b/test/scripts/theme_processors/source.js @@ -6,7 +6,9 @@ const Promise = require('bluebird'); describe('source', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'source_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'source_test'), { + silent: true + }); const processor = require('../../../lib/theme/processors/source'); const process = Promise.method(processor.process.bind(hexo)); const themeDir = pathFn.join(hexo.base_dir, 'themes', 'test'); @@ -15,24 +17,26 @@ describe('source', () => { function newFile(options) { const path = options.path; - options.params = {path}; + options.params = { path }; options.path = 'source/' + path; options.source = pathFn.join(themeDir, options.path); return new hexo.theme.File(options); } - before(() => Promise.all([ - fs.mkdirs(themeDir), - fs.writeFile(hexo.config_path, 'theme: test') - ]).then(() => hexo.init())); + before(() => + Promise.all([ + fs.mkdirs(themeDir), + fs.writeFile(hexo.config_path, 'theme: test') + ]).then(() => hexo.init()) + ); after(() => fs.rmdir(hexo.base_dir)); it('pattern', () => { const pattern = processor.pattern; - pattern.match('source/foo.jpg').should.eql({path: 'foo.jpg'}); + pattern.match('source/foo.jpg').should.eql({ path: 'foo.jpg' }); pattern.match('source/_foo.jpg').should.be.false; pattern.match('source/foo/_bar.jpg').should.be.false; pattern.match('source/foo.jpg~').should.be.false; @@ -51,15 +55,19 @@ describe('source', () => { const id = 'themes/test/' + file.path; - return fs.writeFile(file.source, 'test').then(() => process(file)).then(() => { - const asset = Asset.findById(id); + return fs + .writeFile(file.source, 'test') + .then(() => process(file)) + .then(() => { + const asset = Asset.findById(id); - asset._id.should.eql(id); - asset.path.should.eql(file.params.path); - asset.modified.should.be.true; + asset._id.should.eql(id); + asset.path.should.eql(file.params.path); + asset.modified.should.be.true; - return asset.remove(); - }).finally(() => fs.unlink(file.source)); + return asset.remove(); + }) + .finally(() => fs.unlink(file.source)); }); it('type: update', () => { @@ -77,14 +85,16 @@ describe('source', () => { path: file.params.path, modified: false }) - ]).then(() => process(file)).then(() => { - const asset = Asset.findById(id); - - asset.modified.should.be.true; - }).finally(() => Promise.all([ - fs.unlink(file.source), - Asset.removeById(id) - ])); + ]) + .then(() => process(file)) + .then(() => { + const asset = Asset.findById(id); + + asset.modified.should.be.true; + }) + .finally(() => + Promise.all([fs.unlink(file.source), Asset.removeById(id)]) + ); }); it('type: skip', () => { @@ -102,14 +112,16 @@ describe('source', () => { path: file.params.path, modified: false }) - ]).then(() => process(file)).then(() => { - const asset = Asset.findById(id); - - asset.modified.should.be.false; - }).finally(() => Promise.all([ - fs.unlink(file.source), - Asset.removeById(id) - ])); + ]) + .then(() => process(file)) + .then(() => { + const asset = Asset.findById(id); + + asset.modified.should.be.false; + }) + .finally(() => + Promise.all([fs.unlink(file.source), Asset.removeById(id)]) + ); }); it('type: delete', () => { @@ -123,8 +135,10 @@ describe('source', () => { return Asset.insert({ _id: id, path: file.params.path - }).then(() => process(file)).then(() => { - should.not.exist(Asset.findById(id)); - }); + }) + .then(() => process(file)) + .then(() => { + should.not.exist(Asset.findById(id)); + }); }); }); diff --git a/test/scripts/theme_processors/view.js b/test/scripts/theme_processors/view.js index 64224fc537..2099d06482 100644 --- a/test/scripts/theme_processors/view.js +++ b/test/scripts/theme_processors/view.js @@ -6,7 +6,7 @@ const Promise = require('bluebird'); describe('view', () => { const Hexo = require('../../../lib/hexo'); - const hexo = new Hexo(pathFn.join(__dirname, 'view_test'), {silent: true}); + const hexo = new Hexo(pathFn.join(__dirname, 'view_test'), { silent: true }); const processor = require('../../../lib/theme/processors/view'); const process = Promise.method(processor.process.bind(hexo)); const themeDir = pathFn.join(hexo.base_dir, 'themes', 'test'); @@ -16,17 +16,19 @@ describe('view', () => { function newFile(options) { const path = options.path; - options.params = {path}; + options.params = { path }; options.path = 'layout/' + path; options.source = pathFn.join(themeDir, options.path); return new hexo.theme.File(options); } - before(() => Promise.all([ - fs.mkdirs(themeDir), - fs.writeFile(hexo.config_path, 'theme: test') - ]).then(() => hexo.init())); + before(() => + Promise.all([ + fs.mkdirs(themeDir), + fs.writeFile(hexo.config_path, 'theme: test') + ]).then(() => hexo.init()) + ); after(() => fs.rmdir(hexo.base_dir)); @@ -39,30 +41,30 @@ describe('view', () => { }); it('type: create', () => { - const body = [ - 'foo: bar', - '---', - 'test' - ].join('\n'); + const body = ['foo: bar', '---', 'test'].join('\n'); const file = newFile({ path: 'index.swig', type: 'create' }); - return fs.writeFile(file.source, body).then(() => process(file)).then(() => { - const view = hexo.theme.getView('index.swig'); - - view.path.should.eql('index.swig'); - view.source.should.eql(pathFn.join(themeDir, 'layout', 'index.swig')); - view.data.should.eql({ - foo: 'bar', - _content: 'test' + return fs + .writeFile(file.source, body) + .then(() => process(file)) + .then(() => { + const view = hexo.theme.getView('index.swig'); + + view.path.should.eql('index.swig'); + view.source.should.eql(pathFn.join(themeDir, 'layout', 'index.swig')); + view.data.should.eql({ + foo: 'bar', + _content: 'test' + }); + }) + .finally(() => { + hexo.theme.removeView('index.swig'); + return fs.unlink(file.source); }); - }).finally(() => { - hexo.theme.removeView('index.swig'); - return fs.unlink(file.source); - }); }); it('type: delete', () => { diff --git a/test/util/stream.js b/test/util/stream.js index 930e4ccdc4..ca0624b6fd 100644 --- a/test/util/stream.js +++ b/test/util/stream.js @@ -6,11 +6,14 @@ function readStream(stream) { return new Promise((resolve, reject) => { let data = ''; - stream.on('data', chunk => { - data += chunk.toString(); - }).on('end', () => { - resolve(data); - }).on('error', reject); + stream + .on('data', chunk => { + data += chunk.toString(); + }) + .on('end', () => { + resolve(data); + }) + .on('error', reject); }); }123456 bold and italic
\n