ใช้ Gulp เพื่อเชื่อมต่อและ Uglify ไฟล์


124

ฉันกำลังพยายามใช้ Gulp เพื่อ:

  1. นำไฟล์จาวาสคริปต์ 3 ไฟล์มาต่อกันจากนั้นบันทึกผลลัพธ์ลงในไฟล์ (concat.js)
  2. ใช้ไฟล์ที่ต่อกันนี้และอัปเกรด / ย่อขนาดไฟล์จากนั้นบันทึกผลลัพธ์ลงในไฟล์อื่น (uglify.js)

ฉันมีรหัสต่อไปนี้แล้ว

    var gulp = require('gulp'),
        gp_concat = require('gulp-concat'),
        gp_uglify = require('gulp-uglify');

    gulp.task('js-fef', function(){
        return gulp.src(['file1.js', 'file2.js', 'file3.js'])
            .pipe(gp_concat('concat.js'))
            .pipe(gp_uglify())
            .pipe(gulp.dest('js'));
    });

    gulp.task('default', ['js-fef'], function(){});

อย่างไรก็ตามดูเหมือนว่าการดำเนินการ uglify จะไม่ทำงานหรือไฟล์ไม่ได้ถูกสร้างขึ้นด้วยเหตุผลบางประการ

ฉันต้องทำอย่างไรเพื่อให้สิ่งนี้เกิดขึ้น


3
ประหลาดใจที่ยังไม่เห็นดังนั้นฉันจึงอยากจะตั้งข้อสังเกตอย่างรวดเร็วว่าเป้าหมายในตัวมันค่อนข้างขัดกับปรัชญาของอึก การเขียนไฟล์ตัวกลางเป็นวิธีการทำงานที่หนักหน่วงกว่า Gulp ส่งเสริมสตรีมเพื่อปรับปรุงความเร็ว แต่ฉันแน่ใจว่าคนที่ถามมีเหตุผลของเขา :)
บาร์ต

ฉันรู้ว่ามันเป็นเธรดเก่า แต่ฉันได้สร้างโมดูล npm เพื่อทำงานประเภทนี้ได้อย่างง่ายดายโดยใช้ไฟล์ yaml ตรวจสอบว่า: github.com/Stnaire/gulp-yaml-packages
Stnaire

คำตอบ:


161

ปรากฎว่าฉันจำเป็นต้องใช้gulp-renameและส่งออกไฟล์ที่ต่อกันก่อน 'uglification' นี่คือรหัส:

var gulp = require('gulp'),
    gp_concat = require('gulp-concat'),
    gp_rename = require('gulp-rename'),
    gp_uglify = require('gulp-uglify');

gulp.task('js-fef', function(){
    return gulp.src(['file1.js', 'file2.js', 'file3.js'])
        .pipe(gp_concat('concat.js'))
        .pipe(gulp.dest('dist'))
        .pipe(gp_rename('uglify.js'))
        .pipe(gp_uglify())
        .pipe(gulp.dest('dist'));
});

gulp.task('default', ['js-fef'], function(){});

มาจากgruntตอนแรกสับสนเล็กน้อย แต่ตอนนี้มันสมเหตุสมผลแล้ว ฉันหวังว่ามันจะช่วยgulpnoobs ได้

และหากคุณต้องการซอร์สแมปนี่คือรหัสที่อัปเดต:

var gulp = require('gulp'),
    gp_concat = require('gulp-concat'),
    gp_rename = require('gulp-rename'),
    gp_uglify = require('gulp-uglify'),
    gp_sourcemaps = require('gulp-sourcemaps');

gulp.task('js-fef', function(){
    return gulp.src(['file1.js', 'file2.js', 'file3.js'])
        .pipe(gp_sourcemaps.init())
        .pipe(gp_concat('concat.js'))
        .pipe(gulp.dest('dist'))
        .pipe(gp_rename('uglify.js'))
        .pipe(gp_uglify())
        .pipe(gp_sourcemaps.write('./'))
        .pipe(gulp.dest('dist'));
});

gulp.task('default', ['js-fef'], function(){});

ดูgulp-sourcemapsสำหรับข้อมูลเพิ่มเติมเกี่ยวกับตัวเลือกและการกำหนดค่า


FYI คุณไม่มีเครื่องหมายคำพูดเดียวก่อน concat.js บรรทัดหลังคำสั่งคืนสินค้าของคุณgulp.taskควรเป็น:.pipe(gp_concat('concat.js'))
Eric Jorgensen

1
ไฟล์ทั้งหมดถูกสร้างขึ้นอย่างไรก็ตามในดีบักเกอร์ฉันยังคงเห็นเวอร์ชันที่ย่อขนาด อะไรคือเหตุผล? ไฟล์แผนที่ตั้งชื่ออย่างถูกต้องและสามารถเข้าถึงได้ด้วย URL
Meglio

