GiantSoup
GiantSoup

Reputation: 33

How to incorporate "Auto Prefixer" into "package.json" and "grunt.js"?

I am a newbie to web-design and as you can imagine, trying to become a full-stack developer with stuff like SaSS, NPM and Grunt is a huge learning curve. I have a boilerplate WordPress theme that incorporates a grunt workflow with sass, a minifier, BrowserSync and all that fun stuff. But it does not have autoprefixer in the workflow and I would like to add it because I would like to start testing out FlexBox designs and that requires a lot of prefixing to make work correctly. I searched the web for how to simply add Auto Prefixer to the gruntfile and all the answers are super vague with instructions like "just add this code to the grunt.js file"... ok well where exactly in the file? This is supposed to be a "post-process" and the grunt.js seems to be written in the order it will complete the tasks. I am also not familiar with any of the syntax so just saying "include it" does not help, I am always worried that I didn't put it after a certain bracket or before a semi-colon correctly. I would just like someone to explicitly tell me EXACTLY where I need to put the code in the grunt.js file.

As a bonus, I would like to add this to my package.json file, so that in the future when I start a new project and I run my initial "install npm" command, it will download auto prefixer and be ready to go out the gate.

SO tldr; How do I download auto prefixer? (is it a set of files in a folder? Where exactly in my project should the folder of files go, just in case I install it in the wrong place initially through the command line) Where EXACTLY do I need to add the autoprefixer code in my Grunt.js file? Finally, what and where EXACTLY do I need to put into my package.json file to make sure that autoprefixer is included in my future projects when I type "install npm" the first time?

I will include both my current Grunt.js file and package.json file so one of you will be able to simply copy/paste the necessary code in for me. This will help me in the future to know how to add new processes to my workflow.

This is my Grunt.js file:

