├── .gitignore ├── .jshintrc ├── .npmignore ├── .travis.yml ├── CONTRIBUTING.md ├── Gruntfile.js ├── bin └── can-compile ├── example ├── Gruntfile.js ├── bower.json ├── development.html ├── dist │ ├── production.js │ ├── production.min.js │ └── views.production.js ├── index.html ├── js │ ├── app.js │ ├── components │ │ └── todo-app.js │ └── models │ │ └── todo.js ├── package.json ├── readme.md └── views │ └── todos.mustache ├── gulp.js ├── lib ├── compile.js ├── index.js ├── resolveScripts.js └── version-map.json ├── license.md ├── package.json ├── readme.md ├── tasks └── cancompile.js └── test ├── fixtures ├── view.ejs ├── view.mst ├── view.mustache ├── view.stache └── view.unknown └── test.js /.gitignore: -------------------------------------------------------------------------------- 1 | lib-cov 2 | *.seed 3 | *.log 4 | *.csv 5 | *.dat 6 | *.out 7 | *.pid 8 | *.gz 9 | 10 | pids 11 | logs 12 | results 13 | 14 | node_modules 15 | npm-debug.log 16 | resources/js/resources.js -------------------------------------------------------------------------------- /.jshintrc: -------------------------------------------------------------------------------- 1 | { 2 | "globals": { 3 | "it": true, 4 | "describe": true, 5 | "before": true, 6 | "after": true, 7 | "exports": true 8 | }, 9 | "eqnull": true, 10 | "node": true, 11 | "unused": true, 12 | "undef": true 13 | } 14 | -------------------------------------------------------------------------------- /.npmignore: -------------------------------------------------------------------------------- 1 | .idea/ -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | sudo: false 2 | language: node_js 3 | node_js: 4 | - "0.10" 5 | - "node" 6 | - "iojs" 7 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing to can-compile 2 | 3 | Check out the [contribution guide on CanJS.com](https://canjs.com/doc/guides/contribute.html) for information on: 4 | 5 | - [Code of Conduct](https://canjs.com/doc/guides/contribute.html#CodeofConduct) 6 | - [Getting Help](https://canjs.com/doc/guides/contribute.html#GettingHelp) 7 | - [Project Organization](https://canjs.com/doc/guides/contributing/project-organization.html) 8 | - [Reporting Bugs](https://canjs.com/doc/guides/contributing/bug-report.html) 9 | - [Suggesting Features](https://canjs.com/doc/guides/contributing/feature-suggestion.html) 10 | - [Finding Ways to Contribute](https://canjs.com/doc/guides/contributing/finding-ways-to-contribute.html) 11 | 12 | The rest of this guide has information that’s specific to this repository. 13 | 14 | ## Developing Locally 15 | 16 | This section will walk you through setting up the [repository](https://github.com/canjs/can-compile) on your computer. 17 | 18 | ### Signing up for GitHub 19 | 20 | If you don’t already have a GitHub account, you’ll need to [create a new one](https://help.github.com/articles/signing-up-for-a-new-github-account/). 21 | 22 | ### Forking & cloning the repository 23 | 24 | A “fork” is a copy of a repository in your personal GitHub account. “Cloning” is the process of getting the repository’s source code on your computer. 25 | 26 | GitHub has a guide for [forking a repo](https://help.github.com/articles/fork-a-repo/). To fork can-compile, you can start by going to its [fork page](https://github.com/canjs/can-compile/fork). 27 | 28 | Next, you’ll want to clone the repo. [GitHub’s cloning guide](https://help.github.com/articles/cloning-a-repository/) explains how to do this on Linux, Mac, or Windows. 29 | 30 | GitHub’s guide will [instruct you](https://help.github.com/articles/fork-a-repo/#step-2-create-a-local-clone-of-your-fork) to clone it with a command like: 31 | 32 | ```shell 33 | git clone https://github.com/YOUR-USERNAME/can-compile 34 | ``` 35 | 36 | Make sure you replace `YOUR-USERNAME` with your GitHub username. 37 | 38 | ### Installing the dependencies 39 | 40 | After you’ve forked & cloned the repository, you’ll need to install the project’s dependencies. 41 | 42 | First, make sure you’ve [installed Node.js and npm](https://docs.npmjs.com/getting-started/installing-node). 43 | 44 | If you just cloned the repo from the command line, you’ll want to switch to the folder with your clone: 45 | 46 | ```shell 47 | cd can-compile 48 | ``` 49 | 50 | Next, install the project’s dependencies with npm: 51 | 52 | ```shell 53 | npm install 54 | ``` 55 | 56 | ### Starting the development server 57 | 58 | Run the following to start a dev server: 59 | 60 | ```shell 61 | npm run develop 62 | ``` 63 | 64 | ### Running the tests 65 | 66 | You can manually run this repository’s tests in any browser by starting the dev server (see the section above) and visiting this page: http://localhost:8080/test/test.html 67 | 68 | Firefox is used to run the repository’s automated tests from the command line. If you don’t already have it, [download Firefox](https://www.mozilla.org/en-US/firefox/new/). Mozilla has guides for installing it on [Linux](https://support.mozilla.org/t5/Install-and-Update/Install-Firefox-on-Linux/ta-p/2516), [Mac](https://support.mozilla.org/t5/Install-and-Update/How-to-download-and-install-Firefox-on-Mac/ta-p/3453), and [Windows](https://support.mozilla.org/t5/Install-and-Update/How-to-download-and-install-Firefox-on-Windows/ta-p/2210). 69 | 70 | After Firefox is installed, you can run: 71 | 72 | ```shell 73 | npm test 74 | ``` 75 | 76 | ### Making a build 77 | 78 | Run the following command to create a build: 79 | 80 | ```shell 81 | npm run build 82 | ``` 83 | 84 | This will create a `dist/` folder that contains the AMD, CommonJS, and global module versions of the project. 85 | 86 | -------------------------------------------------------------------------------- /Gruntfile.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | 3 | module.exports = function(grunt) { 4 | 5 | // Project configuration. 6 | grunt.initConfig({ 7 | simplemocha: { 8 | options: { 9 | timeout: 30000 10 | }, 11 | app: { 12 | src: ['test/**/*.js'] 13 | } 14 | }, 15 | jshint: { 16 | options: { 17 | jshintrc: '.jshintrc' 18 | }, 19 | lib: ['lib/**/*.js', 'Gruntfile.js'], 20 | test: ['test/**/*.js'] 21 | }, 22 | release: {} 23 | }); 24 | 25 | grunt.registerTask('default', 'test'); 26 | grunt.registerTask('test', [ 'jshint', 'simplemocha' ]); 27 | 28 | grunt.loadNpmTasks('grunt-simple-mocha'); 29 | grunt.loadNpmTasks('grunt-contrib-jshint'); 30 | grunt.loadNpmTasks('grunt-release'); 31 | }; 32 | -------------------------------------------------------------------------------- /bin/can-compile: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | var program = require('commander'); 3 | var pkg = require('../package.json'); 4 | var glob = require('glob'); 5 | var compiler = require('../lib'); 6 | 7 | program.version(pkg.version) 8 | .usage('[options] ') 9 | .description(pkg.description) 10 | .option('-o, --out [name]', 'The output file', 'views.production.js') 11 | .option('-c, --can [version]', 'The CanJS version') 12 | .option('-w, --wrapper [Mustache Template]', 'The output file wrapper') 13 | .option('-e, --extensions [File extensions]', 'View file extension mapping') 14 | .option('-a, --viewAttributes [View attributes]', 'CanJS view attributes (can.view.attr)') 15 | .parse(process.argv); 16 | 17 | var files = []; 18 | if(!program.args || program.args.length === 0) { 19 | program.args = ['**/*.ejs', '**/*.mustache']; 20 | } 21 | 22 | program.args.forEach(function(pattern) { 23 | files = files.concat(glob.sync(pattern)); 24 | }); 25 | 26 | compiler(files, { 27 | out: program.out, 28 | wrapper: program.wrapper, 29 | extensions: program.extensions, 30 | viewAttributes: program.viewAttributes, 31 | version: program.can 32 | }, function(err, output, outfile) { 33 | if(err) { 34 | console.error('There was an error: ' + err.message); 35 | } else { 36 | console.log('Wrote compiled views to ' + outfile); 37 | } 38 | }, console.log); -------------------------------------------------------------------------------- /example/Gruntfile.js: -------------------------------------------------------------------------------- 1 | module.exports = function (grunt) { 2 | 3 | // Project configuration. 4 | grunt.initConfig({ 5 | cancompile: { 6 | options: { 7 | version: '2.1.1' 8 | }, 9 | dist: { 10 | src: ['**/*.ejs', '**/*.mustache', '**/*.stache'], 11 | dest: 'dist/views.production.js' 12 | } 13 | }, 14 | concat: { 15 | dist: { 16 | src: [ 17 | 'bower_components/todomvc-common/base.js', 18 | 'bower_components/jquery/jquery.js', 19 | 'bower_components/canjs/can.jquery.js', 20 | 'bower_components/canjs-localstorage/can.localstorage.js', 21 | 'js/models/todo.js', 22 | 'js/components/todo-app.js', 23 | 'js/app.js', 24 | '<%= cancompile.dist.dest %>' // The compiled views 25 | ], 26 | dest: 'dist/production.js' 27 | } 28 | }, 29 | uglify: { 30 | dist: { 31 | files: { 32 | 'dist/production.min.js': ['<%= concat.dist.dest %>'] 33 | } 34 | } 35 | } 36 | }); 37 | 38 | // Default task. 39 | grunt.registerTask('default', ['cancompile', 'concat', 'uglify']); 40 | 41 | grunt.loadTasks('../tasks'); 42 | grunt.loadNpmTasks('grunt-contrib-uglify'); 43 | grunt.loadNpmTasks('grunt-contrib-concat'); 44 | }; 45 | -------------------------------------------------------------------------------- /example/bower.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "todomvc-canjs", 3 | "version": "0.0.0", 4 | "dependencies": { 5 | "jquery": "~2.0.0", 6 | "canjs": "~2.1.0", 7 | "canjs-localstorage": "~0.2.0", 8 | "todomvc-common": "~0.1.6" 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /example/development.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CanJS • TodoMVC 6 | 7 | 8 | 9 |
10 |
11 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | -------------------------------------------------------------------------------- /example/dist/production.min.js: -------------------------------------------------------------------------------- 1 | !function(){"use strict";function a(){"tastejs.github.io"===location.hostname&&(location.href=location.href.replace("tastejs.github.io/todomvc","todomvc.com"))}function b(){var a;return[/labs/,/\w*-examples/].forEach(function(b){var c=location.href.match(b);!a&&c&&(a=location.href.indexOf(c))}),location.href.substr(0,a)}function c(a,c){if(!location.host)return console.info("Miss the info bar? Run TodoMVC from a server to avoid a cross-origin error.");var d=new XMLHttpRequest;d.open("GET",b()+a,!0),d.send(),d.onload=function(){200===d.status&&c&&c(d.responseText)}}function d(a,b){if(!(this instanceof d))return new d(a,b);var c,e;if("object"!=typeof a)try{a=JSON.parse(a)}catch(f){return}b&&(c=b.template,e=b.framework),!c&&a.templates&&(c=a.templates.todomvc),!e&&document.querySelector("[data-framework]")&&(e=document.querySelector("[data-framework]").getAttribute("data-framework")),c&&a[e]&&(this.frameworkJSON=a[e],this.template=c,this.append())}var e=function(a){a.defaults=function(a){if(!a)return a;for(var b=1,c=arguments.length;c>b;b++){var d=arguments[b];if(d)for(var e in d)null==a[e]&&(a[e]=d[e])}return a},a.templateSettings={evaluate:/<%([\s\S]+?)%>/g,interpolate:/<%=([\s\S]+?)%>/g,escape:/<%-([\s\S]+?)%>/g};var b=/(.)^/,c={"'":"'","\\":"\\","\r":"r","\n":"n"," ":"t","\u2028":"u2028","\u2029":"u2029"},d=/\\|'|\r|\n|\t|\u2028|\u2029/g;return a.template=function(e,f,g){var h;g=a.defaults({},g,a.templateSettings);var i=new RegExp([(g.escape||b).source,(g.interpolate||b).source,(g.evaluate||b).source].join("|")+"|$","g"),j=0,k="__p+='";e.replace(i,function(a,b,f,g,h){return k+=e.slice(j,h).replace(d,function(a){return"\\"+c[a]}),b&&(k+="'+\n((__t=("+b+"))==null?'':_.escape(__t))+\n'"),f&&(k+="'+\n((__t=("+f+"))==null?'':__t)+\n'"),g&&(k+="';\n"+g+"\n__p+='"),j=h+a.length,a}),k+="';\n",g.variable||(k="with(obj||{}){\n"+k+"}\n"),k="var __t,__p='',__j=Array.prototype.join,print=function(){__p+=__j.call(arguments,'');};\n"+k+"return __p;\n";try{h=new Function(g.variable||"obj","_",k)}catch(l){throw l.source=k,l}if(f)return h(f,a);var m=function(b){return h.call(this,b,a)};return m.source="function("+(g.variable||"obj")+"){\n"+k+"}",m},a}({});"todomvc.com"===location.hostname&&(window._gaq=[["_setAccount","UA-31081062-1"],["_trackPageview"]],function(a,b){var c=a.createElement(b),d=a.getElementsByTagName(b)[0];c.src="//www.google-analytics.com/ga.js",d.parentNode.insertBefore(c,d)}(document,"script")),d.prototype.append=function(){var a=document.createElement("aside");a.innerHTML=e.template(this.template,this.frameworkJSON),a.className="learn";var c=a.querySelectorAll(".demo-link");Array.prototype.forEach.call(c,function(a){a.setAttribute("href",b()+a.getAttribute("href"))}),document.body.className=(document.body.className+" learn-bar").trim(),document.body.insertAdjacentHTML("afterBegin",a.outerHTML)},a(),c("learn.json",d)}(),function(a,b){function c(a){var b=a.length,c=fb.type(a);return fb.isWindow(a)?!1:1===a.nodeType&&b?!0:"array"===c||"function"!==c&&(0===b||"number"==typeof b&&b>0&&b-1 in a)}function d(a){var b=ob[a]={};return fb.each(a.match(hb)||[],function(a,c){b[c]=!0}),b}function e(){Object.defineProperty(this.cache={},0,{get:function(){return{}}}),this.expando=fb.expando+Math.random()}function f(a,c,d){var e;if(d===b&&1===a.nodeType)if(e="data-"+c.replace(sb,"-$1").toLowerCase(),d=a.getAttribute(e),"string"==typeof d){try{d="true"===d?!0:"false"===d?!1:"null"===d?null:+d+""===d?+d:rb.test(d)?JSON.parse(d):d}catch(f){}pb.set(a,c,d)}else d=b;return d}function g(){return!0}function h(){return!1}function i(){try{return T.activeElement}catch(a){}}function j(a,b){for(;(a=a[b])&&1!==a.nodeType;);return a}function k(a,b,c){if(fb.isFunction(b))return fb.grep(a,function(a,d){return!!b.call(a,d,a)!==c});if(b.nodeType)return fb.grep(a,function(a){return a===b!==c});if("string"==typeof b){if(Cb.test(b))return fb.filter(b,a,c);b=fb.filter(b,a)}return fb.grep(a,function(a){return bb.call(b,a)>=0!==c})}function l(a,b){return fb.nodeName(a,"table")&&fb.nodeName(1===b.nodeType?b:b.firstChild,"tr")?a.getElementsByTagName("tbody")[0]||a.appendChild(a.ownerDocument.createElement("tbody")):a}function m(a){return a.type=(null!==a.getAttribute("type"))+"/"+a.type,a}function n(a){var b=Nb.exec(a.type);return b?a.type=b[1]:a.removeAttribute("type"),a}function o(a,b){for(var c=a.length,d=0;c>d;d++)qb.set(a[d],"globalEval",!b||qb.get(b[d],"globalEval"))}function p(a,b){var c,d,e,f,g,h,i,j;if(1===b.nodeType){if(qb.hasData(a)&&(f=qb.access(a),g=qb.set(b,f),j=f.events)){delete g.handle,g.events={};for(e in j)for(c=0,d=j[e].length;d>c;c++)fb.event.add(b,e,j[e][c])}pb.hasData(a)&&(h=pb.access(a),i=fb.extend({},h),pb.set(b,i))}}function q(a,c){var d=a.getElementsByTagName?a.getElementsByTagName(c||"*"):a.querySelectorAll?a.querySelectorAll(c||"*"):[];return c===b||c&&fb.nodeName(a,c)?fb.merge([a],d):d}function r(a,b){var c=b.nodeName.toLowerCase();"input"===c&&Kb.test(a.type)?b.checked=a.checked:("input"===c||"textarea"===c)&&(b.defaultValue=a.defaultValue)}function s(a,b){if(b in a)return b;for(var c=b.charAt(0).toUpperCase()+b.slice(1),d=b,e=_b.length;e--;)if(b=_b[e]+c,b in a)return b;return d}function t(a,b){return a=b||a,"none"===fb.css(a,"display")||!fb.contains(a.ownerDocument,a)}function u(b){return a.getComputedStyle(b,null)}function v(a,b){for(var c,d,e,f=[],g=0,h=a.length;h>g;g++)d=a[g],d.style&&(f[g]=qb.get(d,"olddisplay"),c=d.style.display,b?(f[g]||"none"!==c||(d.style.display=""),""===d.style.display&&t(d)&&(f[g]=qb.access(d,"olddisplay",z(d.nodeName)))):f[g]||(e=t(d),(c&&"none"!==c||!e)&&qb.set(d,"olddisplay",e?c:fb.css(d,"display"))));for(g=0;h>g;g++)d=a[g],d.style&&(b&&"none"!==d.style.display&&""!==d.style.display||(d.style.display=b?f[g]||"":"none"));return a}function w(a,b,c){var d=Ub.exec(b);return d?Math.max(0,d[1]-(c||0))+(d[2]||"px"):b}function x(a,b,c,d,e){for(var f=c===(d?"border":"content")?4:"width"===b?1:0,g=0;4>f;f+=2)"margin"===c&&(g+=fb.css(a,c+$b[f],!0,e)),d?("content"===c&&(g-=fb.css(a,"padding"+$b[f],!0,e)),"margin"!==c&&(g-=fb.css(a,"border"+$b[f]+"Width",!0,e))):(g+=fb.css(a,"padding"+$b[f],!0,e),"padding"!==c&&(g+=fb.css(a,"border"+$b[f]+"Width",!0,e)));return g}function y(a,b,c){var d=!0,e="width"===b?a.offsetWidth:a.offsetHeight,f=u(a),g=fb.support.boxSizing&&"border-box"===fb.css(a,"boxSizing",!1,f);if(0>=e||null==e){if(e=Qb(a,b,f),(0>e||null==e)&&(e=a.style[b]),Vb.test(e))return e;d=g&&(fb.support.boxSizingReliable||e===a.style[b]),e=parseFloat(e)||0}return e+x(a,b,c||(g?"border":"content"),d,f)+"px"}function z(a){var b=T,c=Xb[a];return c||(c=A(a,b),"none"!==c&&c||(Rb=(Rb||fb("