diff --git a/Gruntfile.js b/Gruntfile.js index 61efa3517..7dd004dc4 100644 --- a/Gruntfile.js +++ b/Gruntfile.js @@ -7,7 +7,8 @@ module.exports = function(grunt) { 'lib/static/main.js': ['lib/GUI/js/main.js'] }, options: { - debug: true + debug: true, + transform: ['browserify-handlebars'] } } }, @@ -22,7 +23,7 @@ module.exports = function(grunt) { } }, watch: { - files: [ "lib/GUI/js/**/*", "lib/GUI/css/**/*"], + files: [ "lib/GUI/**/*"], tasks: [ 'default' ] } }); diff --git a/lib/GUI/css/main.less b/lib/GUI/css/main.less index a39a29544..9691fc688 100644 --- a/lib/GUI/css/main.less +++ b/lib/GUI/css/main.less @@ -1,3 +1,28 @@ -body { - +@import "../../../node_modules/helpers.less/helpers.less"; + +/*** Main Styles ***/ +h1 { + text-align: center; + + a, a:visited { + color: black; + text-decoration: none; + } + + a:hover { + text-decoration: underline; + } +} + +/*** Setup ***/ + + +/*** Package Entries ***/ +.entry { + background: #EEE; +} + +/*** Search Results ***/ +.state-search #standard-content { + display: none; } \ No newline at end of file diff --git a/lib/GUI/entry.handlebars b/lib/GUI/entry.handlebars new file mode 100644 index 000000000..9ccb307dd --- /dev/null +++ b/lib/GUI/entry.handlebars @@ -0,0 +1,5 @@ +<article class='entry'> + <h3>{{ name }} <small>v{{ version }}</small></h3> + <div>User: {{ _npmUser.name }}</div> + <p>{{ description }}</p> +</article> \ No newline at end of file diff --git a/lib/GUI/index.handlebars b/lib/GUI/index.handlebars index 0b1f058c6..1c1df7fd4 100644 --- a/lib/GUI/index.handlebars +++ b/lib/GUI/index.handlebars @@ -7,28 +7,33 @@ <link rel="stylesheet" type="text/css" href="/-/static/main.css"> </head> <body> - <h1><a href='/'>{{ name }}</a></h1> + <div id='content'> + <h1><a href='/'>{{ name }}</a></h1> - <form> - <input type='search' name='q' /> - <button>Search</button> - </form> + <form id='search-form'> + <input type='search' name='q' /> + <button>Search</button> + </form> - <h2>Setup:</h2> - <code> - npm set registry {{ baseUrl }}<br> - npm adduser --registry {{ baseUrl }} - </code> + <div id='search-results'></div> - <h2>Packages:</h2> - {{#each packages}} - <article> - <h3>{{ name }} <small>v{{ version }}</small></h3> - <div>User: {{ _npmUser.name }}</div> - <p>{{ description }}</p> - </article> - {{/each}} + <div id='standard-content'> + <article id='setup'> + <h2>Setup:</h2> + <code> + npm set registry {{ baseUrl }}<br> + npm adduser --registry {{ baseUrl }} + </code> + </article> - <script type='text/javascript' src='/-/static/main.js'></script> + <h2>Available Packages:</h2> + {{#each packages}} + {{> entry}} + {{/each}} + + <script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.0/jquery.min.js"></script> + <script type='text/javascript' src='/-/static/main.js'></script> + </div> + </div> </body> </html> diff --git a/lib/GUI/js/main.js b/lib/GUI/js/main.js index e69de29bb..632ae0a12 100644 --- a/lib/GUI/js/main.js +++ b/lib/GUI/js/main.js @@ -0,0 +1,43 @@ +var $ = require('unopinionate').selector, + template = require('../entry.handlebars'); + +$(function() { + var $form = $('#search-form'), + $input = $form.find('[type="search"]'), + $searchResults = $("#search-results"), + $body = $('body'), + request; + + $form.bind('submit keyup', function(e) { + e.preventDefault(); + + var q = $input.val(); + + $body.addClass('state-search'); + + if(q) { + if(request) { + request.abort(); + } + + request = $.getJSON('/-/search/' + q, function(results) { + if(results.length) { + var html = ''; + + $.each(results, function(i, package) { + html += template(package); + }); + + $searchResults.html(html); + } + else { + $searchResults.html("<div class='search-no-results'>No Results</div>"); + } + }); + } + else { + $searchResults.html(''); + $body.removeClass('state-search'); + } + }); +}); diff --git a/lib/index.js b/lib/index.js index f392a753b..7bf9abda5 100644 --- a/lib/index.js +++ b/lib/index.js @@ -14,6 +14,7 @@ var express = require('express') , Handlebars = require('handlebars') , fs = require('fs') , localList = require('./local-list') + , Search = require('./search') , _ = require('underscore'); function match(regexp) { @@ -29,6 +30,7 @@ function match(regexp) { module.exports = function(config_hash) { var config = new Config(config_hash) , storage = new Storage(config) + , search = new Search(storage); var can = function(action) { return function(req, res, next) { @@ -122,8 +124,10 @@ module.exports = function(config_hash) { console.log(d) }) })*/ - + + Handlebars.registerPartial('entry', fs.readFileSync(require.resolve('./GUI/entry.handlebars'), 'utf8')); var template = Handlebars.compile(fs.readFileSync(require.resolve('./GUI/index.handlebars'), 'utf8')); + app.get('/', can('access'), function(req, res, next) { res.setHeader('Content-Type', 'text/html'); @@ -236,6 +240,32 @@ module.exports = function(config_hash) { }); }); + // Search + app.get('/-/search/:query', function(req, res, next) { + var results = search.query(req.params.query), + packages = []; + + var getData = function(i) { + storage.get_package(results[i].ref, function(err, package) { + packages.push(package.versions[package['dist-tags'].latest]); + + if(i >= results.length - 1) { + res.send(packages); + } + else { + getData(i + 1); + } + }); + }; + + if(results.length) { + getData(0); + } + else { + res.send([]); + } + }); + // tagging a package app.put('/:package/:tag', can('publish'), media('application/json'), function(req, res, next) { if (typeof(req.body) !== 'string') return next('route') diff --git a/lib/search.js b/lib/search.js index 5c59b4d87..840fc8d3b 100644 --- a/lib/search.js +++ b/lib/search.js @@ -1,35 +1,40 @@ var lunr = require('lunr') , localList = require('./local-list'); -var Search = function() { +var Search = function(storage) { + this.storage = storage; + this.index = lunr(function () { this.field('name', {boost: 10}); this.field('description'); this.field('author'); }); - this.id = 0; - - var packages = storage.get_local() - , i = packages.length; - - while(i--) { - this.index(packages[i]); - } + this.reindex(); }; Search.prototype = { query: function(q) { - return index.search(q); + return this.index.search(q); }, - index: function(package) { + add: function(package) { this.index.add({ - id: ++this.id, - title: package.name, + id: package.name, + name: package.name, description: package.description, author: package._npmUser.name }); + }, + reindex: function() { + var self = this; + this.storage.get_local(function(err, packages) { + var i = packages.length; + + while(i--) { + self.add(packages[i]); + } + }); } }; -module.exports = new Search(); \ No newline at end of file +module.exports = Search; \ No newline at end of file diff --git a/lib/static/main.css b/lib/static/main.css index e69de29bb..a70e4dcd9 100644 --- a/lib/static/main.css +++ b/lib/static/main.css @@ -0,0 +1,22 @@ +/*** Main Styles ***/ +h1 { + text-align: center; +} +h1 a, +h1 a:visited { + color: black; + text-decoration: none; +} +h1 a:hover { + text-decoration: underline; +} +/*** Setup ***/ +/*** Package Entries ***/ +.entry { + background: #EEE; +} +/*** Search Results ***/ +.state-search #standard-content { + display: none; +} +/*# sourceMappingURL=data:application/json,%7B%22version%22%3A3%2C%22sources%22%3A%5B%22lib%2FGUI%2Fcss%2Fmain.less%22%5D%2C%22names%22%3A%5B%5D%2C%22mappings%22%3A%22%3BAAGA%3BEACC%2CkBAAA%3B%3BAADD%2CEAGC%3BAAHD%2CEAGI%2CEAAC%3BEACH%2CYAAA%3BEACA%2CqBAAA%3B%3BAALF%2CEAQC%2CEAAC%3BEACA%2C0BAAA%3B%3B%3B%3BAAQF%3BEACC%2CgBAAA%3B%3B%3BAAID%2CaAAc%3BEACb%2CaAAA%22%7D */ \ No newline at end of file diff --git a/lib/static/main.js b/lib/static/main.js index 8a7bd83c5..ea6e5f435 100644 --- a/lib/static/main.js +++ b/lib/static/main.js @@ -1,3 +1,572 @@ (function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);throw new Error("Cannot find module '"+o+"'")}var f=n[o]={exports:{}};t[o][0].call(f.exports,function(e){var n=t[o][1][e];return s(n?n:e)},f,f.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o<r.length;o++)s(r[o]);return s})({1:[function(require,module,exports){ +var templater = require("handlebars/runtime").default.template;module.exports = templater(function (Handlebars,depth0,helpers,partials,data) { + this.compilerInfo = [4,'>= 1.0.0']; +helpers = this.merge(helpers, Handlebars.helpers); data = data || {}; + var buffer = "", stack1, helper, functionType="function", escapeExpression=this.escapeExpression; -},{}]},{},[1]) \ No newline at end of file + + buffer += "<article class='entry'>\n <h3>"; + if (helper = helpers.name) { stack1 = helper.call(depth0, {hash:{},data:data}); } + else { helper = (depth0 && depth0.name); stack1 = typeof helper === functionType ? helper.call(depth0, {hash:{},data:data}) : helper; } + buffer += escapeExpression(stack1) + + " <small>v"; + if (helper = helpers.version) { stack1 = helper.call(depth0, {hash:{},data:data}); } + else { helper = (depth0 && depth0.version); stack1 = typeof helper === functionType ? helper.call(depth0, {hash:{},data:data}) : helper; } + buffer += escapeExpression(stack1) + + "</small></h3>\n <div>User: " + + escapeExpression(((stack1 = ((stack1 = (depth0 && depth0._npmUser)),stack1 == null || stack1 === false ? stack1 : stack1.name)),typeof stack1 === functionType ? stack1.apply(depth0) : stack1)) + + "</div>\n <p>"; + if (helper = helpers.description) { stack1 = helper.call(depth0, {hash:{},data:data}); } + else { helper = (depth0 && depth0.description); stack1 = typeof helper === functionType ? helper.call(depth0, {hash:{},data:data}) : helper; } + buffer += escapeExpression(stack1) + + "</p>\n</article>"; + return buffer; + }); +},{"handlebars/runtime":9}],2:[function(require,module,exports){ +var $ = require('unopinionate').selector, + template = require('../entry.handlebars'); + +$(function() { + var $form = $('#search-form'), + $input = $form.find('[type="search"]'), + $searchResults = $("#search-results"), + $body = $('body'), + request; + + $form.bind('submit keyup', function(e) { + e.preventDefault(); + + var q = $input.val(); + + $body.addClass('state-search'); + + if(q) { + if(request) { + request.abort(); + } + + request = $.getJSON('/-/search/' + q, function(results) { + if(results.length) { + var html = ''; + + $.each(results, function(i, package) { + html += template(package); + }); + + $searchResults.html(html); + } + else { + $searchResults.html("<div class='search-no-results'>No Results</div>"); + } + }); + } + else { + $searchResults.html(''); + $body.removeClass('state-search'); + } + }); +}); + +},{"../entry.handlebars":1,"unopinionate":10}],3:[function(require,module,exports){ +"use strict"; +/*globals Handlebars: true */ +var base = require("./handlebars/base"); + +// Each of these augment the Handlebars object. No need to setup here. +// (This is done to easily share code between commonjs and browse envs) +var SafeString = require("./handlebars/safe-string")["default"]; +var Exception = require("./handlebars/exception")["default"]; +var Utils = require("./handlebars/utils"); +var runtime = require("./handlebars/runtime"); + +// For compatibility and usage outside of module systems, make the Handlebars object a namespace +var create = function() { + var hb = new base.HandlebarsEnvironment(); + + Utils.extend(hb, base); + hb.SafeString = SafeString; + hb.Exception = Exception; + hb.Utils = Utils; + + hb.VM = runtime; + hb.template = function(spec) { + return runtime.template(spec, hb); + }; + + return hb; +}; + +var Handlebars = create(); +Handlebars.create = create; + +exports["default"] = Handlebars; +},{"./handlebars/base":4,"./handlebars/exception":5,"./handlebars/runtime":6,"./handlebars/safe-string":7,"./handlebars/utils":8}],4:[function(require,module,exports){ +"use strict"; +var Utils = require("./utils"); +var Exception = require("./exception")["default"]; + +var VERSION = "1.3.0"; +exports.VERSION = VERSION;var COMPILER_REVISION = 4; +exports.COMPILER_REVISION = COMPILER_REVISION; +var REVISION_CHANGES = { + 1: '<= 1.0.rc.2', // 1.0.rc.2 is actually rev2 but doesn't report it + 2: '== 1.0.0-rc.3', + 3: '== 1.0.0-rc.4', + 4: '>= 1.0.0' +}; +exports.REVISION_CHANGES = REVISION_CHANGES; +var isArray = Utils.isArray, + isFunction = Utils.isFunction, + toString = Utils.toString, + objectType = '[object Object]'; + +function HandlebarsEnvironment(helpers, partials) { + this.helpers = helpers || {}; + this.partials = partials || {}; + + registerDefaultHelpers(this); +} + +exports.HandlebarsEnvironment = HandlebarsEnvironment;HandlebarsEnvironment.prototype = { + constructor: HandlebarsEnvironment, + + logger: logger, + log: log, + + registerHelper: function(name, fn, inverse) { + if (toString.call(name) === objectType) { + if (inverse || fn) { throw new Exception('Arg not supported with multiple helpers'); } + Utils.extend(this.helpers, name); + } else { + if (inverse) { fn.not = inverse; } + this.helpers[name] = fn; + } + }, + + registerPartial: function(name, str) { + if (toString.call(name) === objectType) { + Utils.extend(this.partials, name); + } else { + this.partials[name] = str; + } + } +}; + +function registerDefaultHelpers(instance) { + instance.registerHelper('helperMissing', function(arg) { + if(arguments.length === 2) { + return undefined; + } else { + throw new Exception("Missing helper: '" + arg + "'"); + } + }); + + instance.registerHelper('blockHelperMissing', function(context, options) { + var inverse = options.inverse || function() {}, fn = options.fn; + + if (isFunction(context)) { context = context.call(this); } + + if(context === true) { + return fn(this); + } else if(context === false || context == null) { + return inverse(this); + } else if (isArray(context)) { + if(context.length > 0) { + return instance.helpers.each(context, options); + } else { + return inverse(this); + } + } else { + return fn(context); + } + }); + + instance.registerHelper('each', function(context, options) { + var fn = options.fn, inverse = options.inverse; + var i = 0, ret = "", data; + + if (isFunction(context)) { context = context.call(this); } + + if (options.data) { + data = createFrame(options.data); + } + + if(context && typeof context === 'object') { + if (isArray(context)) { + for(var j = context.length; i<j; i++) { + if (data) { + data.index = i; + data.first = (i === 0); + data.last = (i === (context.length-1)); + } + ret = ret + fn(context[i], { data: data }); + } + } else { + for(var key in context) { + if(context.hasOwnProperty(key)) { + if(data) { + data.key = key; + data.index = i; + data.first = (i === 0); + } + ret = ret + fn(context[key], {data: data}); + i++; + } + } + } + } + + if(i === 0){ + ret = inverse(this); + } + + return ret; + }); + + instance.registerHelper('if', function(conditional, options) { + if (isFunction(conditional)) { conditional = conditional.call(this); } + + // Default behavior is to render the positive path if the value is truthy and not empty. + // The `includeZero` option may be set to treat the condtional as purely not empty based on the + // behavior of isEmpty. Effectively this determines if 0 is handled by the positive path or negative. + if ((!options.hash.includeZero && !conditional) || Utils.isEmpty(conditional)) { + return options.inverse(this); + } else { + return options.fn(this); + } + }); + + instance.registerHelper('unless', function(conditional, options) { + return instance.helpers['if'].call(this, conditional, {fn: options.inverse, inverse: options.fn, hash: options.hash}); + }); + + instance.registerHelper('with', function(context, options) { + if (isFunction(context)) { context = context.call(this); } + + if (!Utils.isEmpty(context)) return options.fn(context); + }); + + instance.registerHelper('log', function(context, options) { + var level = options.data && options.data.level != null ? parseInt(options.data.level, 10) : 1; + instance.log(level, context); + }); +} + +var logger = { + methodMap: { 0: 'debug', 1: 'info', 2: 'warn', 3: 'error' }, + + // State enum + DEBUG: 0, + INFO: 1, + WARN: 2, + ERROR: 3, + level: 3, + + // can be overridden in the host environment + log: function(level, obj) { + if (logger.level <= level) { + var method = logger.methodMap[level]; + if (typeof console !== 'undefined' && console[method]) { + console[method].call(console, obj); + } + } + } +}; +exports.logger = logger; +function log(level, obj) { logger.log(level, obj); } + +exports.log = log;var createFrame = function(object) { + var obj = {}; + Utils.extend(obj, object); + return obj; +}; +exports.createFrame = createFrame; +},{"./exception":5,"./utils":8}],5:[function(require,module,exports){ +"use strict"; + +var errorProps = ['description', 'fileName', 'lineNumber', 'message', 'name', 'number', 'stack']; + +function Exception(message, node) { + var line; + if (node && node.firstLine) { + line = node.firstLine; + + message += ' - ' + line + ':' + node.firstColumn; + } + + var tmp = Error.prototype.constructor.call(this, message); + + // Unfortunately errors are not enumerable in Chrome (at least), so `for prop in tmp` doesn't work. + for (var idx = 0; idx < errorProps.length; idx++) { + this[errorProps[idx]] = tmp[errorProps[idx]]; + } + + if (line) { + this.lineNumber = line; + this.column = node.firstColumn; + } +} + +Exception.prototype = new Error(); + +exports["default"] = Exception; +},{}],6:[function(require,module,exports){ +"use strict"; +var Utils = require("./utils"); +var Exception = require("./exception")["default"]; +var COMPILER_REVISION = require("./base").COMPILER_REVISION; +var REVISION_CHANGES = require("./base").REVISION_CHANGES; + +function checkRevision(compilerInfo) { + var compilerRevision = compilerInfo && compilerInfo[0] || 1, + currentRevision = COMPILER_REVISION; + + if (compilerRevision !== currentRevision) { + if (compilerRevision < currentRevision) { + var runtimeVersions = REVISION_CHANGES[currentRevision], + compilerVersions = REVISION_CHANGES[compilerRevision]; + throw new Exception("Template was precompiled with an older version of Handlebars than the current runtime. "+ + "Please update your precompiler to a newer version ("+runtimeVersions+") or downgrade your runtime to an older version ("+compilerVersions+")."); + } else { + // Use the embedded version info since the runtime doesn't know about this revision yet + throw new Exception("Template was precompiled with a newer version of Handlebars than the current runtime. "+ + "Please update your runtime to a newer version ("+compilerInfo[1]+")."); + } + } +} + +exports.checkRevision = checkRevision;// TODO: Remove this line and break up compilePartial + +function template(templateSpec, env) { + if (!env) { + throw new Exception("No environment passed to template"); + } + + // Note: Using env.VM references rather than local var references throughout this section to allow + // for external users to override these as psuedo-supported APIs. + var invokePartialWrapper = function(partial, name, context, helpers, partials, data) { + var result = env.VM.invokePartial.apply(this, arguments); + if (result != null) { return result; } + + if (env.compile) { + var options = { helpers: helpers, partials: partials, data: data }; + partials[name] = env.compile(partial, { data: data !== undefined }, env); + return partials[name](context, options); + } else { + throw new Exception("The partial " + name + " could not be compiled when running in runtime-only mode"); + } + }; + + // Just add water + var container = { + escapeExpression: Utils.escapeExpression, + invokePartial: invokePartialWrapper, + programs: [], + program: function(i, fn, data) { + var programWrapper = this.programs[i]; + if(data) { + programWrapper = program(i, fn, data); + } else if (!programWrapper) { + programWrapper = this.programs[i] = program(i, fn); + } + return programWrapper; + }, + merge: function(param, common) { + var ret = param || common; + + if (param && common && (param !== common)) { + ret = {}; + Utils.extend(ret, common); + Utils.extend(ret, param); + } + return ret; + }, + programWithDepth: env.VM.programWithDepth, + noop: env.VM.noop, + compilerInfo: null + }; + + return function(context, options) { + options = options || {}; + var namespace = options.partial ? options : env, + helpers, + partials; + + if (!options.partial) { + helpers = options.helpers; + partials = options.partials; + } + var result = templateSpec.call( + container, + namespace, context, + helpers, + partials, + options.data); + + if (!options.partial) { + env.VM.checkRevision(container.compilerInfo); + } + + return result; + }; +} + +exports.template = template;function programWithDepth(i, fn, data /*, $depth */) { + var args = Array.prototype.slice.call(arguments, 3); + + var prog = function(context, options) { + options = options || {}; + + return fn.apply(this, [context, options.data || data].concat(args)); + }; + prog.program = i; + prog.depth = args.length; + return prog; +} + +exports.programWithDepth = programWithDepth;function program(i, fn, data) { + var prog = function(context, options) { + options = options || {}; + + return fn(context, options.data || data); + }; + prog.program = i; + prog.depth = 0; + return prog; +} + +exports.program = program;function invokePartial(partial, name, context, helpers, partials, data) { + var options = { partial: true, helpers: helpers, partials: partials, data: data }; + + if(partial === undefined) { + throw new Exception("The partial " + name + " could not be found"); + } else if(partial instanceof Function) { + return partial(context, options); + } +} + +exports.invokePartial = invokePartial;function noop() { return ""; } + +exports.noop = noop; +},{"./base":4,"./exception":5,"./utils":8}],7:[function(require,module,exports){ +"use strict"; +// Build out our basic SafeString type +function SafeString(string) { + this.string = string; +} + +SafeString.prototype.toString = function() { + return "" + this.string; +}; + +exports["default"] = SafeString; +},{}],8:[function(require,module,exports){ +"use strict"; +/*jshint -W004 */ +var SafeString = require("./safe-string")["default"]; + +var escape = { + "&": "&", + "<": "<", + ">": ">", + '"': """, + "'": "'", + "`": "`" +}; + +var badChars = /[&<>"'`]/g; +var possible = /[&<>"'`]/; + +function escapeChar(chr) { + return escape[chr] || "&"; +} + +function extend(obj, value) { + for(var key in value) { + if(Object.prototype.hasOwnProperty.call(value, key)) { + obj[key] = value[key]; + } + } +} + +exports.extend = extend;var toString = Object.prototype.toString; +exports.toString = toString; +// Sourced from lodash +// https://github.com/bestiejs/lodash/blob/master/LICENSE.txt +var isFunction = function(value) { + return typeof value === 'function'; +}; +// fallback for older versions of Chrome and Safari +if (isFunction(/x/)) { + isFunction = function(value) { + return typeof value === 'function' && toString.call(value) === '[object Function]'; + }; +} +var isFunction; +exports.isFunction = isFunction; +var isArray = Array.isArray || function(value) { + return (value && typeof value === 'object') ? toString.call(value) === '[object Array]' : false; +}; +exports.isArray = isArray; + +function escapeExpression(string) { + // don't escape SafeStrings, since they're already safe + if (string instanceof SafeString) { + return string.toString(); + } else if (!string && string !== 0) { + return ""; + } + + // Force a string conversion as this will be done by the append regardless and + // the regex test will do this transparently behind the scenes, causing issues if + // an object's to string has escaped characters in it. + string = "" + string; + + if(!possible.test(string)) { return string; } + return string.replace(badChars, escapeChar); +} + +exports.escapeExpression = escapeExpression;function isEmpty(value) { + if (!value && value !== 0) { + return true; + } else if (isArray(value) && value.length === 0) { + return true; + } else { + return false; + } +} + +exports.isEmpty = isEmpty; +},{"./safe-string":7}],9:[function(require,module,exports){ +// Create a simple path alias to allow browserify to resolve +// the runtime on a supported path. +module.exports = require('./dist/cjs/handlebars.runtime'); + +},{"./dist/cjs/handlebars.runtime":3}],10:[function(require,module,exports){ +(function (global){ +(function(root) { + var unopinionate = { + selector: root.jQuery || root.Zepto || root.ender || root.$, + template: root.Handlebars || root.Mustache + }; + + /*** Export ***/ + + //AMD + if(typeof define === 'function' && define.amd) { + define([], function() { + return unopinionate; + }); + } + //CommonJS + else if(typeof module.exports !== 'undefined') { + module.exports = unopinionate; + } + //Global + else { + root.unopinionate = unopinionate; + } +})(typeof window != 'undefined' ? window : global); + +}).call(this,typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {}) +},{}]},{},[2]) \ No newline at end of file diff --git a/package.json b/package.json index 74956581c..049fdde0f 100644 --- a/package.json +++ b/package.json @@ -20,25 +20,29 @@ "commander": ">= 2.1.0", "cookies": ">= 0.3.8", "express": "3.4.x", - "handlebars": "^2.0.0-alpha.2", + "handlebars": "1.x.x", + "helpers.less": "git://github.com/bpeacock/helpers.less.git", "js-yaml": ">= 3.0.1", "lunr": "^0.5.2", "minimatch": ">= 0.2.14", "mkdirp": ">= 0.3.5", "request": ">= 2.31.0", "semver": ">= 2.2.1", - "underscore": "^1.6.0" + "underscore": "^1.6.0", + "unopinionate": "0.0.4" }, "optionalDependencies": { "fs-ext": ">= 0.3.2" }, "devDependencies": { "browserify": "^3.46.0", + "browserify-handlebars": "~0.2.0", "eslint": ">= 0.4.2", "grunt": "^0.4.4", "grunt-browserify": "^2.0.8", "grunt-contrib-less": "^0.11.0", "grunt-contrib-watch": "^0.6.1", + "handlebars": "^1.3.0", "mocha": ">= 1.17.0", "rimraf": ">= 2.2.5" },