module.exports = function ( grunt ) {
    'use strict';

    // Load all grunt tasks matching the 'grunt-*' pattern
    require( 'load-grunt-tasks' )( grunt );

    // Time how long tasks take.
    require('time-grunt')(grunt);

    // Get this party started
    grunt.initConfig({

        pkg: grunt.file.readJSON( 'package.json' ),

        // Global variables
        config: {
            src: 'assets/src',
            dist: 'assets/dist',
            devUrl: 'tayloroyer.local:8888'
        },

        // Libsass
        sass: {
            minified: {
                options: {
                    sourceMap: true,
                    outputStyle: 'compressed', // expanded, nested, compressed
                },
                files: {
                    '<%= config.dist %>/css/main.min.css': '<%= config.src %>/sass/main.scss',
                    '<%= config.dist %>/css/no-mq.min.css': '<%= config.src %>/sass/no-mq.scss'
                }
            },
            expanded: {
                options: {
                    outputStyle: 'expanded'
                },
                files: {
                    '<%= config.dist %>/css/main.css': '<%= config.src %>/sass/main.scss',
                    '<%= config.dist %>/css/no-mq.css': '<%= config.src %>/sass/no-mq.scss'
                }
            }
        },

        // Clean CSS Output
        csscomb: {
            dist: {
                options: {
                    config: '<%= config.src %>/sass/csscomb.json'
                },
                files: {
                    '<%= config.dist %>/css/main.css': ['<%= config.dist %>/css/main.css'],
                    '<%= config.dist %>/css/no-mq.css': ['<%= config.dist %>/css/no-mq.css']
                }
            }
        },

        // Concatenate JS Files
        concat: {
            main: {
                files: {
                    '<%= config.dist %>/js/main.js': '<%= config.src %>/js/main.js'
                }
            },
            plugins: {
                files: {
                    '<%= config.dist %>/js/plugins.js': [
                        '<%= config.src %>/js/plugins/boilerplate.js',
                        '<%= config.src %>/js/plugins/jquery.magnific-popup.js',
                        '<%= config.src %>/js/plugins/jquery.cycle2.js',
                        '<%= config.src %>/js/plugins/jquery.cycle2.swipe.js'
                    ]
                }
            }
        },

        // Minify JS
        uglify: {
            options: {
                sourceMap: true,
                preserveComments: 'some'
            },
            main: {
                files: {
                    '<%= config.dist %>/js/main.min.js': [ '<%= config.src %>/js/main.js' ]
                }
            },
            plugins: {
                files: {
                    '<%= config.dist %>/js/plugins.min.js': [ '<%= config.dist %>/js/plugins.js' ]
                }
            }
        },

        // Optimize Media
        imagemin: {
            images: {
                options: {
                    optimizationLevel: 3, // default
                    progressive: true // default
                },
                files: [{
                    expand: true,
                    cwd: '<%= config.src %>/img/',
                    src: ['**/*.{png,jpg,gif}'],
                    dest: '<%= config.dist %>/img/'
                }]
            }
        },

        // Copy Files/Folders
        copy: {
            js: {
                expand: true,
                cwd: '<%= config.src %>/js/plugins/',
                src: 'modernizr-2.8.3.min.js',
                dest: '<%= config.dist %>/js/plugins/',
            }
        },

        // Growl Notifications
        notify: {
            livereload: {
                options: {
                    title: 'Browser Updated',
                    message: 'Livereload completed.'
                }
            }
        },

        browserSync: {
            bsFiles: {
                src: [
                    '<%= config.dist %>/css/*.css',
                    '<%= config.dist %>/js/**/*.js',
                    '<%= config.dist %>/img/',
                    '**/*.php'
                ],
            },
            options: {
                // notify: false,
                // open: false,
                watchTask: true,
                proxy: '<%= config.devUrl %>'
            }
        },

        // Run Tasks When Files Are Modified
        watch: {
            css: {
                files: '<%= config.src %>/sass/**/*.{scss,sass}',
                tasks: [ 'sass:minified' ],
                // tasks: [ 'sass', 'csscomb' ] // slower, but will process all CSS files
            },
            jsMain: {
                files: [
                    '<%= config.src %>/js/main.js'
                ],
                tasks: [ 'uglify:main' ]
            },
            jsPlugins: {
                files: [
                    '<%= config.src %>/js/plugins.js',
                    '<%= config.src %>/js/plugins/**/*.js'
                ],
                tasks: [ 'concat', 'uglify:plugins', 'newer:copy:js' ]
            },
            images: {
                files: [
                    '<%= config.src %>/img/**/*.{png,jpg,gif}'
                ],
                tasks: [ 'newer:imagemin' ]
            },
            // This can be used in place of BrowserSync
            // livereload: {
            //     options: {
            //         livereload: true,
            //         spawn: false
            //     },
            //     files: [
            //         '<%= config.dist %>/css/*.css',
            //         '<%= config.dist %>/js/**/*.js',
            //         '<%= config.dist %>/img/',
            //         // '**/*.php'
            //     ],
            //     tasks: [ 'notify:livereload' ]
            // }
        },

    });

    // Default
    grunt.registerTask( 'default', [
        'sass',
        'csscomb',
        'concat',
        'uglify',
        'newer:copy:js',
        'newer:imagemin',
        'browserSync',
        'watch', // add after 'browserSync'. Not needed for Livereload
    ]);

    // Build
    // Run all tasks, including sass:expanded
    grunt.registerTask( 'build', [
        'sass',
        'csscomb',
        'concat',
        'uglify',
        'newer:copy:js',
        'newer:imagemin',
    ]);

    // Images
    grunt.registerTask( 'media', ['newer:imagemin'] );

};

This is my package.json file:

