Verwenden von Gulp zum Verketten und Uglifizieren von Dateien

124

Ich versuche Gulp zu verwenden, um:

  1. Nehmen Sie 3 bestimmte Javascript-Dateien, verketten Sie sie und speichern Sie das Ergebnis in einer Datei (concat.js).
  2. Nehmen Sie diese verkettete Datei, uglifizieren / minimieren Sie sie und speichern Sie das Ergebnis in einer anderen Datei (uglify.js).

Ich habe bisher den folgenden Code

    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(){});

Die uglify-Operation scheint jedoch nicht zu funktionieren, oder die Datei wird aus irgendeinem Grund nicht generiert.

Was muss ich tun, um dies zu erreichen?

Obinwanne Hill
quelle
3
Erstaunt, dass ich es noch nicht gesehen habe, möchte ich nur schnell bemerken, dass das Ziel an sich etwas gegen die Philosophie von Gulp verstößt. Das Schreiben von Zwischendateien ist eher die Arbeitsweise von Grunt. Gulp fördert Streams, um die Geschwindigkeit zu verbessern. Aber ich bin sicher, der fragende Typ hatte seine Gründe :).
Bart
Ich weiß, dass es ein alter Thread ist, aber ich habe ein npm-Modul erstellt, um diese Art von Arbeit sehr einfach mit einer yaml-Datei zu erledigen. Probieren Sie es aus: github.com/Stnaire/gulp-yaml-packages .
Stnaire

Antworten:

161

Es stellte sich heraus, dass ich gulp-renamedie verkettete Datei zuerst verwenden und auch ausgeben musste, bevor ich sie hässlich machte. Hier ist der Code:

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(){});

Von gruntes war ein wenig verwirrend auf den ersten , aber es macht jetzt Sinn. Ich hoffe es hilft den gulpNoobs.

Und wenn Sie Sourcemaps benötigen, finden Sie hier den aktualisierten Code:

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(){});

Weitere Informationen zu Optionen und Konfiguration finden Sie unter gulp-sourcemaps .

Obinwanne Hill
quelle
Zu Ihrer Information, vor concat.js fehlt ein einfaches Anführungszeichen. Die Zeile nach Ihrer Rückgabeerklärung gulp.tasksollte lauten:.pipe(gp_concat('concat.js'))
Eric Jorgensen
1
Alle Dateien werden generiert, im Debugger wird jedoch weiterhin die minimierte Version angezeigt. Was kann der Grund sein? Die Kartendatei hat den richtigen Namen und kann über ihre URL aufgerufen werden.
Meglio
Abhängig von den Browsern befinden sich die Originalquellen auf verschiedenen Registerkarten. Sie müssen dort einen Haltepunkt setzen.
Przemcio
4
Mir ist nicht klar, warum wir umbenennen müssen? Ist es ein Fehler oder?
Przemcio
@przemcio In meinem Fall wollte ich bei jedem Schritt des Prozesses eine Aufzeichnung aller Dateien. Wenn Sie sich jedoch nur um die endgültige minimierte Datei kümmern, können Sie die Schluckdatei natürlich noch weiter verkürzen
Obinwanne Hill,
17

Meine gulp-Datei erzeugt eine endgültige compiled-bundle-min.js, hoffe, dies hilft jemandem.

Geben Sie hier die Bildbeschreibung ein

//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"));
});
dynamiclynk
quelle
1
Tolles Beispiel @wchoward es war genau das, wonach ich gesucht habe, sehr sauberes, unkompliziertes Design.
Faito
10

- Lösung gulp-uglify, gulp-concatund gulp-sourcemaps. Dies ist aus einem Projekt, an dem ich arbeite.

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'))
});

Dies kombiniert und komprimiert alle Ihre scripts, fügt sie in eine Datei namens all_the_things.js. Die Datei endet mit einer speziellen Zeile

//# sourceMappingURL=all_the_things.js.map

Dadurch wird Ihr Browser angewiesen, nach dieser Kartendatei zu suchen, die er auch ausgibt.

mpen
quelle
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'));
});