จะขึ้นอยู่กับเบราว์เซอร์แหล่งที่มาดั้งเดิมอยู่ในแท็บอื่น คุณต้องวางเบรกพอยต์ไว้ที่นั่น
przemcio

4
ยังไม่ชัดเจนสำหรับฉันว่าทำไมเราต้องเปลี่ยนชื่อ? เป็นบั๊กหรือ?
przemcio

@przemcio ในกรณีของฉันฉันต้องการบันทึกไฟล์ทั้งหมดในแต่ละขั้นตอนในกระบวนการ อย่างไรก็ตามหากสิ่งที่คุณสนใจคือไฟล์ที่ย่อขนาดสุดท้ายคุณสามารถย่อไฟล์อึกให้สั้นลงได้อีกแน่นอน
Obinwanne Hill

17

ไฟล์ gulp ของฉันสร้างบันเดิล -min.js ที่คอมไพล์ขั้นสุดท้ายหวังว่านี่จะช่วยใครบางคนได้

ใส่คำอธิบายภาพที่นี่

//Gulpfile.js

var gulp = require("gulp");
var watch = require("gulp-watch");

var concat = require("gulp-concat");
var rename = require("gulp-rename");
var uglify = require("gulp-uglify");
var del = require("del");
var minifyCSS = require("gulp-minify-css");
var copy = require("gulp-copy");
var bower = require("gulp-bower");
var sourcemaps = require("gulp-sourcemaps");

var path = {
    src: "bower_components/",
    lib: "lib/"
}

var config = {
    jquerysrc: [
        path.src + "jquery/dist/jquery.js",
        path.src + "jquery-validation/dist/jquery.validate.js",
        path.src + "jquery-validation/dist/jquery.validate.unobtrusive.js"
    ],
    jquerybundle: path.lib + "jquery-bundle.js",
    ngsrc: [
        path.src + "angular/angular.js",
         path.src + "angular-route/angular-route.js",
         path.src + "angular-resource/angular-resource.js"
    ],
    ngbundle: path.lib + "ng-bundle.js",

    //JavaScript files that will be combined into a Bootstrap bundle
    bootstrapsrc: [
        path.src + "bootstrap/dist/js/bootstrap.js"
    ],
    bootstrapbundle: path.lib + "bootstrap-bundle.js"
}

// Synchronously delete the output script file(s)
gulp.task("clean-scripts", function (cb) {
    del(["lib","dist"], cb);
});

//Create a jquery bundled file
gulp.task("jquery-bundle", ["clean-scripts", "bower-restore"], function () {
    return gulp.src(config.jquerysrc)
     .pipe(concat("jquery-bundle.js"))
     .pipe(gulp.dest("lib"));
});

//Create a angular bundled file
gulp.task("ng-bundle", ["clean-scripts", "bower-restore"], function () {
    return gulp.src(config.ngsrc)
     .pipe(concat("ng-bundle.js"))
     .pipe(gulp.dest("lib"));
});

//Create a bootstrap bundled file
gulp.task("bootstrap-bundle", ["clean-scripts", "bower-restore"], function     () {
    return gulp.src(config.bootstrapsrc)
     .pipe(concat("bootstrap-bundle.js"))
     .pipe(gulp.dest("lib"));
});


// Combine and the vendor files from bower into bundles (output to the Scripts folder)
gulp.task("bundle-scripts", ["jquery-bundle", "ng-bundle", "bootstrap-bundle"], function () {

});

//Restore all bower packages
gulp.task("bower-restore", function () {
    return bower();
});

//build lib scripts
gulp.task("compile-lib", ["bundle-scripts"], function () {
    return gulp.src("lib/*.js")
        .pipe(sourcemaps.init())
        .pipe(concat("compiled-bundle.js"))
        .pipe(gulp.dest("dist"))
        .pipe(rename("compiled-bundle.min.js"))
        .pipe(uglify())
        .pipe(sourcemaps.write("./"))
        .pipe(gulp.dest("dist"));
});

1
ตัวอย่างที่ดี @wchoward มันเป็นเพียงสิ่งที่ฉันกำลังมองหาการออกแบบที่ตรงไปตรงมาสะอาด
Faito

10

วิธีการแก้ปัญหาโดยใช้gulp-uglify, และgulp-concat gulp-sourcemapsนี่มาจากโครงการที่ฉันกำลังทำอยู่