{
"name": "wordpress-theme",
"version": "1.0.0",
"description": "WordPress theme",
"devDependencies": {
"grunt": "^0.4.5",
"grunt-browser-sync": "^2.1.1",
"grunt-contrib-concat": "^0.5.1",
"grunt-contrib-copy": "^0.8.0",
"grunt-contrib-imagemin": "^0.9.4",
"grunt-contrib-uglify": "^0.9.1",
"grunt-contrib-watch": "^0.6.1",
"grunt-csscomb": "^3.0.0",
"grunt-newer": "^1.1.0",
"grunt-notify": "^0.4.1",
"grunt-sass": "^0.18.1",
"load-grunt-tasks": "^3.1.0",
"time-grunt": "^1.0.0"
},
"repository": {
"type": "git",
"url": "https://github.com/blainerobison/_s.git"
}
}

Upvotes: 2

Views: 864

Answers (1)

Ahmad Alfy
Ahmad Alfy

Reputation: 13371

If you used npm install grunt-autoprefixer that will just install this package into your project. If you added the flag --save that will add this package to packages.json. This way, if you are ignoring the node_modules directory from version control, you can type npm install and it will be fetched automatically.

To clarify, adding the flag means you type the command like this:

npm install grunt-autoprefixer --save

Now onward to start using it. Usually, in order to use any package in grunt you will find that the documentation tells you to include this on the top of the file

grunt.loadNpmTasks('grunt-package-name'); // e.g grunt-autoprefixer

Fortunately, we have a grunt task that automatically check for all grunt tasks on package.json file and include them without the need to include the line mentioned above manually. It's this line on your file

// Load all grunt tasks matching the 'grunt-*' pattern
require( 'load-grunt-tasks' )( grunt );

Now to configure the task, I have modified your Gruntfile.js to this

