Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to 'watch' Sass files? #17

Closed
Integralist opened this issue Jan 22, 2013 · 11 comments
Closed

How to 'watch' Sass files? #17

Integralist opened this issue Jan 22, 2013 · 11 comments

Comments

@Integralist
Copy link

Hi,

Below is my Gruntfile (I'm using 0.4.0rc2 at the moment). I'm trying to 'watch' my Sass files so I don't have to manually run either grunt or grunt sass to compile changes in my Sass file. Can any one demonstrate in my below set-up how to do that?

Thanks.

module.exports = function (grunt) {

  /*
      Grunt set-up:
        npm install -g grunt-cli
        npm install -g grunt-init
        npm init

      Requirements: 
        npm install grunt@devel --save-dev
        npm install grunt-contrib-watch --save-dev
        npm install grunt-contrib-jshint --save-dev
            At time of testing I needed more up to date version of jshint: npm install https://github.com/gruntjs/grunt-contrib-jshint/archive/7fd70e86c5a8d489095fa81589d95dccb8eb3a46.tar.gz --save-dev
        npm install grunt-contrib-uglify --save-dev
        npm install grunt-contrib-requirejs --save-dev
        npm install grunt-contrib-sass --save-dev
        npm install grunt-contrib-imagemin --save-dev
        npm install grunt-contrib-htmlmin --save-dev

   */

  // Project configuration.
  grunt.initConfig({

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

    jshint: {
      files: ['Gruntfile.js', 'app/**/*.js', '!app/release/**', 'modules/**/*.js'],
      options: {
        curly: true,
        eqeqeq: true,
        immed: true,
        latedef: true,
        newcap: true,
        noarg: true,
        sub: true,
        undef: true,
        boss: true,
        eqnull: true,
        browser: true,

        globals: {
          module: true,
          require: true,
          requirejs: true,
          jQuery: true,
          console: true,
          define: true
        }
      }
    },

    watch: {
      files: '<%= jshint.files %> <%= sass.dev.files %>',
      tasks: 'default'
    },

    requirejs: {
      compile: {
        options: {
          baseUrl: './app',
          mainConfigFile: './app/main.js',
          dir: './app/release/',
          modules: [
            {
              name: 'main'
            }
          ]
        }
      }
    },

    sass: {
      dist: {
        options: {
          style: 'compressed'
        },
        files: {
          './app/styles/main.css': './app/styles/sass/main.scss'
        }
      },
      dev: {
        options: {
          style: 'expanded'
        },
        files: {
          './app/styles/main.css': './app/styles/sass/main.scss'
        }
      }
    }

  });

  // Load NPM Tasks
  grunt.loadNpmTasks('grunt-contrib-watch');
  grunt.loadNpmTasks('grunt-contrib-jshint');
  grunt.loadNpmTasks('grunt-contrib-uglify');
  grunt.loadNpmTasks('grunt-contrib-requirejs');
  grunt.loadNpmTasks('grunt-contrib-sass');
  grunt.loadNpmTasks('grunt-contrib-imagemin');
  grunt.loadNpmTasks('grunt-contrib-htmlmin');

  // Default Task
  grunt.registerTask('default', ['jshint', 'sass']);

  // Release Task
  grunt.registerTask('release', ['requirejs']);
};

To elaborate on the issue I'm having, if I run grunt watch then I see the message Running "watch" task Waiting...

If I then update my JS files so there is an error, nothing is flagged up on the CLI. But if I edit the line in my grunt file to not point to any Sass files. e.g. change

watch: {
      files: '<%= jshint.files %>  <%= sass.dev.files %>',
      tasks: 'default'
    }

to

watch: {
      files: '<%= jshint.files %>',
      tasks: 'default'
    }

...then run grunt watch again, this time any JS errors are picked up as they should be.

But nothing I do seems to get the Sass files to be re-compiled when the .scss is updated?

@shama
Copy link
Member

shama commented Jan 22, 2013

Change your watch target:
files: '<%= jshint.files %> <%= sass.dev.files %>',
to files: ['<%= jshint.files %>', '<%= sass.dev.files %>'],

@Integralist
Copy link
Author

Thanks @sindresorhus for moving this issue over and @shama for your feedback but I still have an issue with the watch command.

I'm currently using the command grunt watch but I get the following error...

$ grunt watch
Running "watch" task
Waiting...Fatal error: glob pattern string required

...I'm not sure what the fix is for this as I was under the impression the Gruntfile was valid?

Any ideas?

Below is my updated Gruntfile.js file content...

module.exports = function (grunt) {

  grunt.initConfig({

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

    jshint: {
      files: ['Gruntfile.js', 'app/**/*.js', '!app/release/**', 'modules/**/*.js'],
      options: {
        curly: true,
        eqeqeq: true,
        immed: true,
        latedef: true,
        newcap: true,
        noarg: true,
        sub: true,
        undef: true,
        boss: true,
        eqnull: true,
        browser: true,

        globals: {
          module: true,
          require: true,
          requirejs: true,
          jQuery: true,
          console: true,
          define: true
        }
      }
    },

    watch: {
      files: ['<%= jshint.files %>', '<%= sass.dev.files %>'],
      tasks: 'default'
    },

    requirejs: {
      compile: {
        options: {
          baseUrl: './app',
          mainConfigFile: './app/main.js',
          dir: './app/release/',
          modules: [
            {
              name: 'main'
            }
          ]
        }
      }
    },

    sass: {
      dist: {
        options: {
          style: 'compressed'
        },
        files: {
          './app/styles/main.css': './app/styles/sass/main.scss'
        }
      },
      dev: {
        options: {
          style: 'expanded'
        },
        files: {
          './app/styles/main.css': './app/styles/sass/main.scss'
        }
      }
    },

    imagemin: {
      dist: {
        options: {
          optimizationLevel: 7,
          progressive: true
        },
        files: {
          //'./app/images/': './app/images/**/*.jpg'
          './app/images/test-min.jpg': './app/images/test.jpg',
          './app/images/car-min.jpg': './app/images/car.jpg'
        }
      },
      dev: {
        options: {
          optimizationLevel: 1
        },
        files: {
          //'./app/images/': './app/images/**/*.jpg'
          './app/images/test-min.jpg': './app/images/test.jpg',
          './app/images/car-min.jpg': './app/images/car.jpg'
        }
      }
    },

    htmlmin: {
      dist: {
        options: {
          removeComments: true,
          collapseWhitespace: true,
          removeEmptyAttributes: true,
          removeCommentsFromCDATA: true,
          removeRedundantAttributes: true,
          collapseBooleanAttributes: true
        },
        files: {
          './index-min.html': './index.html'
        }
      },
      dev: {
        files: {
          './index-min.html': './index.html'
        }
      }
    }

  });

  // Load NPM Tasks
  grunt.loadNpmTasks('grunt-contrib-watch');
  grunt.loadNpmTasks('grunt-contrib-jshint');
  grunt.loadNpmTasks('grunt-contrib-uglify');
  grunt.loadNpmTasks('grunt-contrib-requirejs');
  grunt.loadNpmTasks('grunt-contrib-sass');
  grunt.loadNpmTasks('grunt-contrib-imagemin');
  grunt.loadNpmTasks('grunt-contrib-htmlmin');

  // Default Task
  grunt.registerTask('default', ['jshint', 'sass:dev']);

  // Release Task
  grunt.registerTask('release', ['requirejs', 'sass:dist', 'imagemin', 'htmlmin']);
};

@shama
Copy link
Member

shama commented Jan 23, 2013

To run the watch task, try grunt watch (and not grunt --watch).

@Integralist
Copy link
Author

@shama thanks I've literally just finished updating my comment when I noticed you posted a reply! You'll now see my updated comment already mentions this and I'm now geting an odd error message. If you have any ideas I'd be grateful. Thanks again

@shama
Copy link
Member

shama commented Jan 23, 2013

Oh interesting, it's because <%= sass.dev.files %> points to an object. Currently the watch task only supports a string or array of patterns. But I think it should read objects as well. In the meantime, just replace <%= sass.dev.files %> with app/styles/sass/main.scss. I'll open up an issue on the watch task to get that format supported.

@shama
Copy link
Member

shama commented Jan 23, 2013

Closing as moved to the watch task issue tracker. Thanks @Integralist

@shama shama closed this as completed Jan 23, 2013
@shama
Copy link
Member

shama commented Jan 23, 2013

Ok nevermind, I was wrong the watch shouldn't read object literals.
Just specify your sass targets with explicit src and dest paramters, like this:

sass: {
  dev: {
    options: {
      style: 'expanded'
    },
    src: ['./app/styles/sass/main.scss'],
    dest: './app/styles/main.css'
  }
},

and then update your watch target like this:

watch: {
  files: ['<%= jshint.files %>', '<%= sass.dev.src %>'],
  tasks: 'default'
},

@sindresorhus
Copy link
Member

@shama Why shouldn't

files: {
          './app/styles/main.css': './app/styles/sass/main.scss'
        }

work?

// @cowboy

@cowboy
Copy link
Member

cowboy commented Jan 23, 2013

Because I'd have to code logic into the underlying grunt.config system to somehow tell it that (all) objects referenced via a template string should be stringified in a non-generalized way.

@sindresorhus
Copy link
Member

Any plans to fix it?

Right now it feels a bit convoluted, since you recommend the above style, but it can't be referenced in templates.

Should at least be clearly documented. I've been bitten by this before too.

@cowboy
Copy link
Member

cowboy commented Jan 23, 2013

I currently can't think of a way to fix it, but I'm sure I'll spend countless hours trying for grunt 0.5. It might require me to create my own underscore template processing function, I have no idea. It's fairly complicated tbh.

I probably won't be able to take a look at the docs until next week.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants