简易Express资源合并中间件http-concat打赏

相信很多前端童鞋都见过一些网站有如下url输出js或者css

http://example.com/??script1.js,script2.js,build/script.js

http://example.com/??script1.js,script2.js,build/script.js?v=2016

http://example.com/??style1.css,style2.css,build/style.css

http://example.com/??style1.css,style2.css,build/style.css?v=2016

在以前,使用YUI、DOJO等企业前端库的时候,往往会用到类似功能,最近使用express,搜了下似乎没有类似中间件,索性自己写一个,参数形式参考了阿里的nginx-http-concat(似乎目前大部分有此类功能的网站都是采用阿里的nginx模块实现)。代码如下:

var fs = require('fs');
var path = require('path');

var MIME = {
    '.css': 'text/css;charset=utf-8',
    '.js': 'application/javascript;charset=utf-8'
};

var httpConcat = function (options) {

    options = options || {};

    var opts = {
        //file base path
        base: options.base || '/public',
        //url path
        path: options.path || '/',
        //separator for url path & file path
        separator: options.separator || '??',
        //separator for file path
        fileSeparator: options.fileSeparator || ',',
        //setHeaders callback
        setHeaders: options.setHeaders
    };

    return function httpConcat(req, res, next) {
        if (req.url.indexOf(opts.path) === 0) {
            var patten = req.url.split(opts.separator);
            if (patten.length < 2) {
                next();
            } else {
                var pathArrayStr = patten[1].split('?')[0],
                    pathArray = validPath(opts.base, pathArrayStr ? pathArrayStr.split(opts.fileSeparator) : []);
                if (pathArray.length) {
                    res.setHeader('Content-Type', parseMIME(pathArray[0]));
                    if (opts.setHeaders) opts.setHeaders(res);
                    outputFiles(pathArray, res);
                } else {
                    res.status(404);
                    next();
                }
            }
        } else {
            next();
        }
    };
};

module.exports = httpConcat;

function parseMIME(filename) {
    return MIME[path.extname(filename)] || 'text/plain;charset=utf-8';
}

function validPath(base, pathArray) {
    var validPathArray = [], tmpPath;
    for (var i = 0; i < pathArray.length; i++) {
        tmpPath = base + '/' + pathArray[i];
        if (fs.existsSync(tmpPath))
            validPathArray.push(tmpPath);
    }
    return validPathArray;
}

function outputFiles(pathArray, writer) {
    (function next(i, len) {
        if (i < len) {
            var reader = fs.createReadStream(pathArray[i], {encoding: 'utf-8'});
            reader.pipe(writer, {end: false});
            reader.on('end', function () {
                next(i + 1, len);
            });
        } else {
            writer.end();
        }
    }(0, pathArray.length));
}

安装

npm i http-concat --save

使用

var app = express();

app.use(httpConcat({

base: path.join(__dirname, 'public', 'static'),

path: '/'

}));

github地址:https://github.com/weizs/http-concat

npm地址:https://www.npmjs.com/package/http-concat

简易Express资源合并中间件http-concat
文章《简易Express资源合并中间件http-concat》二维码
  • 微信打赏
  • 支付宝打赏

已有13条评论

  1. 跨境电商是什么

    非常不错~~~~~

    2016-10-12 11:36 回复
  2. 飞利浦呼吸机

    对于小白来说,真的看不懂

    2016-10-08 09:18 回复
  3. 连衣裙

    看不懂!崇拜高手!

    2016-09-22 22:12 回复
  4. 工控资料窝

    非常实用的分享,不错哦

    2016-09-19 11:09 回复
  5. 浙江经济理事会

    看不懂,纯支持!

    2016-09-18 09:42 回复
  6. 外贸电商培训

    大力顶起。。。。

    2016-09-16 09:34 回复
  7. 博客大全网

    感谢分享

    2016-09-16 09:08 回复
  8. 卢松松博客

    感谢分享,祝博主中秋节快乐

    2016-09-15 13:50 回复
  9. 微商

    按文章里 描述的去 编写 就可以了

    2016-09-14 15:07 回复
  10. 短线炒股技巧

    新手,准备着手这个。。。

    2016-09-04 05:48 回复
  11. 刘明野博客

    写的很好,感谢分享

    2016-09-03 19:48 回复
  12. 卡卡

    哥们 找工作吗 我们是一家互联网公司做自研产品哦 有兴趣加我扣扣1452519241

    2016-08-31 18:38 回复

(必填)

(必填)

(可选)