gulp.task('scripts', function () {
    return gulp.src(scripts, {base: '.'})
        .pipe(plumber(plumberOptions))
        .pipe(sourcemaps.init({
            loadMaps: false,
            debug: debug,
        }))
        .pipe(gulpif(debug, wrapper({
            header: fileHeader,
        })))
        .pipe(concat('all_the_things.js', {
            newLine:'\n;' // the newline is needed in case the file ends with a line comment, the semi-colon is needed if the last statement wasn't terminated
        }))
        .pipe(uglify({
            output: { // http://lisperator.net/uglifyjs/codegen
                beautify: debug,
                comments: debug ? true : /^!|\b(copyright|license)\b|@(preserve|license|cc_on)\b/i,
            },
            compress: { // http://lisperator.net/uglifyjs/compress, http://davidwalsh.name/compress-uglify
                sequences: !debug,
                booleans: !debug,
                conditionals: !debug,
                hoist_funs: false,
                hoist_vars: debug,
                warnings: debug,
            },
            mangle: !debug,
            outSourceMap: true,
            basePath: 'www',
            sourceRoot: '/'
        }))
        .pipe(sourcemaps.write('.', {
            includeContent: true,
            sourceRoot: '/',
        }))
        .pipe(plumber.stop())
        .pipe(gulp.dest('www/js'))
});

สิ่งนี้จะรวมและบีบอัดทั้งหมดของคุณscriptsทำให้เป็นไฟล์ที่เรียกว่าall_the_things.js. ไฟล์จะลงท้ายด้วยบรรทัดพิเศษ

//# sourceMappingURL=all_the_things.js.map

ซึ่งจะบอกให้เบราว์เซอร์ของคุณมองหาไฟล์แผนที่นั้นซึ่งจะเขียนออกมาด้วย


7
var gulp = require('gulp');
var concat = require('gulp-concat');
var uglify = require('gulp-uglify');

gulp.task('create-vendor', function () {
var files = [
    'bower_components/q/q.js',
    'bower_components/moment/min/moment-with-locales.min.js',
    'node_modules/jstorage/jstorage.min.js'
];

return gulp.src(files)
    .pipe(concat('vendor.js'))
    .pipe(gulp.dest('scripts'))
    .pipe(uglify())
    .pipe(gulp.dest('scripts'));
});

วิธีแก้ปัญหาของคุณไม่ได้ผลเนื่องจากคุณต้องบันทึกไฟล์หลังจากกระบวนการ concat แล้วอัปลักษณ์และบันทึกอีกครั้ง คุณไม่จำเป็นต้องเปลี่ยนชื่อไฟล์ระหว่าง concat และ uglify


ฉันจะบอกว่ามันเป็นสิทธิพิเศษของนักพัฒนาในการตัดสินใจว่าพวกเขาทำอะไรและไม่จำเป็นต้องใช้เมื่อใช้อึก ในกรณีของฉันฉันต้องการเปลี่ยนชื่อไฟล์ในแต่ละขั้นตอน คนอื่นอาจชอบเป็นอย่างอื่น
Obinwanne Hill

1
แน่นอนคุณสามารถตัดสินใจได้ว่าอะไรคือตัวเลือกที่ดีที่สุดสำหรับคุณ ฉันเข้าใจว่าคำตอบด้านล่างบอกว่าคุณต้องเปลี่ยนชื่อไฟล์ฉันแค่บอกว่าคุณไม่จำเป็นต้องใช้ (ไม่บังคับ) ขอโทษถ้าฉันทำให้สับสน
Milos

4

10 มิถุนายน 2558:หมายเหตุจากผู้เขียนgulp-uglifyjs:

เลิกใช้แล้ว:ปลั๊กอินนี้ถูกขึ้นบัญชีดำเนื่องจากต้องอาศัย Uglify เพื่อต่อไฟล์แทนการใช้ gulp-concat ซึ่งจะทำลายกระบวนทัศน์ "ควรทำสิ่งเดียว" เมื่อฉันสร้างปลั๊กอินนี้ไม่มีวิธีใดที่จะรับแผนที่แหล่งที่มาเพื่อทำงานกับอึกอย่างไรก็ตามตอนนี้มีปลั๊กอิน gulp-sourcemaps ที่บรรลุเป้าหมายเดียวกัน gulp-uglifyjs ยังคงใช้งานได้ดีและให้การควบคุมที่ละเอียดมากในการดำเนินการ Uglify ฉันแค่แจ้งให้คุณทราบว่ามีตัวเลือกอื่น ๆ อยู่ในขณะนี้


18 กุมภาพันธ์ 2558: gulp-uglifyและgulp-concatทั้งสองก็ทำงานได้ดีกับgulp-sourcemapsตอนนี้ ตรวจสอบให้แน่ใจว่าได้ตั้งค่าnewLineตัวเลือกอย่างถูกต้องสำหรับgulp-concat; ฉันแนะนำ\n;.


คำตอบเดิม (ธันวาคม 2014):ใช้gulp-uglifyjsแทน gulp-concatไม่จำเป็นต้องปลอดภัย จำเป็นต้องจัดการเซมิโคลอนต่อท้ายอย่างถูกต้อง gulp-uglifyยังไม่รองรับแผนที่ต้นทาง นี่คือตัวอย่างจากโครงการที่ฉันกำลังดำเนินการ:

