DSL for compiling files
-- Makefile hello: hello.c
$ make hello cc -o hello hello.c $ make hello make: 'hello' er tidssvarende
Use file dependencies and modification time
# Makefile hello: hello.c
# Catch system calls from process $ strace -e stat "make hello" ... stat("hello", {st_mode=S_IFREG|0775, st_size=8559, ...}) = 0 stat("hello.c", {st_mode=S_IFREG|0664, st_size=61, ...}) = 0 ...
make: 'hello' er tidssvarende.
Rules
# Makefile fisk.js: fisk.coffee %.js: %.coffee coffee < $< > $@
JS_FINAL = js/project-name-all.js JS_TARGETS = $(shell find js -name "*.js") JS_MINIFIED = $(JS_TARGETS:.js=.min.js) all: $(JS_FINAL) # Concat $(JS_FINAL): $(JS_MINIFIED) cat $^ >$@ rm -f $^ %.min.js: %.js uglifyjs -o $@ $< echo >> $@ clean: rm -f $(JS_FINAL)
Actually build system, but great project "menu" and tool abstraction layer
[Why use make]# Makefile .PHONY: migrate js migrate: php artisan migrate --env=development js: # grunt build gulp
$ make migrate $ make js
Could also use npm/composer "scripts"
$ composer run-script migrate
At least one pr language
<!--?xml version="1.0" encoding="UTF-8"?--> <project name="FooBar" default="dist"> <target name="prepare"> <echo msg="Making directory ./build"> <mkdir dir="./build"> </mkdir></echo></target> <target name="build" depends="prepare"> <echo msg="Copying files to build directory..."> <echo msg="Copying ./about.php to ./build directory..."> <copy file="./about.php" tofile="./build/about.php"> <echo msg="Copying ./browsers.php to ./build directory..."> <copy file="./browsers.php" tofile="./build/browsers.php"> <echo msg="Copying ./contact.php to ./build directory..."> <copy file="./contact.php" tofile="./build/contact.php"> </copy></echo></copy></echo></copy></echo></echo></target> <target name="dist" depends="build"> <echo msg="Creating archive..."> <tar destfile="./build/build.tar.gz" compression="gzip"> <fileset dir="./build"> <include name="*"> </include></fileset> </tar> <echo msg="Files copied and compressed in build directory OK!"> </echo></echo></target> </project>
redo, fabricate.py, Tup, ninja, shake
Aim for make, with virtual fs, etc.
Lots of plugins, though
coffee, less, stylus, jade...
// JavaScript module.exports = function(grunt) { grunt.initConfig({ pkg: grunt.file.readJSON('package.json'), concat: { options: { separator: ';' }, dist: { src: ['src/**/*.js'], dest: 'dist/<%= pkg.name %>.js' } }, uglify: { options: { banner: '/*! <%= pkg.name %> <%= grunt.template.today("dd-mm-yyyy") %> */\n' }, dist: { files: { 'dist/<%= pkg.name %>.min.js': ['<%= concat.dist.dest %>'] } } },-> Educas.dk
The streaming build system
Streams er en del af vinyl-fs, men det er et centralt og interessant konceptvar gulp = require("gulp"), jade = require("gulp-jade"); gulp.task("default", function () { gulp.src("app/**/*.jade") .pipe(jade()) .pipe(gulp.dest("public/")); });
Concurrent tasks
// takes in a callback so the engine knows when it'll be done orchestrator.add('one', function (cb) { // do stuff -- async or otherwise cb(err); }); // identifies a dependent task must be complete before this one begins orchestrator.add('two', ['one'], function () { // task 'one' is done now }); orchestrator.start('one', 'two');
# .on('something', ...) "EventEmitter" readable.on('data', function(chunk) { console.log('got %d bytes of data', chunk.length); }) readable.on('end', function() { console.log('there will be no more data.'); }); # Readable stream -> writeable stream
File watching (wraps fs.watch)
gulp.watch("app/**/*.coffee", function () {...});
Virtual files on streams
new File({ cwd: "/home/tbh/educas-dk/", base: "/app/", path: "/app/file.coffee" contents: new Buffer("test = 123") });
Assets
# Gemfile source 'https://rails-assets.org' gem 'rails' gem 'rails-assets' gem 'rails-assets-angular' gem 'rails-assets-bootstrap'
// application.js //= require angular angular.module(...)
$ bundle install $ rails server