module.exports = function ( grunt ) {
    'use strict';

    // Load all grunt tasks matching the 'grunt-*' pattern
    require( 'load-grunt-tasks' )( grunt );

    // Time how long tasks take.
    require('time-grunt')(grunt);

    // Get this party started
    grunt.initConfig({

        pkg: grunt.file.readJSON( 'package.json' ),

        // Global variables
        config: {
            src: 'assets/src',
            dist: 'assets/dist',
            devUrl: 'tayloroyer.local:8888'
        },

        // Libsass
        sass: {
            minified: {
                options: {
                    sourceMap: true,
                    outputStyle: 'compressed', // expanded, nested, compressed
                },
                files: {
                    '<%= config.dist %>/css/main.min.css': '<%= config.src %>/sass/main.scss',
                    '<%= config.dist %>/css/no-mq.min.css': '<%= config.src %>/sass/no-mq.scss'
                }
            },
            expanded: {
                options: {
                    outputStyle: 'expanded'
                },
                files: {
                    '<%= config.dist %>/css/main.css': '<%= config.src %>/sass/main.scss',
                    '<%= config.dist %>/css/no-mq.css': '<%= config.src %>/sass/no-mq.scss'
                }
            }
        },

        // Clean CSS Output
        csscomb: {
            dist: {
                options: {
                    config: '<%= config.src %>/sass/csscomb.json'
                },
                files: {
                    '<%= config.dist %>/css/main.css': ['<%= config.dist %>/css/main.css'],
                    '<%= config.dist %>/css/no-mq.css': ['<%= config.dist %>/css/no-mq.css']
                }
            }
        },

        // Add vendor prefixed styles
        autoprefixer: {
            options: {
                browsers: ['> 1%', 'last 2 versions', 'Firefox ESR', 'Opera 12.1']
            },
            dist: {
                files: [{
                    expand: true,
                    cwd: '<%= config.dist %>/css/',
                    src: '{,*/}*.css',
                    dest: '<%= config.dist %>/css/'
                }]
            }
        },

        // Concatenate JS Files
        concat: {
            main: {
                files: {
                    '<%= config.dist %>/js/main.js': '<%= config.src %>/js/main.js'
                }
            },
            plugins: {
                files: {
                    '<%= config.dist %>/js/plugins.js': [
                        '<%= config.src %>/js/plugins/boilerplate.js',
                        '<%= config.src %>/js/plugins/jquery.magnific-popup.js',
                        '<%= config.src %>/js/plugins/jquery.cycle2.js',
                        '<%= config.src %>/js/plugins/jquery.cycle2.swipe.js'
                    ]
                }
            }
        },

        // Minify JS
        uglify: {
            options: {
                sourceMap: true,
                preserveComments: 'some'
            },
            main: {
                files: {
                    '<%= config.dist %>/js/main.min.js': [ '<%= config.src %>/js/main.js' ]
                }
            },
            plugins: {
                files: {
                    '<%= config.dist %>/js/plugins.min.js': [ '<%= config.dist %>/js/plugins.js' ]
                }
            }
        },

        // Optimize Media
        imagemin: {
            images: {
                options: {
                    optimizationLevel: 3, // default
                    progressive: true // default
                },
                files: [{
                    expand: true,
                    cwd: '<%= config.src %>/img/',
                    src: ['**/*.{png,jpg,gif}'],
                    dest: '<%= config.dist %>/img/'
                }]
            }
        },

        // Copy Files/Folders
        copy: {
            js: {
                expand: true,
                cwd: '<%= config.src %>/js/plugins/',
                src: 'modernizr-2.8.3.min.js',
                dest: '<%= config.dist %>/js/plugins/',
            }
        },

        // Growl Notifications
        notify: {
            livereload: {
                options: {
                    title: 'Browser Updated',
                    message: 'Livereload completed.'
                }
            }
        },

        browserSync: {
            bsFiles: {
                src: [
                    '<%= config.dist %>/css/*.css',
                    '<%= config.dist %>/js/**/*.js',
                    '<%= config.dist %>/img/',
                    '**/*.php'
                ],
            },
            options: {
                // notify: false,
                // open: false,
                watchTask: true,
                proxy: '<%= config.devUrl %>'
            }
        },

        // Run Tasks When Files Are Modified
        watch: {
            css: {
                files: '<%= config.src %>/sass/**/*.{scss,sass}',
                tasks: [ 'sass:minified', 'autoprefixer' ], // We added autoprefixer here
                // tasks: [ 'sass', 'csscomb' ] // slower, but will process all CSS files
            },
            jsMain: {
                files: [
                    '<%= config.src %>/js/main.js'
                ],
                tasks: [ 'uglify:main' ]
            },
            jsPlugins: {
                files: [
                    '<%= config.src %>/js/plugins.js',
                    '<%= config.src %>/js/plugins/**/*.js'
                ],
                tasks: [ 'concat', 'uglify:plugins', 'newer:copy:js' ]
            },
            images: {
                files: [
                    '<%= config.src %>/img/**/*.{png,jpg,gif}'
                ],
                tasks: [ 'newer:imagemin' ]
            },
            // This can be used in place of BrowserSync
            // livereload: {
            //     options: {
            //         livereload: true,
            //         spawn: false
            //     },
            //     files: [
            //         '<%= config.dist %>/css/*.css',
            //         '<%= config.dist %>/js/**/*.js',
            //         '<%= config.dist %>/img/',
            //         // '**/*.php'
            //     ],
            //     tasks: [ 'notify:livereload' ]
            // }
        },

    });

    // Default
    grunt.registerTask( 'default', [
        'sass',
        'autoprefixer', // Adding autoprefixer task
        'csscomb',
        'concat',
        'uglify',
        'newer:copy:js',
        'newer:imagemin',
        'browserSync',
        'watch', // add after 'browserSync'. Not needed for Livereload
    ]);

    // Build
    // Run all tasks, including sass:expanded
    grunt.registerTask( 'build', [
        'sass',
        'autoprefixer', // Adding autoprefixer task
        'csscomb',
        'concat',
        'uglify',
        'newer:copy:js',
        'newer:imagemin',
    ]);

    // Images
    grunt.registerTask( 'media', ['newer:imagemin'] );

};

I would really recommed you read it carefully and refer to the package's documentation. This is not something you do from your memory; people always refer to the documentation when it comes to similar stuff.

Upvotes: 1

Related Questions