gulp.task('scripts', function () {
    gulp.src(scripts)
        .pipe(plumber())
        .pipe(uglify('all_the_things.js',{
            output: {
                beautify: false
            },
            outSourceMap: true,
            basePath: 'www',
            sourceRoot: '/'
        }))
        .pipe(plumber.stop())
        .pipe(gulp.dest('www/js'))
});

ฮะ? gulp-uglify รองรับแผนที่แหล่งที่มาอย่างแน่นอน: github.com/floridoo/gulp-sourcemaps/wiki/…
มิสเตอร์โอ

1
@MisterOh ไม่แน่ใจว่ามันทำในขณะที่เขียนหรือถ้าเป็นเช่นนั้นอาจจะgulp-concatไม่ได้ ( gulp-uglifyจะไม่อนุญาตให้คุณย่อขนาดไฟล์หลายไฟล์ดังนั้นคุณต้องเชื่อมต่อกันก่อน) นอกจากนี้ให้gulp-concatใช้\r\nโดยค่าเริ่มต้นซึ่งอาจทำให้เกิดปัญหาหากไฟล์ JS ของคุณไม่ยุติอย่างถูกต้อง แต่ใช่ตอนนี้มีการสนับสนุนแล้วการไปเส้นทางนั้นน่าจะดีกว่าเพราะมีความยืดหยุ่นมากขึ้น
mpen

@Mark - จะขอบคุณมากถ้าคุณจะโพสต์วิธีแก้ปัญหาด้วย gulp-sourcemaps ที่ทำงานร่วมกับคำตอบของ Obinwanne ดูเหมือนจะไม่สามารถใช้งานได้
NightOwl888

@ NightOwl888 โอเคที่จริงมันไม่ได้สร้างแหล่งที่มาแบบอินไลน์หากนั่นคือสิ่งที่คุณถาม มันยังคงเป็นไฟล์แยกต่างหาก
mpen

ตอนนี้ gulp-uglifyjs แค่ใช้ปลั๊กอิน gulp-uglify ก็น่าจะเพียงพอแล้ว ดูคำตอบอื่น ๆ สำหรับโซลูชันที่ทันสมัย
Neil Monroe

0

เรากำลังใช้การกำหนดค่าด้านล่างเพื่อทำสิ่งที่คล้ายกัน

    var gulp = require('gulp'),
    async = require("async"),
    less = require('gulp-less'),
    minifyCSS = require('gulp-minify-css'),
    uglify = require('gulp-uglify'),
    concat = require('gulp-concat'),
    gulpDS = require("./gulpDS"),
    del = require('del');

// CSS & Less
var jsarr = [gulpDS.jsbundle.mobile, gulpDS.jsbundle.desktop, gulpDS.jsbundle.common];
var cssarr = [gulpDS.cssbundle];

var generateJS = function() {

    jsarr.forEach(function(gulpDSObject) {
        async.map(Object.keys(gulpDSObject), function(key) {
            var val = gulpDSObject[key]
            execGulp(val, key);
        });

    })
}

var generateCSS = function() {
    cssarr.forEach(function(gulpDSObject) {
        async.map(Object.keys(gulpDSObject), function(key) {
            var val = gulpDSObject[key];
            execCSSGulp(val, key);
        })
    })
}

var execGulp = function(arrayOfItems, dest) {
    var destSplit = dest.split("/");
    var file = destSplit.pop();
    del.sync([dest])
    gulp.src(arrayOfItems)
        .pipe(concat(file))
        .pipe(uglify())
        .pipe(gulp.dest(destSplit.join("/")));
}

var execCSSGulp = function(arrayOfItems, dest) {
    var destSplit = dest.split("/");
    var file = destSplit.pop();
    del.sync([dest])
    gulp.src(arrayOfItems)
        .pipe(less())
        .pipe(concat(file))
        .pipe(minifyCSS())
        .pipe(gulp.dest(destSplit.join("/")));
}

gulp.task('css', generateCSS);
gulp.task('js', generateJS);

gulp.task('default', ['css', 'js']);

ไฟล์ GulpDS ตัวอย่างอยู่ด้านล่าง:

{

    jsbundle: {
        "mobile": {
            "public/javascripts/sample.min.js": ["public/javascripts/a.js", "public/javascripts/mobile/b.js"]
           },
        "desktop": {
            'public/javascripts/sample1.js': ["public/javascripts/c.js", "public/javascripts/d.js"]},
        "common": {
            'public/javascripts/responsive/sample2.js': ['public/javascripts/n.js']
           }
    },
    cssbundle: {
        "public/stylesheets/a.css": "public/stylesheets/less/a.less",
        }
}
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.