UNPKG

capt

Version:

Command line tool for creating backbone.js applications with coffeescript

220 lines (159 loc) 6.76 kB
fs = require('fs') sys = require('sys') Path = require("path") Glob = require("glob").globSync root = __dirname + "/../" router = require("#{root}/lib/router") request = require("#{root}/lib/request") _ = require("#{root}/lib/underscore") yaml = require("#{root}/lib/yaml") server = router.getServer() Project = require("#{root}/src/project").Project String.prototype.capitalize = -> this.charAt(0).toUpperCase() + this.substring(1).toLowerCase() OptionParser = require("#{root}/lib/parseopt").OptionParser parser = new OptionParser { minargs : 1 maxargs : 10 } $usage = ''' Usage: capt new projectname - create a new project capt server - serve the current project on port 3000 capt watch - watch the current project and recompile as needed ''' try data = parser.parse() catch e sys.puts $usage process.exit() # # Raise an error # raise = (error) -> sys.puts error process.exit() task = (command, description, func) -> length = command.split(' ').length if data.arguments.slice(0,length).join(" ") == command func(data.arguments.slice(length)) # # Start the server # task 'server', 'start a webserver', (arguments) -> project = new Project(process.cwd()) project.targets = arguments server.get "/", (req, res, match) -> ejs = fs.readFileSync("#{project.root}/index.jst") + "" _.template(ejs, { project : project }) server.get "/test/", (req, res) -> ejs = fs.readFileSync("#{root}/templates/html/runner.jst") + "" _.template(ejs, { project : project }) server.get /(.*)/, router.staticDirHandler(project.root, '/') server.listen(3000) task 'build', 'concatenate and minify all javascript and stylesheets for production', (arguments) -> project = new Project(process.cwd()) project.targets = arguments sys.puts "Building #{project.name()}..." if project.targets.length > 0 sys.puts " * Targets: #{project.targets.join(', ')}" else sys.puts "You must specify a target (eg web)" try fs.mkdirSync "#{project.root}/build", 0755 catch e # .. ok .. output = "#{project.root}/build/#{project.targets[0]}" try fs.mkdirSync output, 0755 catch e # .. ok .. sys.puts " * #{output}/bundled-javascript.js" sys.puts " - " + project.getScriptDependencies().join("\n - ") project.bundleJavascript("#{output}/bundled-javascript.js") sys.puts " * #{output}/bundled-stylesheet.css" sys.puts " - " + project.getStylesheetDependencies().join("\n - ") project.bundleStylesheet("#{output}/bundled-stylesheet.css") sys.puts " * #{output}/index.html" project.scriptIncludes = -> project.getScriptTagFor('/bundled-javascript.js') project.stylesheetIncludes = -> project.getStyleTagFor('/bundled-stylesheet.css') ejs = fs.readFileSync("#{project.root}/index.jst") + "" fs.writeFileSync("#{output}/index.html", _.template(ejs, { project : project })) task 'watch', 'watch files and regenerate test.html and index.html as needed', (arguments) -> project = new Project(process.cwd()) project.targets = arguments timer = null doRebuild = -> sys.puts "Rebuilt project..." ejs = fs.readFileSync("#{project.root}/index.jst") + "" fs.writeFileSync("#{project.root}/index.html", _.template(ejs, { project : project })) ejs = fs.readFileSync("#{project.root}/spec/index.jst") + "" fs.writeFileSync("#{project.root}/spec/index.html", _.template(ejs, { project : project })) rebuild = -> if timer clearTimeout timer timer = setTimeout(doRebuild, 25) for script in project.getFilesToWatch() fs.watchFile Path.join(project.root, script), -> rebuild() rebuild() task 'new', 'create a new project', (arguments) -> project = arguments[0] or raise("Must supply a name for new project.") sys.puts " * Creating folders" dirs = ["", "app", "app/views", "app/views/jst", "app/controllers", "app/models", "lib", "public", "public/stylesheets", "test", "test/controllers", "test/views", "test/models", "test/fixtures"] for dir in dirs fs.mkdirSync "#{project}/#{dir}", 0755 sys.puts " * Downloading libraries" libs = { "lib/jquery.js" : "http://code.jquery.com/jquery-1.4.4.js", "lib/underscore.js" : "http://documentcloud.github.com/underscore/underscore.js" "lib/backbone.js" : "http://documentcloud.github.com/backbone/backbone.js" "lib/coffeescript.js" : "http://jashkenas.github.com/coffee-script/extras/coffee-script.js" "lib/less.js" : "https://github.com/cloudhead/less.js/raw/master/dist/less-1.0.40.js" "test/qunit.js" : "http://github.com/jquery/qunit/raw/master/qunit/qunit.js" "test/qunit.css" : "http://github.com/jquery/qunit/raw/master/qunit/qunit.css" "config.yml" : Path.join(root, "templates/config.yml") "index.jst" : Path.join(root, "templates/html/index.jst") } downloadLibrary = (path, lib) -> request { uri : lib }, (error, response, body) -> if (!error && response.statusCode == 200) fs.writeFileSync("#{project}/#{path}", body) copyLibrary = (path, lib) -> fs.writeFileSync(Path.join(project, path), fs.readFileSync(lib) + "") for path, lib of libs if lib.match(/^http/) downloadLibrary(path, lib) else copyLibrary(path, lib) task 'generate model', 'create a new model', (arguments) -> project = new Project(process.cwd()) if arguments[0] model = arguments[0].toLowerCase() else raise("Must supply a name for the model") copyFile = (from, to) -> ejs = fs.readFileSync(from) + "" fs.writeFileSync(Path.join(project.root, to), _.template(ejs, { project : project, model : model })) sys.puts "Created #{to}" copyFile "#{root}/templates/models/model.coffee", "app/models/#{model}.#{project.language()}" copyFile "#{root}/templates/models/test.coffee", "test/models/#{model}.#{project.language()}" copyFile "#{root}/templates/models/fixture.yml", "test/fixtures/#{model}.yml" task 'generate controller', 'create a new controller', (arguments) -> project = new Project(process.cwd()) if arguments[0] controller = arguments[0].toLowerCase() else raise("Must supply a name for the controller") copyFile = (from, to) -> ejs = fs.readFileSync(from) + "" fs.writeFileSync(Path.join(project.root, to), _.template(ejs, { project : project, controller : controller })) sys.puts "Created #{to}" fs.mkdirSync "#{project.root}/app/views/#{controller}", 0755 copyFile "#{root}/templates/controllers/controller.coffee", "app/controllers/#{controller}_controller.#{project.language()}" copyFile "#{root}/templates/controllers/test.coffee", "test/controllers/#{controller}_controller.#{project.language()}"