Ihre Lösung funktioniert nicht, da Sie die Datei nach dem Concat-Prozess speichern und dann hässlich machen und erneut speichern müssen. Sie müssen die Datei nicht zwischen concat und uglify umbenennen.

Milos
quelle
Ich würde sagen, es ist das Vorrecht des Entwicklers, zu entscheiden, was er bei der Verwendung von gulp tut und was nicht. In meinem Fall wollte ich die Dateien bei jedem Schritt umbenennen. Andere mögen es anders bevorzugen.
Obinwanne Hill
1
Natürlich können Sie entscheiden, was für Sie die beste Option ist. Ich habe verstanden, dass die Antwort unten besagt, dass Sie die Datei umbenennen müssen. Ich habe nur gesagt, dass Sie sie nicht benötigen (es ist nicht obligatorisch). Tut mir leid, wenn ich etwas Verwirrung stiftete.
Milos
4

10. Juni 2015: Anmerkung des Autors von gulp-uglifyjs:

DEPRECATED: Dieses Plugin wurde auf die schwarze Liste gesetzt, da es sich auf Uglify stützt, um die Dateien zu konkatieren, anstatt gulp-concat zu verwenden, was das Paradigma "Es sollte eins tun" bricht. Als ich dieses Plugin erstellt habe, gab es keine Möglichkeit, Quellkarten mit gulp zum Laufen zu bringen. Jetzt gibt es jedoch ein gulp-sourcemaps-Plugin, das das gleiche Ziel erreicht. gulp-uglifyjs funktioniert immer noch hervorragend und bietet eine sehr detaillierte Kontrolle über die Uglify-Ausführung. Ich möchte Ihnen nur mitteilen, dass es jetzt andere Optionen gibt.


18. Februar 2015: gulp-uglify und gulp-concatbeide arbeiten gulp-sourcemapsjetzt gut mit . Stellen Sie einfach sicher, dass die newLineOption richtig eingestellt ist gulp-concat. Ich empfehle \n;.


Ursprüngliche Antwort (Dezember 2014): Verwenden Sie stattdessen gulp-uglifyjs . gulp-concatist nicht unbedingt sicher; Es muss mit nachfolgenden Semikolons korrekt umgehen. gulp-uglifyunterstützt auch keine Quellkarten. Hier ist ein Ausschnitt aus einem Projekt, an dem ich arbeite:

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'))
});
mpen
quelle
Huh? gulp-uglify unterstützt definitiv Quellkarten: github.com/floridoo/gulp-sourcemaps/wiki/…
Mister Oh
1
@MisterOh Ich bin mir nicht sicher, ob dies zum Zeitpunkt des Schreibens der Fall war oder ob dies der Fall war gulp-concat( vielleicht können gulp-uglifySie nicht mehrere Dateien minimieren, sodass Sie sich zuerst konzentrieren müssen). Außerdem gulp-concatverwendet eine \r\nstandardmäßig, das könnte Probleme verursachen , wenn Ihre JS - Dateien nicht ordnungsgemäß beenden. Aber ja, jetzt, wo es Unterstützung gibt, ist es wahrscheinlich besser, diesen Weg zu gehen, da er flexibler ist.
Mpen
@Mark - Würde mich freuen, wenn Sie die Lösung mit Gulp-Sourcemaps veröffentlichen würden, die mit Obinwannes Antwort übereinstimmen. Ich kann es scheinbar nicht zum Laufen bringen.
NightOwl888
@ NightOwl888 okay Eigentlich erzeugt das keine Inline-Sourcemaps, wenn Sie danach gefragt haben. Es ist immer noch eine separate Datei.
Mpen
gulp-uglifyjs wird jetzt auch depecated. Nur das gulp-uglify-Plugin zu verwenden, sollte jetzt ausreichen. Weitere Antworten finden Sie in anderen Antworten.
Neil Monroe
0

Wir verwenden die folgende Konfiguration, um etwas Ähnliches zu tun

    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']);

Beispiel GulpDS-Datei ist unten:

{

    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",
        }
}
Dinesh
quelle