构build工具:包含多个组件的Coffeescript / Node项目

我正在开始一个项目,想知道最好的构build工具是什么。

整个事情是用CoffeeScript编写的,使用AngularJS作为客户端,使用NodeJS作为服务器。

应用程序有几个组件:

  • 一个iPad应用程序
  • 一个iPhone应用程序(与iPad不同的function)
  • 一个CMS的应用程序
  • 一个NodeJS服务器

所有这些代码之间都有大量的共享代码,全部用CoffeeScript编写。

我想要一个构build工具,在那里我可以列出哪个应用程序使用什么代码(大部分共享),并将每个应用程序的JavaScript文件构build到一个单独的文件夹。

例如,我将设置一个名为“/ compiled / ipad /”的文件夹,其中包含index.html,以及js,css,img等的文件夹。我将列出要编译的咖啡文件放入/ compiled / ipad / js (其中一些来自/src/shared/*.coffee,其中一些来自/src/ipad/*.coffee等)以及我想将哪些文件引入/ compiled / ipad / css。 我希望它能够轻松地连接文件,我也想要。

它也会编译我的testing,从/ src / test / ipad到/compiled/test/ipad/*.js。

我所有的客户端unit testing都是使用单线testing编写的,而且我不确定我会写什么服务器端unit testing。

什么构build工具/configuration是最好的方法在这里? 一个Makefile? 像Grunt的东西? 我真的是新来的整个build设现场。

编辑 :决定去Browserify。 您可以在这里find我的解决scheme使其与Angular协同工作: https : //groups.google.com/forum/#!topic/ angular/ ytoVaikOcCs

我会把所有的共享代码放到Node.js模块中,并创build一个如下所示的项目:

Project |~apps/ | |~cms/ | | `-app.js | |~ipad/ | | `-app.js | |~iphone/ | | `-app.js | `~node/ | `-app.js |~libs/ | |-module.js | `-module2.js |~specs/ | |~cms/ | | `-app.js | |~ipad/ | | `-app.js | |~iphone/ | | `-app.js | `~node/ | `-app.js | `~libs/ | |-module.js | `-module2.js `-Makefile 

然后,我会使用像Browserify(还有其他)来在需要的地方制作客户端应用程序。 这样,而不是有一个构build文件,你说你需要你实际上有真正的应用程序导入模块。

就我个人而言,我认为在javascript或coffeescript中编写服务器端代码的驱动器也扩展到了您的构build工具链中:所以也坚持使用javascript / coffeescript。 这将允许你轻松地从你的构build工具自动化你的服务器/客户端任务 – 我怀疑它是否有可能使用另一个工具如make(你只是在编写node.js命令调用的包装器)。 build议,按结构化sorting:

  • node.js :只需在JavaScript中构build脚本,并使用节点调用它们即可。 类似于shell脚本,我想。 我不推荐这条路线。
  • 杰克还是蛋糕 :我来自java世界,所以这些都让我想起了ant,这并不奇怪。 我更喜欢咖啡,因此喜欢蛋糕。
  • 咕噜声 :我以前没有听说过这个,所以我不能给出太多build议。 这让我想起了maven,当然…我可以说…构build工具越倾向于执行的结构越不灵活。 这是一个权衡的东西。 只要你这样做“构build工具”的方式,你可以节省很多时间。 但是,如果您有特定的应用程序问题,解决这个问题可能是一个极大的难题。

当然,你可以使用其他一些你已经熟悉的构build工具:rake,maven,ant,gradle等等。

我根据需要使用节点模块在Cakefile中完成了几乎所有的事情。

使用每个文件的path设置一些全局variables,这些全局variables是数组,将这些文件连接成指定的编译目录中的文件,然后将该文件编译为js。

对于风格来说,与没有编译的连接相同的东西,显然。

 fs = require 'fs' path = require 'path' {spawn, exec} = require 'child_process' parser = require('uglify-js').parser uglify = require('uglify-js').uglify cleanCss = require 'clean-css' coffees = [ "/src/shared/file1.coffee" "/src/shared/file2.coffee" "/src/ipad/file1.coffee" ] tests = [ "/src/ipad/tests.coffee" ] styles = [ "/src/ipad/styles1.css" "/src/shared/styles2.css" ] concatenate = (destinationFile, files, type) -> newContents = new Array remaining = files.length for file, index in files then do (file, index) -> fs.readFile file, 'utf8', (err, fileContents) -> throw err if err newContents[index] = fileContents if --remaining is 0 fs.writeFile destinationFile, newContents.join '\n\n', 'utf8', (err) -> throw err if err if type is 'styles' minifyCss fileName else compileCoffee fileName compileCoffee = (file) -> exec "coffee -c #{file}", (err) -> throw err if err # delete coffee file leaving only js fs.unlink 'path/specifying/compiled_coffee', (err) -> throw err if err minifyJs file minifyJs = (file) -> fs.readFile f, 'utf8', (err, contents) -> ast = parser.parse contents ast = uglify.ast_mangle ast ast = uglify.ast_squeeze ast minified = uglify.gen_code ast writeMinified file, minified writeMinified = (file, contents) -> fs.writeFile file, contents, 'utf8', (err) -> throw err if err minifyCss = (file) -> fs.readFile file, 'utf8', (err, contents) -> throw err if err minimized = cleanCss.process contents clean = minimized.replace 'app/assets', '' fs.writeFile file, clean, 'utf8', (err) -> throw err if err task 'compile_coffees', 'concat, compile, and minify coffees', -> concatenate '/compiled/ipad/code.coffee', coffees, 'coffee' task 'concat_styles', 'concat and minify styles', -> concatenate '/compiled/ipad/css/styles.css', styles, 'styles' task 'compile_tests', 'concat, compile, and minify test', -> concatenate '/compiled/ipad/tests.coffee', tests, 'tests' 

现在这大概是我想你所要求的。

可以肯定是更漂亮,尤其是有一个单独的函数来编写缩小的内容,但它的工作原理。

不完美的风格要么因为我使用Sass和其他function之前,它击中缩小function,但我认为你明白了。