From e21f8aec4f048a47ccf7a1e5323786e4d5ef7a51 Mon Sep 17 00:00:00 2001 From: ikeq <9206414+ikeq@users.noreply.github.com> Date: Wed, 6 Nov 2019 19:15:44 +0800 Subject: [PATCH] fix: theme.assets work with post_asset_folder (#170) --- .travis.yml | 13 +++--- lib/filter/post.js | 38 +++++++++++------- package.json | 2 +- test/scripts/filters/post.js | 76 +++++++++++++++++++++++++++++++++--- 4 files changed, 99 insertions(+), 30 deletions(-) diff --git a/.travis.yml b/.travis.yml index 2c261c9..27e5419 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,19 +1,16 @@ language: node_js -node_js: - - "10" cache: - directories: - - node_modules + npm: true -branches: - only: - - master +node_js: + - "10" -before_install: +script: - git clone https://github.com/hexojs/hexo-theme-unit-test generate_test - git clone https://github.com/ikeq/hexo-theme-inside.git generate_test/themes/landscape - cd generate_test - npm install - hexo g & hexo g - cd .. + - npm test diff --git a/lib/filter/post.js b/lib/filter/post.js index 8764cae..7fc6e66 100644 --- a/lib/filter/post.js +++ b/lib/filter/post.js @@ -1,13 +1,13 @@ const cheerio = require('cheerio'); const { date } = require('hexo/lib/plugins/helper/date'); +const { snippet, parseToc, isObject, isEmptyObject, localeId, pick, trimHtml } = require('../utils'); const bounded = '
'; const table = '
'; -const { snippet, parseToc, isObject, isEmptyObject, localeId, pick, trimHtml } = require('../utils'); const date_formats = [ 'll', // Sep 4, 1986 'L', // 09/04/1986 'MM-DD' // 06-17 -] +]; // cache let hasComments, hasReward, hasToc, copyright, dateHelper, uriReplacer; @@ -29,17 +29,23 @@ module.exports = function (data) { copyright = theme.copyright; if (dateHelper === undefined) dateHelper = date.bind({ page: { lang: localeId(config.language, true) }, config }) - if (uriReplacer === undefined) - uriReplacer = theme.assets ? - (() => { - const { prefix, suffix } = theme.assets; - return s => /^(\/\/|http|data\:image)/.test(s) ? - s : - s.replace(/^\/*(.*[^\/])\/*$/, prefix + '/$1' + suffix) - })() : - config.post_asset_folder ? - (s, p) => /\//.test(s) ? s : `/${p}/${s}` : - s => s; + if (uriReplacer === undefined) { + uriReplacer = (() => { + let assetsFn = src => src; + if (theme.assets) { + const prefix = theme.assets.prefix ? theme.assets.prefix + '/' : '' + const suffix = theme.assets.suffix || '' + assetsFn = src => prefix + `${src}${suffix}`.replace(/\/{2,}/g, '/') + } + + return (src, assetPath) => { + assetPath = assetPath ? assetPath + '/' : '' + + // skip both external and absolute path + return /^(\/\/?|http|data\:image)/.test(src) ? src : assetsFn(`${assetPath}${src}`); + } + })(); + } // pre format date for i18n data.date_formatted = date_formats.reduce((ret, format) => { @@ -57,8 +63,10 @@ module.exports = function (data) { // comments data.comments = hasComments && data.comments !== false; - // asset path - const assetPath = isPage ? trimHtml(data.path, true) : data.link; + // asset path (for post_asset_folder) + const assetPath = config.post_asset_folder + ? (isPage ? trimHtml(data.path, true) : data.link) + : undefined; // Make sure articles without titles are also accessible if (!data.title) data.title = data.slug diff --git a/package.json b/package.json index 307656f..708134d 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "hexo-theme-inside", - "version": "2.5.0", + "version": "2.5.1", "description": "❤️ SPA, flat and clean theme for Hexo.", "scripts": { "test": "jasmine --config=test/jasmine.json" diff --git a/test/scripts/filters/post.js b/test/scripts/filters/post.js index 36ddede..d5115fd 100644 --- a/test/scripts/filters/post.js +++ b/test/scripts/filters/post.js @@ -1,7 +1,13 @@ 'use strict'; describe('post', function () { - const post = require('../../../lib/filter/post'); + const filterPath = require.resolve('../../../lib/filter/post'); + const post = { + call(ctx, arg) { + delete require.cache[filterPath] + return require(filterPath).call(ctx, arg) + } + } beforeEach(function () { this.ctx = { @@ -170,19 +176,77 @@ describe('post', function () { source: 'test/index.md', content: '', }; + const { ctx } = this; - post.call(this.ctx, data); + post.call(ctx, data); expect(data.thumbnail).toBe('https://sample.com/img/sample.jpg?q=80') - expect(data.content).toBe('') + expect(data.content).toBe(''); + + // suffix only + data.thumbnail = 'img/sample.jpg' + data.content = '' + ctx.theme.config.assets = { suffix: '?q=80' } + post.call(ctx, data); + expect(data.thumbnail).toBe('img/sample.jpg?q=80') + expect(data.content).toBe(''); + + // prefix only + data.thumbnail = 'img/sample.jpg' + data.content = '' + ctx.theme.config.assets = { prefix: 'https://sample.com' } + post.call(ctx, data); + expect(data.thumbnail).toBe('https://sample.com/img/sample.jpg') + expect(data.content).toBe(''); data.layout = 'page' - post.call(this.ctx, data); - data.thumbnail = 'img/sample.jpg'; - post.call(this.ctx, data); + post.call(ctx, data); expect(data.thumbnail).toBe('img/sample.jpg') }); + it('post_asset_folder', function () { + const data = { + layout: 'post', + thumbnail: 'sample.jpg', + excerpt: '', + source: 'test/index.md', + content: '', + path: 'post/test' + }; + const { ctx } = this; + + // post_asset_folder off, theme.assets off + delete ctx.theme.config.assets + post.call(ctx, data) + expect(data.thumbnail).toBe('sample.jpg') + expect(data.content).toBe('') + + // post_asset_folder on, theme.assets off + data.thumbnail = 'sample.jpg' + data.content = '' + ctx.config.post_asset_folder = true + post.call(ctx, data) + expect(data.thumbnail).toBe('post/test/sample.jpg') + expect(data.content).toBe('') + + // post_asset_folder off, theme.assets on + data.thumbnail = 'img/sample.jpg' + data.content = '' + ctx.config.post_asset_folder = false + ctx.theme.config.assets = { prefix: 'https://sample.com', suffix: '?q=80' } + post.call(ctx, data) + expect(data.thumbnail).toBe('https://sample.com/img/sample.jpg?q=80') + expect(data.content).toBe('') + + // post_asset_folder on, theme.assets on + data.thumbnail = 'img/sample.jpg' + data.content = '' + ctx.config.post_asset_folder = true + post.call(ctx, data) + expect(data.thumbnail).toBe('https://sample.com/post/test/img/sample.jpg?q=80') + expect(data.content).toBe('') + }) + it('escape with data:image', function () { const data = { layout: 'post',