Grunt:观看多个文件,只编译更改

我是Grunt的新手,到目前为止我非常享受。 我希望Grunt在运行grunt watch时只编译更改的文件

在我的Grunfile.coffee中,我现在有(相关部分)。
注意:assets / javascript / app.coffee和assets / javascript / app.js是目录

  coffee: default: expand: true cwd: "assets/javascript/app.coffee" src: ["*.coffee"] dest: "assets/javascript/app.js" ext: ".js" uglify: dev: options: beautify: true compress: false mangle: false preserveComments: 'all' files: "js/app.js": "assets/javascript/app.js/*.js" "js/libs.js": "assets/javascript/libs/*.js" watch: coffeescript: files: 'assets/javascript/**/*.coffee' tasks: ["coffee"] javascript: files: "assets/**/*.js" tasks: ["uglify:dev"] livereload: files: ["Gruntfile.coffee", "js/*.js", "*.php", "css/*.css", "images/**/*.{png,jpg,jpeg,gif,webp,svg}", "js/*.js", ] options: livereload: true 

有可能是一个较短的路,但我首先编译app.coffee到app.js,以便在我分发我的工作后,不喜欢Coffeescript的人可以以合理的方式浏览代码。

所有这一切的问题是,现在我保存了一个Coffeescript文件,我得到了太多的步骤(我认为):

 >> File "assets/javascript/app.coffee/browse.coffee" changed. Running "coffee:default" (coffee) task File assets/javascript/app.js/browse.js created. File assets/javascript/app.js/filters.js created. Done, without errors. Completed in 0.837s at Tue May 28 2013 12:30:18 GMT+0300 (EEST) - Waiting... OK >> File "assets/javascript/app.js/browse.js" changed. >> File "assets/javascript/app.js/filters.js" changed. Running "uglify:dev" (uglify) task File "js/app.js" created. File "js/libs.js" created. Done, without errors. Completed in 0.831s at Tue May 28 2013 12:30:19 GMT+0300 (EEST) - Waiting... OK >> File "js/app.js" changed. >> File "js/libs.js" changed. Completed in 0.000s at Tue May 28 2013 12:30:19 GMT+0300 (EEST) - Waiting... 

目前,我只是设置了我的项目,但是我将拥有更多的Coffeescript文件,并且我不希望Coffeescript在每次更改文件时重新编译所有文件。

另外,libs.js根本就没有这个function,但是我猜它仍然是编译好的,因为它也匹配“assets / * / .js”模式。

有没有办法让Grunt只编译已经改变的文件?

我终于find了一个真正的解决scheme! 而且它也超级简单!

npm install grunt-newer --save-dev

然后在你的Gruntfile中(在grunt中加载任务之后):

 watch: coffeescript: files: 'assets/javascript/**/*.coffee' tasks: ["newer:coffee"] 

而就是这样! 真棒咕噜新 –真棒!

如果将所有的.coffee源文件连接成一个.js文件,那么每当源文件发生更改时,都必须重新编译它。 将其拆分成几个.js文件,然后制作一个发布任务,只在这些.js文件中进行连接。 这样你仍然只需要包含一个.js文件。

请参阅使用gruntjs,如何监视.coffee文件中的更改?

grunt.event.on事件检测文件中的更改,接收action和文件filepath参数。

这是一个基于我的gruntfiles之一的未经testing的例子。 在这种情况下,我所有的源代码coffeescript文件都保存在一个名为sources的目录中,并且为了预览它们被编译并保存到一个名为dev的目录下的相同目录结构

 SOURCES_DIR = 'sources' DEV_DIR = 'dev' grunt.initConfig watch : all : files : ["**/*.coffee"] coffee : dev : files : dest : "app.js" grunt.loadNpmTasks 'grunt-contrib-watch' grunt.loadNpmTasks 'grunt-contrib-coffee' grunt.registerTask 'build', ['coffee:dev'] grunt.event.on('watch', (action,filepath) -> # Determine the full directory of the changed file wdi = filepath.lastIndexOf '/' wd = filepath.substring 0,wdi # remove `sources` prefix from that directory fpath = wd.replace(SOURCES_DIR,'') + '/' # determine the filename fnamei = filepath.lastIndexOf '.' fname = filepath.substring wdi+1,fnamei # NOTE: this breaks the case where in same dir # concatenate fpath and fname with the dir to be compiled into deststr = "#{DEV_DIR}#{fpath}#{fname}.coffee" # set coffee.dev.files value in the coffee task to have am entry of form {"destination":"source"} obj = {} obj[deststr] = filepath grunt.config "coffee.dev.files", obj # fire the coffee task grunt.task.run "coffee" ) 

希望有所帮助。

编辑:可能不完全是你想要的 – 因为毫无疑问,你想访问中间variables,行动等 – 但你可以使用grunt来运行一个shell的咖啡命令。 例如, grunt-shell npm任务执行此操作

EDIT2:我遇到了grunt.watch.on在OSX 10.8和MacVim 7.3的grunt 0.4.1中不能稳定工作的问题; 无论出于何种原因,都会停止观看。 我已经恢复到只使用基本的grunt initConfig对象,但具有更多的粒度,所以它只能监视和编译相对较小的文件组而不是整个文件。 这大大减缓了构build时间,但它更强大。 你的里程可能非常。

我也偶然发现了这个问题,并没有find与当前版本(0.4.1)一起工作的任何工作版本,但Jof Arnolds的回答显示了一个好方法。

这就是我想到的:

 # only recompile changed files grunt.event.on "watch", (action, filepath) -> # note that we have to manually change the target file name to # our desired format targetName = filepath.replace(/\/(client|shared)/, "") .replace(".coffee", ".js") .replace("app/", "") options = src: filepath dest: "public/javascripts/#{targetName}" grunt.config ["coffee", "client"], options 

我有一个咖啡部分,看起来有点像这样:

 coffee: client: options: sourceMap: false files: [ expand: true cwd: "app" src: ["*/client/**/*.coffee", "helpers/{client,shared}/*.coffee"] dest: "public/javascripts" rename: (folder, name) -> name = name.replace(/\/(client|shared)/, "") [folder, name].join path.sep ext: ".js" ]