<file_sep>import gulp from 'gulp';
import gulpLoadPlugins from 'gulp-load-plugins';
import browserSync from 'browser-sync';
import del from 'del';
import browserify from 'browserify';
import debowerify from 'debowerify';
import source from 'vinyl-source-stream';
import mergeStream from 'merge-stream';
import { stream as wiredep } from 'wiredep';

const $ = gulpLoadPlugins();
const reload = browserSync.reload;

var Config = {
    path: {
        'assets': 'app/assets',
        'build': 'web/assets'
    },
    scripts: ['app.js'],
    reload: {
        'proxy': 'local.dev/app_dev.php',
        'port': 3000
    }
};

// Styles
gulp.task('styles', ['wiredep'], () => {
    return gulp.src(Config.path.assets + '/styles/*.scss')
        .pipe($.plumber({
            errorHandler: $.notify.onError('Error: <%= error.message %>')
        }))
        .pipe($.sourcemaps.init())
        .pipe($.sass.sync({
            outputStyle: 'expanded',
            precision: 10,
            includePaths: ['.']
        }))
        .pipe($.autoprefixer({
            browsers: ['> 1%', 'last 2 versions', 'Firefox ESR']
        }))
        .pipe($.sourcemaps.write())
        .pipe(gulp.dest(Config.path.build + '/css'))
        .pipe(reload({
            stream: true
        }));
});

// Scripts
gulp.task('scripts', () => {
    var merged = mergeStream();
    var scripts = Config.scripts;
    scripts.forEach(function(file) {
        merged.add(browserify(Config.path.assets + '/scripts/' + file)
            .transform(debowerify)
            .bundle()
            .on('error', $.notify.onError(function(error) {
                return error.message;
            }))
            .pipe(source(file))
            .pipe(gulp.dest(Config.path.build + '/js')));
    });
    return merged;
});

// Lint
function lint(files, options) {
    return () => {
        return gulp.src(files)
            .pipe(reload({
                stream: true,
                once: true
            }))
            .pipe($.eslint(options))
            .pipe($.eslint.format())
            .pipe($.if(!browserSync.active, $.eslint.failAfterError()))
            .on('error', $.notify.onError(function(error) {
                return 'Linting: ' + error.message;
            }));
    };
}
gulp.task('lint', lint(Config.path.assets + '/scripts/**/*.js'));

// Assets
gulp.task('assets', ['styles', 'scripts'], () => {
    return gulp.src([
            Config.path.build + '/js/**/*.js',
            Config.path.build + '/css/**/*.css'
        ], {
            base: Config.path.build
        })
        .pipe($.if('*.js', $.uglify()))
        .pipe($.if('*.css', $.cssnano()))
        .pipe(gulp.dest(Config.path.build));
});

// Images
gulp.task('images', () => {
    return gulp.src(Config.path.assets + '/images/**/*')
        .pipe($.cache($.imagemin({
            progressive: true,
            interlaced: true,
            // don't remove IDs from SVGs, they are often used
            // as hooks for embedding and styling
            svgoPlugins: [{
                cleanupIDs: false
            }]
        })))
        .pipe(gulp.dest(Config.path.build + '/img'));
});

// Fonts
gulp.task('fonts', () => {
    return gulp.src(require('main-bower-files')('**/*.{eot,svg,ttf,woff,woff2}')
        .concat(Config.path.assets + '/fonts/**/*'))
        .pipe(gulp.dest(Config.path.build + '/fonts'));
});

// Clean
gulp.task('clean', del.bind(null, [Config.path.build]));

// Serve
gulp.task('serve', ['styles', 'scripts', 'fonts'], () => {
    browserSync({
        notify: false,
        port: Config.reload.port,
        proxy: Config.reload.proxy
    });

    gulp.watch([
        'app/Resources/**/*.html.twig',
        // 'src/**/Resources/views/**/*.html.twig',
        Config.path.build + '/js/**/*.js',
        Config.path.build + '/css/**/*.css',
        Config.path.build + '/img/**/*',
        Config.path.build + '/fonts/**/*'
    ]).on('change', reload);

    gulp.watch(Config.path.assets + '/styles/**/*.scss', ['styles']);
    gulp.watch(Config.path.assets + '/scripts/**/*.js', ['scripts']);
    gulp.watch(Config.path.assets + '/fonts/**/*', ['fonts']);
    gulp.watch(Config.path.assets + '/images/**/*', ['images']);
    gulp.watch('bower.json', ['wiredep', 'fonts']);
});

// Wiredep
gulp.task('wiredep', () => {
    gulp.src(Config.path.assets + '/styles/*.scss')
        .pipe(wiredep())
        .pipe(gulp.dest(Config.path.assets + '/styles'));
});

// Build
gulp.task('build', ['lint', 'assets', 'images', 'fonts'], () => {
    return gulp.src(Config.path.build + '/**/*').pipe($.size({
        title: 'build',
        gzip: true
    }));
});

// Default task
gulp.task('default', ['clean'], () => {
    gulp.start('build');
});
<file_sep>console.log('app.js');

var jQuery = require('jquery');

(function($) {
    $('body').append('jQuery should works fine!');
})(jQuery);
<file_sep># gulp-symfony

Symfony assets management with Gulp - made simple.

## About
Speed up your frontend workflow while developing Symfony apps with tools like [Gulp](http://gulpjs.com), [Bower](http://bower.io), [Browserify](http://browserify.org), [Sass](http://sass-lang.com), [BrowserSync](https://browsersync.io) and more. Inspired by and partially copied from [Yeoman](http://yeoman.io) [Web app generator](https://github.com/yeoman/generator-gulp-webapp).

## Features
- Livereload with [BrowserSync](https://browsersync.io)
- CSS with Sass, Autoprefixer, sourcemaps for developing and CSSNano for minification
- JavaScript with [ESLint](http://eslint.org) and [Browserify](http://browserify.org) + [Debowerify](https://github.com/eugeneware/debowerify) for bundling bower components.
- Image optimalization with [imagemin](https://github.com/imagemin/imagemin)

## Installation
Download this repository to your Symfony project folder. Assets are located under app/assets folder, feel free to change if needed.

Install Gulp and Bower globally
```
$ npm install -g gulp bower
```

Install dependencies
```
$ npm install
```

## Configuration
Inside gulpfile you can find Config variable.
```javascript
var Config = {
    path: {
        'assets': 'app/assets',
        'build': 'web/assets'
    },
    scripts: ['app.js'],
    reload: {
        'proxy': 'local.dev/app_dev.php',
        'port': 3000
    }
};
```
`path`: files location, `assets` for source files and `build` for build

`scripts`: you can define more than just one script if you need admin.js or whatever

`reload`: browsersync options, set proxy to your local url

**Important!** Build folder is cleaned before every build, so do not change this folder to web or any other. You don't want to lose it. :)

## Usage
Install vendors with Bower (default Bootstrap 4)
```
$ bower install
```
`wiredep` task automatically inject files, using main entry inside bower.json, for overriding main entry see [wiredep docs](https://github.com/taptapship/wiredep/tree/master#bower-overrides)

For imported scss files use name prefixed with underscore, because Sass does not compile those files.

Gulp tasks
```
$ gulp -T
```

Build
```
$ gulp
```

Develop
```
$ gulp serve
```

For more information check docs of the tools used in gulpfile.

## Symfony
Linking in Twig
```html
<link rel="stylesheet" href="{{ asset('assets/css/app.css') }}">
<script src="{{ asset('assets/js/app.js') }}"></script>
```

**Note**
By default BrowserSync reloads only if views in app folder changed, you can enable this also for bundle views. Just simply [uncomment this line](https://github.com/makao/gulp-symfony/blob/master/gulpfile.babel.js#L131) in gulpfile.
```javascript
// 'src/**/Resources/views/**/*.html.twig',
```