<commit_before>
kff.ServiceContainer = kff.createClass(
{
	statics:
	{
		CONFIG_CONSTRUCTOR: 'construct',
		singleParamRegex: /^%[^%]+%$/g,
		multipleParamsRegex: /%([^%]+)%/g,
		serviceNameRegex: /^[^\s#]*/
	}
},
/** @lends kff.ServiceContainer.prototype */
{
	/**
	 * Simple dependency injection (or service) container class.
	 * @constructs
	 * @param {Object} config Configuration object
	 */
	constructor: function(config, loader)
	{
		this.config = config || { parameters: {}, services: {} };
		this.services = {};
		this.cachedParams = {};
		if(loader) this.loadService = loader;
	},

	/**
	 * Returns instance of service class.
	 * @param {string} service Service name (service config to be found in config.services[service])
	 * @param {Array} argsExtend Array to overload default arguments array (optional)
	 * @returns {Object} Instance of service
	 */
	getService: function(serviceName, argsExtend)
	{
		var serviceConfig;
		if(!this.config.services[serviceName])
		{
			serviceConfig = this.getServiceConfigAnnotation(serviceName);
			if(serviceConfig) this.config.services[serviceName] = serviceConfig;
			else throw new Error('Service ' + serviceName + ' not defined');
		}
		if(this.config.services[serviceName].shared)
		{
			if(typeof this.services[serviceName] === 'undefined') this.services[serviceName] = this.createService(serviceName, argsExtend);
			return this.services[serviceName];
		}
		return this.createService(serviceName, argsExtend);
	},

	/**
	 * Checks if given serviceName exists in container declaration
	 * @param {string} serviceName Service name
	 * @returns {boolean} True if service exists, false otherwise
	 */
	hasService: function(serviceName)
	{
		if(this.config.services.hasOwnProperty(serviceName)) return true;
		else {
			var serviceConfig = this.getServiceConfigAnnotation(serviceName);
			if(serviceConfig)
			{
				this.config.services[serviceName] = serviceConfig;
				return true;
			}
		}
		return false;
	},

	/**
	 * Creates instance of service.
	 *
	 * If second argument is passed, then it will be used to overload constructor arguments.
	 * If items at the same index are both objects, then the second one will bee deep-mixed into
	 * the first one resulting in a new object (i.e. the config args won't be overwritten).
	 *
	 * @param {string} serviceName Name of service to be instantiated
	 * @param {Array} argsExtend Array to overload default arguments array (optional)
	 * @returns {Object} Instance of service
	 */
	createService: function(serviceName, argsExtend)
	{
		var serviceConfig, Ctor, Temp, service, ret, i, l, args, argsExtended, calls;

		serviceConfig = this.config.services[serviceName];

		Ctor = this.getServiceConstructor(serviceName);

		if(typeof Ctor !== 'function' || serviceConfig.type === 'function') return Ctor;

		if(serviceConfig.type !== 'factory')
		{
			Temp = function(){};
			Temp.prototype = Ctor.prototype;
			service = new Temp();
		}

		args = this.resolveParameters(serviceConfig.args || []);
		if(argsExtend && argsExtend instanceof Array)
		{
			argsExtended = [];
			for(i = 0, l = argsExtend.length; i < l; i++)
			{
				if(argsExtend[i] !== undefined)
				{
					if(kff.isPlainObject(args[i]) && kff.isPlainObject(argsExtend[i])) argsExtended[i] = kff.mixins({}, args[i], argsExtend[i]);
					else argsExtended[i] = argsExtend[i];
				}
				else argsExtended[i] = args[i];
			}
			args = argsExtended;
		}

		if(serviceConfig.type === 'factory')
		{
			service = Ctor.apply(null, args);
		}
		else
		{
			ret = Ctor.apply(service, args);
			if(Object(ret) === ret) service = ret;
		}

		calls = serviceConfig.calls;
		if(calls instanceof Array)
		{
			for(i = 0, l = calls.length; i < l; i++)
			{
				service[calls[i].method].apply(service, this.resolveParameters(calls[i].args));
			}
		}
		return service;
	},

	/**
	 * Returns constructor function for given service name.
	 * @param {string} serviceName Service name
	 * @returns {function} Constructor function for service
	 */
	getServiceConstructor: function(serviceName)
	{
		var serviceConfig, ctor, construct = kff.ServiceContainer.CONFIG_CONSTRUCTOR, type, name, serviceObject;
		serviceConfig = this.config.services[serviceName];
		if(!serviceConfig)
		{
			serviceConfig = this.getServiceConfigAnnotation(serviceName);
			if(!serviceConfig) return null;
			else this.config.services[serviceName] = serviceConfig;
		}

		if(serviceConfig.construct) construct = serviceConfig.construct;
		else construct = serviceName;

		if(!serviceConfig.hasOwnProperty('serviceObject'))
		{
			if(typeof construct === 'string')
			{
				serviceConfig['serviceObject'] = this.loadService(construct);
			}
			else serviceConfig['serviceObject'] = construct;
			if(!serviceConfig['serviceObject']) return null;
		}

		return serviceConfig['serviceObject'];
	},

	/**
	 * Returns configuration object of a service from its constructor (function).
	 * @param  {string} serviceName Name of service
	 * @return {object}             Service configuration object
	 */
	getServiceConfigAnnotation: function(serviceName)
	{
		var serviceConfig = {};
		var ctor = this.loadService(serviceName);
		if(typeof ctor === 'function')
		{
			if('service' in ctor && kff.isPlainObject(ctor.service)) serviceConfig = ctor.service;
			serviceConfig.serviceObject = ctor;
			return serviceConfig;
		}
		else if(ctor)
		{
			serviceConfig.serviceObject = ctor;
			return serviceConfig;
		}
		return null;
	},

	/**
	 * Evaluates parameter defined in container configuration.
	 *
	 * Parameter could be:
	 *
	 * - a string - see below
	 * - an Array or Object - iterates over properties and evaluates them recursively
	 *
	 * String parameters refers to parameters defined in config.parameters section
	 * If parameter is a string, it could have these special chars:
	 * '@serviceName' - resolves to instance of service
	 * '%parameterName%' - resolves to reference to parameter parameterName
	 * '%someParameter% some %otherParameter% some more string' - resolves to string with 'inner parameters' resolved to strings as well
	 *
	 * @param {string|Array|Object} params Parameters to be resolved
	 * @returns {mixed} Resolved parameter value
	 */
	resolveParameters: function(params)
	{
		var ret, i, l, config;

		config = this.config;

		if(typeof params === 'string')
		{
			if(params.indexOf('@@') === 0)
			{
				params = params.slice(2);
				if(params.length === 0) ret = null;
				else ret = this.createServiceFactory(params);
			}
			else if(params.charAt(0) === '@')
			{
				params = params.slice(1);
				if(params.length === 0) ret = this;
				else ret = this.getService(params);
			}
			else if(this.cachedParams[params] !== undefined) ret = this.cachedParams[params];
			else
			{
				if(params.search(kff.ServiceContainer.singleParamRegex) !== -1)
				{
					ret = config.parameters[params.slice(1, -1)];
				}
				else
				{
					ret = params.replace('%%', 'escpersign');
					ret = ret.replace(kff.ServiceContainer.multipleParamsRegex, function(match, p1)
					{
						if(config.parameters[p1]) return config.parameters[p1];
						else return '';
					});
					ret = ret.replace('escpersign', '%');
				}
				this.cachedParams[params] = ret;
			}
		}
		else if(params instanceof Array)
		{
			ret = [];
			for(i = 0, l = params.length; i < l; i++)
			{
				ret[i] = this.resolveParameters(params[i]);
			}
		}
		else if(kff.isPlainObject(params))
		{
			ret = {};
			for(i in params)
			{
				if(params.hasOwnProperty(i)) ret[i] = this.resolveParameters(params[i]);
			}
		}
		else
		{
			ret = params;
		}
		return ret;
	},

	/**
	 * Registers a new service configuration
	 *
	 * @param  {Object} services Services configuration object
	 * @param  {Boolean} overwrite If service already exists, overwrite it with new config
	 */
	registerServices: function(services, overwrite)
	{
		var service;
		for(service in services)
		{
			if(!this.config.services.hasOwnProperty(service) || overwrite)
			{
				this.config.services[service] = services[service];
				this.services[service] = undefined;
			}
		}
	},

	/**
	 * Registers a new parameters configuration
	 *
	 * @param  {Object} parameters Parameters configuration object
	 * @param  {Boolean} overwrite If parameter already exists, overwrite it with new config
	 */
	registerParameters: function(parameters, overwrite)
	{
		var parameter;
		for(parameter in parameters)
		{
			if(!this.config.parameters.hasOwnProperty(parameter) || overwrite)
			{
				this.config.parameters[parameter] = parameters[parameter];
			}
		}
	},

	/**
	 * Returns a service (constructor, function or another type of service)
	 * @param  {string}   serviceName Name of service
	 * @return {mixed}                Service constructor or factory or any other type of service
	 */
	loadService: function(serviceName)
	{
		if(typeof serviceName === 'string')
		{
			var match = serviceName.match(kff.ServiceContainer.serviceNameRegex);
			if(match)
			{
				serviceName = match[0];
			}
		}
		return kff.evalObjectPath(serviceName);
	},

	/**
	 * Creates a factory function for a service
	 * @param  {string} serviceName Name of the service
	 * @return {function}           Factory function that returns the service
	 */
	createServiceFactory: function(serviceName)
	{
		var container = this;
		return function()
		{
			return container.getService(serviceName);
		};
	}

});

<commit_msg>refactor(kff.ServiceContainer): remove parameters<commit_after>
kff.ServiceContainer = kff.createClass(
{
	statics:
	{
		CONFIG_CONSTRUCTOR: 'construct',
		serviceNameRegex: /^[^\s#]*/
	}
},
/** @lends kff.ServiceContainer.prototype */
{
	/**
	 * Simple dependency injection (or service) container class.
	 * @constructs
	 * @param {Object} config Configuration object
	 */
	constructor: function(config, loader)
	{
		this.config = config || { parameters: {}, services: {} };
		this.services = {};
		this.cachedParams = {};
		if(loader) this.loadService = loader;
	},

	/**
	 * Returns instance of service class.
	 * @param {string} service Service name (service config to be found in config.services[service])
	 * @param {Array} argsExtend Array to overload default arguments array (optional)
	 * @returns {Object} Instance of service
	 */
	getService: function(serviceName, argsExtend)
	{
		var serviceConfig;
		if(!this.config.services[serviceName])
		{
			serviceConfig = this.getServiceConfigAnnotation(serviceName);
			if(serviceConfig) this.config.services[serviceName] = serviceConfig;
			else throw new Error('Service ' + serviceName + ' not defined');
		}
		if(this.config.services[serviceName].shared)
		{
			if(typeof this.services[serviceName] === 'undefined') this.services[serviceName] = this.createService(serviceName, argsExtend);
			return this.services[serviceName];
		}
		return this.createService(serviceName, argsExtend);
	},

	/**
	 * Checks if given serviceName exists in container declaration
	 * @param {string} serviceName Service name
	 * @returns {boolean} True if service exists, false otherwise
	 */
	hasService: function(serviceName)
	{
		if(this.config.services.hasOwnProperty(serviceName)) return true;
		else {
			var serviceConfig = this.getServiceConfigAnnotation(serviceName);
			if(serviceConfig)
			{
				this.config.services[serviceName] = serviceConfig;
				return true;
			}
		}
		return false;
	},

	/**
	 * Creates instance of service.
	 *
	 * If second argument is passed, then it will be used to overload constructor arguments.
	 * If items at the same index are both objects, then the second one will bee deep-mixed into
	 * the first one resulting in a new object (i.e. the config args won't be overwritten).
	 *
	 * @param {string} serviceName Name of service to be instantiated
	 * @param {Array} argsExtend Array to overload default arguments array (optional)
	 * @returns {Object} Instance of service
	 */
	createService: function(serviceName, argsExtend)
	{
		var serviceConfig, Ctor, Temp, service, ret, i, l, args, argsExtended, calls;

		serviceConfig = this.config.services[serviceName];

		Ctor = this.getServiceConstructor(serviceName);

		if(typeof Ctor !== 'function' || serviceConfig.type === 'function') return Ctor;

		if(serviceConfig.type !== 'factory')
		{
			Temp = function(){};
			Temp.prototype = Ctor.prototype;
			service = new Temp();
		}

		args = this.resolveParameters(serviceConfig.args || []);
		if(argsExtend && argsExtend instanceof Array)
		{
			argsExtended = [];
			for(i = 0, l = argsExtend.length; i < l; i++)
			{
				if(argsExtend[i] !== undefined)
				{
					if(kff.isPlainObject(args[i]) && kff.isPlainObject(argsExtend[i])) argsExtended[i] = kff.mixins({}, args[i], argsExtend[i]);
					else argsExtended[i] = argsExtend[i];
				}
				else argsExtended[i] = args[i];
			}
			args = argsExtended;
		}

		if(serviceConfig.type === 'factory')
		{
			service = Ctor.apply(null, args);
		}
		else
		{
			ret = Ctor.apply(service, args);
			if(Object(ret) === ret) service = ret;
		}

		calls = serviceConfig.calls;
		if(calls instanceof Array)
		{
			for(i = 0, l = calls.length; i < l; i++)
			{
				service[calls[i].method].apply(service, this.resolveParameters(calls[i].args));
			}
		}
		return service;
	},

	/**
	 * Returns constructor function for given service name.
	 * @param {string} serviceName Service name
	 * @returns {function} Constructor function for service
	 */
	getServiceConstructor: function(serviceName)
	{
		var serviceConfig, ctor, construct = kff.ServiceContainer.CONFIG_CONSTRUCTOR, type, name, serviceObject;
		serviceConfig = this.config.services[serviceName];
		if(!serviceConfig)
		{
			serviceConfig = this.getServiceConfigAnnotation(serviceName);
			if(!serviceConfig) return null;
			else this.config.services[serviceName] = serviceConfig;
		}

		if(serviceConfig.construct) construct = serviceConfig.construct;
		else construct = serviceName;

		if(!serviceConfig.hasOwnProperty('serviceObject'))
		{
			if(typeof construct === 'string')
			{
				serviceConfig['serviceObject'] = this.loadService(construct);
			}
			else serviceConfig['serviceObject'] = construct;
			if(!serviceConfig['serviceObject']) return null;
		}

		return serviceConfig['serviceObject'];
	},

	/**
	 * Returns configuration object of a service from its constructor (function).
	 * @param  {string} serviceName Name of service
	 * @return {object}             Service configuration object
	 */
	getServiceConfigAnnotation: function(serviceName)
	{
		var serviceConfig = {};
		var ctor = this.loadService(serviceName);
		if(typeof ctor === 'function')
		{
			if('service' in ctor && kff.isPlainObject(ctor.service)) serviceConfig = ctor.service;
			serviceConfig.serviceObject = ctor;
			return serviceConfig;
		}
		else if(ctor)
		{
			serviceConfig.serviceObject = ctor;
			return serviceConfig;
		}
		return null;
	},

	/**
	 * Evaluates parameter defined in container configuration.
	 *
	 * Parameter could be:
	 *
	 * - a string - see below
	 * - an Array or Object - iterates over properties and evaluates them recursively
	 *
	 * String parameters refers to parameters defined in config.parameters section
	 * If parameter is a string, it could have these special chars:
	 * '@serviceName' - resolves to instance of service
	 *
	 * @param {string|Array|Object} params Parameters to be resolved
	 * @returns {mixed} Resolved parameter value
	 */
	resolveParameters: function(params)
	{
		var ret, i, l, config;

		config = this.config;

		if(typeof params === 'string')
		{
			if(params.indexOf('@@') === 0)
			{
				params = params.slice(2);
				if(params.length === 0) ret = null;
				else ret = this.createServiceFactory(params);
			}
			else if(params.charAt(0) === '@')
			{
				params = params.slice(1);
				if(params.length === 0) ret = this;
				else ret = this.getService(params);
			}
		}
		else if(params instanceof Array)
		{
			ret = [];
			for(i = 0, l = params.length; i < l; i++)
			{
				ret[i] = this.resolveParameters(params[i]);
			}
		}
		else if(kff.isPlainObject(params))
		{
			ret = {};
			for(i in params)
			{
				if(params.hasOwnProperty(i)) ret[i] = this.resolveParameters(params[i]);
			}
		}
		else
		{
			ret = params;
		}
		return ret;
	},

	/**
	 * Registers a new service configuration
	 *
	 * @param  {Object} services Services configuration object
	 * @param  {Boolean} overwrite If service already exists, overwrite it with new config
	 */
	registerServices: function(services, overwrite)
	{
		var service;
		for(service in services)
		{
			if(!this.config.services.hasOwnProperty(service) || overwrite)
			{
				this.config.services[service] = services[service];
				this.services[service] = undefined;
			}
		}
	},

	/**
	 * Returns a service (constructor, function or another type of service)
	 * @param  {string}   serviceName Name of service
	 * @return {mixed}                Service constructor or factory or any other type of service
	 */
	loadService: function(serviceName)
	{
		if(typeof serviceName === 'string')
		{
			var match = serviceName.match(kff.ServiceContainer.serviceNameRegex);
			if(match)
			{
				serviceName = match[0];
			}
		}
		return kff.evalObjectPath(serviceName);
	},

	/**
	 * Creates a factory function for a service
	 * @param  {string} serviceName Name of the service
	 * @return {function}           Factory function that returns the service
	 */
	createServiceFactory: function(serviceName)
	{
		var container = this;
		return function()
		{
			return container.getService(serviceName);
		};
	}

});

<|endoftext|>


<commit_before>var year = {

  getMonth : function(m,y) {

    var path = require('path');
    var month = require(path.join(process.cwd(),'/lib/cal.month')).display(m,y);

    return month;

  },
  monthLine : function(s) { // s = starting month

    var path = require('path');
    var month = require(path.join(process.cwd(),'/lib/cal.month'));
    var yr = require(path.join(process.cwd(),'/lib/year'));

    var output = ''; // initialize output

    for (var i = 1; i < 4; i++) { // iterates 3 times, once for each column
      var L = output.length;
      var m = yr.monthName[i + s - 1];
      var numSpaces = month.startIndex(0,m)+1; // +1 because we're using .join(' ')
      var whitespace = new Array(numSpaces).join(' ');
      var moreNumSpaces = 20 - (numSpaces + m.length) +4;
      output += whitespace + m;
      var moreWhitespace =
        i === 3 ?
        '\n' :
        new Array(moreNumSpaces).join(' ');
      output += moreWhitespace;
    }

    return output;

  },
  monthRow : function(s,y) { // s = starting column, e.g. 1 for Jan, y = year

    var path = require('path');
    var month = require(path.join(process.cwd(),'/lib/cal.month'));
    var yr = require(path.join(process.cwd(),'/lib/cal.month'));

    var output = ''; // initialize output

    output += this.monthLine(1)
            + this.wkdys();

  },
  rowCombiner : function(s,y,r) { // s = starting column, e.g. 1 for Jan, y = year, r = row #

    var months = [];
    for (var i = 1; i < 4; i++) { // iterates 3 times
      var m = this.splitByRow((i + s - 1),y); // in the month matrix, i specifies the column
      months.push(m);                         // index while s specifies the row
    }

    var my = this;
    var rows = months[0].map(function(el,i) {
      el += '  '
          + my.trailingSpace(el,1)
          + months[1][i]
          + my.trailingSpace(months[1][i],2)
          + '  '
          + months[2][i];
          + my.trailingSpace(months[2][i],3)
      return el;
    }).filter(function(el,i) {
      return i > 1
    });

    return rows;

  },
  splitByRow : function(m) {

    return m.split('\n');

  },
  title : function(y) {

    var whitespace = new Array(30).join(' ');
    return whitespace + y + '\n\n';

  },
  trailingSpace : function(input,c) { // c = column number, e.g. March is (1,3)

    var length = 20 - input.length;
    var trailingSpace =
      c < 3 ?
      new Array(length + 1).join(' ') :
      '\n';
    return trailingSpace;

  },
  wkdys : function() {

    var weekdays = 'Su Mo Tu We Th Fr Sa';
    return [ weekdays, weekdays, weekdays ].join('  ') + '\n';

  }

};

module.exports = year;
<commit_msg>Making sense of this month row function<commit_after>var year = {

  getMonth : function(m,y) {

    var path = require('path');
    var month = require(path.join(process.cwd(),'/lib/cal.month')).display(m,y);

    return month;

  },
  monthLine : function(s) { // s = starting month

    var path = require('path');
    var month = require(path.join(process.cwd(),'/lib/cal.month'));
    var yr = require(path.join(process.cwd(),'/lib/year'));

    var output = ''; // initialize output

    for (var i = 1; i < 4; i++) { // iterates 3 times, once for each column
      var L = output.length;
      var m = yr.monthName[i + s - 1];
      var numSpaces = month.startIndex(0,m)+1; // +1 because we're using .join(' ')
      var whitespace = new Array(numSpaces).join(' ');
      var moreNumSpaces = 20 - (numSpaces + m.length) +4;
      output += whitespace + m;
      var moreWhitespace =
        i === 3 ?
        '\n' :
        new Array(moreNumSpaces).join(' ');
      output += moreWhitespace;
    }

    return output;

  },
  monthRow : function(r,s,y) { // r = row #, s = starting month, e.g. 1 for Jan, y = year

    var path = require('path');
    var month = require(path.join(process.cwd(),'/lib/cal.month'));
    var yr = require(path.join(process.cwd(),'/lib/cal.month'));

    var output = ''; // initialize output

    output += this.monthLine(1)
            + this.wkdys();

  },
  rowCombiner : function(s,y,r) { // s = starting column, e.g. 1 for Jan, y = year, r = row #

    var months = [];
    for (var i = 1; i < 4; i++) { // iterates 3 times
      var m = this.splitByRow((i + s - 1),y); // in the month matrix, i specifies the column
      months.push(m);                         // index while s specifies the row
    }

    var my = this;
    var rows = months[0].map(function(el,i) {
      el += '  '
          + my.trailingSpace(el,1)
          + months[1][i]
          + my.trailingSpace(months[1][i],2)
          + '  '
          + months[2][i];
          + my.trailingSpace(months[2][i],3)
      return el;
    }).filter(function(el,i) {
      return i > 1
    });

    return rows;

  },
  splitByRow : function(m) {

    return m.split('\n');

  },
  title : function(y) {

    var whitespace = new Array(30).join(' ');
    return whitespace + y + '\n\n';

  },
  trailingSpace : function(input,c) { // c = column number, e.g. March is (1,3)

    var length = 20 - input.length;
    var trailingSpace =
      c < 3 ?
      new Array(length + 1).join(' ') :
      '\n';
    return trailingSpace;

  },
  wkdys : function() {

    var weekdays = 'Su Mo Tu We Th Fr Sa';
    return [ weekdays, weekdays, weekdays ].join('  ') + '\n';

  }

};

module.exports = year;
<|endoftext|>


<commit_before>/*global require*/
'use strict';

var util = require('util');
var path = require('path');
var yeoman = require('yeoman-generator');
var when = require('when');
var http = require('http');
var fs = require('fs-extra');
var url = require('url');
var GitHubApi = require('github');
var DecompressZip = require('decompress-zip');
var tar = require('tar-fs');
var zlib = require('zlib');

/*jshint camelcase: false*/
var proxy = process.env.http_proxy || process.env.HTTP_PROXY || process.env.https_proxy || process.env.HTTPS_PROXY || null;
var githubOptions = {
  version: '3.0.0'
};

if (proxy) {
  githubOptions.proxy = {};
  githubOptions.proxy.host = url.parse(proxy).hostname;
  githubOptions.proxy.port = url.parse(proxy).port;
}

var github = new GitHubApi(githubOptions);

var suggestAppNameFromPath = function (_) {
  var basePath = path.basename(process.env.PWD);
  return _.slugify(basePath);
};

var NodeWebkitGenerator = module.exports = function NodeWebkitGenerator(args, options) {
  yeoman.generators.Base.apply(this, arguments);

  this.on('end', function () {
    this.installDependencies({
      skipInstall: options['skip-install']
    });
  });

  this.pkg = JSON.parse(this.readFileAsString(path.join(__dirname, '../package.json')));
  this.nodeWebkitBaseUrl = 'http://dl.node-webkit.org/v0.9.2/node-webkit-v0.9.2-';
};

util.inherits(NodeWebkitGenerator, yeoman.generators.Base);

NodeWebkitGenerator.prototype.askFor = function askFor() {
  var done = this.async();
  var appName = suggestAppNameFromPath(this._);

  // have Yeoman greet the user.
  console.log(this.yeoman);

  var prompts = [{
    name: 'appName',
    message: 'What do you want to call your app? Allowed characters ^[a-zA-Z0-9]+$',
    default: appName,
    validate: function (answer) {
      if (!/^[a-zA-Z0-9]+$/.test(answer)) {
        return 'The application name should only consist of the following characters a-z, A-Z and 0-9.';
      }
      return true;
    }
  }, {
    name: 'appDescription',
    message: 'A little description for your app?'
  }, {
    name: 'githubUser',
    message: 'Would you mind telling me your username on GitHub?',
    default: 'someuser'
  }, {
    type: 'confirm',
    name: 'downloadNodeWebkit',
    message: 'Do you want to download latest node-webkit?',
    default: true
  }, {
    type: 'checkbox',
    name: 'platforms',
    message: 'Which platform do you wanna support?',
    choices: [{
      name: 'MacOS',
      checked: true
    }, {
      name: 'Linux 64',
      checked: true
    }, {
      name: 'Windows',
      checked: true
    }],
    when: function (answers) {
      return answers.downloadNodeWebkit;
    },
    validate: function (answer) {
      if (answer.length < 1) {
        return 'You must choose at least one platform.';
      }
      return true;
    }
  }];

  this.prompt(prompts, function (props) {
    var _this = this;
    this.appName = props.appName;
    this.appDescription = props.appDescription;
    this.platforms = props.platforms;
    this.githubUser = props.githubUser;
    this.downloadNodeWebkit = props.downloadNodeWebkit;
    this.MacOS = false;
    this.Linux64 = false;
    this.Windows = false;
    this.github = false;

    if (props.downloadNodeWebkit) {
      props.platforms.forEach(function (platform) {
        switch (platform) {
        case 'MacOS':
          _this.MacOS = true;
          break;
        case 'Linux 64':
          _this.Linux64 = true;
          break;
        case 'Windows':
          _this.Windows = true;
          break;
        }
      });
    }
    done();
  }.bind(this));
};

NodeWebkitGenerator.prototype.userInfo = function userInfo() {
  var done = this.async();
  var _this = this;
  var responseClbk = function (err, responseText) {
    if (err) {
      _this.log.conflict(err);
      throw err;
    } else {
      var responseObject = JSON.parse(JSON.stringify(responseText));
      _this.log.ok('Github informations successfully retrieved.');
      _this.realname = responseObject.name;
      _this.email = responseObject.email;
      _this.githubUrl = responseObject.html_url;
      done();
    }
  };

  if (this.githubUser !== 'someuser') {
    this.log.info('Get GitHub informations');
    this.github = true;
    github.user.getFrom({
      user: this.githubUser
    }, responseClbk);
  } else {
    done();
  }
};

NodeWebkitGenerator.prototype.app = function app() {
  this.mkdir('app');
  this.mkdir('app/img');
  this.mkdir('resources/node-webkit');
  if (this.MacOS) {
    this.mkdir('resources/node-webkit/MacOS');
  }
  if (this.Linux64) {
    this.mkdir('resources/node-webkit/Linux64');
  }
  if (this.Windows) {
    this.mkdir('resources/node-webkit/Windows');
  }
  this.mkdir('tmp');
};

NodeWebkitGenerator.prototype.getNodeWebkit = function getNodeWebkit() {
  var done = this.async();

  var successClbk = function () {
    done();
  };
  var failureClbk = function (error) {
    throw error;
  };
  if (this.downloadNodeWebkit) {
    when.all(this._getNodeWebkit(), successClbk, failureClbk);
  } else {
    when.all(this._createFolder(), successClbk, failureClbk);
  }
};

NodeWebkitGenerator.prototype._createFolder = function _createFolder() {
  var promises = [];
  var basePath = 'resources/node-webkit/';
  var platforms = ['MacOS', 'Linux64', 'Windows'];
  platforms.forEach(function (platform) {
    var defer = when.defer();
    promises.push(defer.promise);
    fs.mkdirs(basePath + '/' + platform, function (err) {
      if (err) {
        defer.reject(err);
      } else {
        defer.resolve();
      }
    });
  });
  return promises;
};

NodeWebkitGenerator.prototype._getNodeWebkit = function _getNodeWebkit() {
  var promises = [];
  if (this.MacOS) {
    promises.push(this._requestNodeWebkit('osx-ia32', '.zip', 'MacOS'));
  }
  if (this.Linux64) {
    promises.push(this._requestNodeWebkit('linux-x64', '.tar.gz', 'Linux64'));
  }
  if (this.Windows) {
    promises.push(this._requestNodeWebkit('win-ia32', '.zip', 'Windows'));
  }
  return promises;
};

NodeWebkitGenerator.prototype._requestNodeWebkit = function _requestNodeWebkit(versionString, extension, platform) {
  var defer = when.defer(),
    _this = this,
    contentType = extension === '.zip' ? 'application/zip' : 'application/octet-stream';
  if (!fs.existsSync('tmp/' + platform + extension)) {
    this.log.info('Downloading node-webkit for ' + platform);
    http.get(this.nodeWebkitBaseUrl + versionString + extension, function (res) {
      if (res.headers['content-type'] === contentType) {
        res.on('data', function (chunk) {
          fs.appendFileSync('tmp/' + platform + extension, chunk);
        }).on('end', function () {
          _this.log.ok('Node-webkit for ' + platform + ' downloaded');
          defer.resolve();
        }).on('error', function (error) {
          _this.log.conflict('Error while downloading node-webkit for ' + platform, error);
          defer.reject(error);
        });
      } else {
        _this.log.conflict('Wrong content type for %s', platform);
        defer.reject('Wrong content type for ' + platform);
      }
    }).on('error', function (error) {
      _this.log.conflict('Error while downloading node-webkit for ' + platform, error);
      defer.reject(error);
    });
  } else {
    this.log.ok('Node-webkit for ' + platform + ' already downloaded');
    defer.resolve();
  }
  return defer.promise;
};

NodeWebkitGenerator.prototype.unzipNodeWebkit = function unzipNodeWebkit() {
  var done = this.async();
  var successClbk = function () {
    done();
  };
  var failureClbk = function (error) {
    throw error;
  };
  when.all(this._unzipNodeWebkit(), successClbk, failureClbk);
};

NodeWebkitGenerator.prototype._unzipNodeWebkit = function _unzipNodeWebkit() {
  var promises = [];

  if (this.MacOS) {
    promises.push(this._extract('MacOS', '.zip'));
  }
  if (this.Linux64) {
    promises.push(this._extract('Linux64', '.tar.gz'));
  }
  if (this.Windows) {
    promises.push(this._extract('Windows', '.zip'));
  }
  return promises;
};

NodeWebkitGenerator.prototype._extract = function _extract(platform, extension) {
  var _this = this;
  var defer = when.defer();
  if ('.zip' === extension) {
    if (fs.existsSync('tmp/' + platform + extension)) {
      this.log.info('Unzip %s files.', platform);
      var unzipper = new DecompressZip('tmp/' + platform + extension);

      unzipper.on('error', function (error) {
        _this.log.conflict('Error while unzipping "tmp/' + platform + extension + '"', error);
        defer.reject(error);
      });

      unzipper.on('extract', function () {
        _this.log.ok('"tmp/%s.zip" successfully unzipped', platform);
        defer.resolve();
      });

      unzipper.extract({
        path: 'resources/node-webkit/' + platform
      });
    } else {
      defer.resolve();
    }
  } else if ('.tar.gz' === extension) {
    this.log.info('Un.tar.gz %s files.', platform);
    var src = 'tmp/' + platform + extension;
    var dst = 'resources/node-webkit/' + platform;
    fs.createReadStream(src).pipe(zlib.createGunzip()).pipe(tar.extract(dst)).on('finish', function (error) {
      if (!error) {
        fs.copy('resources/node-webkit/' + platform + '/node-webkit-v0.9.2-linux-x64', 'resources/node-webkit/' + platform, function (error) {
          if (error) {
            _this.log.conflict('Error while copying files for ' + platform + '!', error);
          } else {
            _this.log.ok('%s files successfully copied.', platform);
            fs.removeSync('resources/node-webkit/' + platform + '/node-webkit-v0.9.2-linux-x64');
            defer.resolve();
          }
        });
      }
    });
  }
  return defer.promise;
};

NodeWebkitGenerator.prototype._copyNodeWebkit = function _copyNodeWebkit(platform) {
  var _this = this;
  this.log.info('Copy %s files.', platform);
  switch (platform) {
  case 'MacOS':
    fs.copy('tmp/mac/node-webkit.app', 'resources/node-webkit/mac/node-webkit.app', function (error) {
      if (error) {
        _this.log.conflict('Error while copying files for ' + platform + '!', error);
      } else {
        _this.log.ok('%s files successfully copied.', platform);
      }
    });
    break;
  default:
    this.log.ok('No files to copy');
  }
};

NodeWebkitGenerator.prototype._cleanUp = function _cleanUp(platform) {
  var _this = this;
  this.log.info('Cleaning up tmp directories for %s.', platform);
  switch (platform) {
  case 'MacOS':
    fs.remove('tmp/mac', function (error) {
      if (error) {
        _this.log.conflict('Error while deleting tmp directory for ' + platform + '!', error);
      } else {
        _this.log.ok('Tmp directory for %s successfully removed.', platform);
      }
    });
    fs.remove('tmp/node-webkit-osx-ia32.zip', function (error) {
      if (error) {
        _this.log.conflict('Error while deleting zip file for ' + platform + '!', error);
      } else {
        _this.log.ok('Zip file for %s successfully removed.', platform);
      }
    });
    break;
  default:
    this.log.ok('No files to clean.');
  }
};

NodeWebkitGenerator.prototype.projectfiles = function projectfiles() {
  this.copy('editorconfig', '.editorconfig');
  this.copy('jshintrc', '.jshintrc');
};

NodeWebkitGenerator.prototype.copyFiles = function copyFiles() {
  this.copy('_bower.json', 'bower.json');
  this.copy('app/_main.css', 'app/css/main.css');
  this.copy('app/_index.js', 'app/js/index.js');
  this.template('_package.json', 'package.json');
  this.template('app/_package.json', 'app/package.json');
  this.template('app/_index.html', 'app/views/index.html');
  this.template('_Gruntfile.js', 'Gruntfile.js');
  this.template('mac/_Info.plist.tmp', 'resources/mac/Info.plist.tmp');
  this.template('mac/_Info.plist', 'resources/mac/Info.plist');
  this.copy('mac/dmgStyler.applescript', 'resources/mac/dmgStyler.applescript');
  this.copy('mac/package.sh', 'resources/mac/package.sh');
  this.copy('mac/background.png', 'resources/mac/background.png');
};
<commit_msg>* update when.all to match new when API<commit_after>/*global require*/
'use strict';

var util = require('util');
var path = require('path');
var yeoman = require('yeoman-generator');
var when = require('when');
var http = require('http');
var fs = require('fs-extra');
var url = require('url');
var GitHubApi = require('github');
var DecompressZip = require('decompress-zip');
var tar = require('tar-fs');
var zlib = require('zlib');

/*jshint camelcase: false*/
var proxy = process.env.http_proxy || process.env.HTTP_PROXY || process.env.https_proxy || process.env.HTTPS_PROXY || null;
var githubOptions = {
  version: '3.0.0'
};

if (proxy) {
  githubOptions.proxy = {};
  githubOptions.proxy.host = url.parse(proxy).hostname;
  githubOptions.proxy.port = url.parse(proxy).port;
}

var github = new GitHubApi(githubOptions);

var suggestAppNameFromPath = function (_) {
  var basePath = path.basename(process.env.PWD);
  return _.slugify(basePath);
};

var NodeWebkitGenerator = module.exports = function NodeWebkitGenerator(args, options) {
  yeoman.generators.Base.apply(this, arguments);

  this.on('end', function () {
    this.installDependencies({
      skipInstall: options['skip-install']
    });
  });

  this.pkg = JSON.parse(this.readFileAsString(path.join(__dirname, '../package.json')));
  this.nodeWebkitBaseUrl = 'http://dl.node-webkit.org/v0.9.2/node-webkit-v0.9.2-';
};

util.inherits(NodeWebkitGenerator, yeoman.generators.Base);

NodeWebkitGenerator.prototype.askFor = function askFor() {
  var done = this.async();
  var appName = suggestAppNameFromPath(this._);

  // have Yeoman greet the user.
  console.log(this.yeoman);

  var prompts = [{
    name: 'appName',
    message: 'What do you want to call your app? Allowed characters ^[a-zA-Z0-9]+$',
    default: appName,
    validate: function (answer) {
      if (!/^[a-zA-Z0-9]+$/.test(answer)) {
        return 'The application name should only consist of the following characters a-z, A-Z and 0-9.';
      }
      return true;
    }
  }, {
    name: 'appDescription',
    message: 'A little description for your app?'
  }, {
    name: 'githubUser',
    message: 'Would you mind telling me your username on GitHub?',
    default: 'someuser'
  }, {
    type: 'confirm',
    name: 'downloadNodeWebkit',
    message: 'Do you want to download latest node-webkit?',
    default: true
  }, {
    type: 'checkbox',
    name: 'platforms',
    message: 'Which platform do you wanna support?',
    choices: [{
      name: 'MacOS',
      checked: true
    }, {
      name: 'Linux 64',
      checked: true
    }, {
      name: 'Windows',
      checked: true
    }],
    when: function (answers) {
      return answers.downloadNodeWebkit;
    },
    validate: function (answer) {
      if (answer.length < 1) {
        return 'You must choose at least one platform.';
      }
      return true;
    }
  }];

  this.prompt(prompts, function (props) {
    var _this = this;
    this.appName = props.appName;
    this.appDescription = props.appDescription;
    this.platforms = props.platforms;
    this.githubUser = props.githubUser;
    this.downloadNodeWebkit = props.downloadNodeWebkit;
    this.MacOS = false;
    this.Linux64 = false;
    this.Windows = false;
    this.github = false;

    if (props.downloadNodeWebkit) {
      props.platforms.forEach(function (platform) {
        switch (platform) {
        case 'MacOS':
          _this.MacOS = true;
          break;
        case 'Linux 64':
          _this.Linux64 = true;
          break;
        case 'Windows':
          _this.Windows = true;
          break;
        }
      });
    }
    done();
  }.bind(this));
};

NodeWebkitGenerator.prototype.userInfo = function userInfo() {
  var done = this.async();
  var _this = this;
  var responseClbk = function (err, responseText) {
    if (err) {
      _this.log.conflict(err);
      throw err;
    } else {
      var responseObject = JSON.parse(JSON.stringify(responseText));
      _this.log.ok('Github informations successfully retrieved.');
      _this.realname = responseObject.name;
      _this.email = responseObject.email;
      _this.githubUrl = responseObject.html_url;
      done();
    }
  };

  if (this.githubUser !== 'someuser') {
    this.log.info('Get GitHub informations');
    this.github = true;
    github.user.getFrom({
      user: this.githubUser
    }, responseClbk);
  } else {
    done();
  }
};

NodeWebkitGenerator.prototype.app = function app() {
  this.mkdir('app');
  this.mkdir('app/img');
  this.mkdir('resources/node-webkit');
  if (this.MacOS) {
    this.mkdir('resources/node-webkit/MacOS');
  }
  if (this.Linux64) {
    this.mkdir('resources/node-webkit/Linux64');
  }
  if (this.Windows) {
    this.mkdir('resources/node-webkit/Windows');
  }
  this.mkdir('tmp');
};

NodeWebkitGenerator.prototype.getNodeWebkit = function getNodeWebkit() {
  var done = this.async();

  var successClbk = function () {
    done();
  };
  var failureClbk = function (error) {
    throw error;
  };
  if (this.downloadNodeWebkit) {
    when.all(this._getNodeWebkit()).then(successClbk, failureClbk);
  } else {
    when.all(this._createFolder()).then(successClbk, failureClbk);
  }
};

NodeWebkitGenerator.prototype._createFolder = function _createFolder() {
  var promises = [];
  var basePath = 'resources/node-webkit/';
  var platforms = ['MacOS', 'Linux64', 'Windows'];
  platforms.forEach(function (platform) {
    var defer = when.defer();
    promises.push(defer.promise);
    fs.mkdirs(basePath + '/' + platform, function (err) {
      if (err) {
        defer.reject(err);
      } else {
        defer.resolve();
      }
    });
  });
  return promises;
};

NodeWebkitGenerator.prototype._getNodeWebkit = function _getNodeWebkit() {
  var promises = [];
  if (this.MacOS) {
    promises.push(this._requestNodeWebkit('osx-ia32', '.zip', 'MacOS'));
  }
  if (this.Linux64) {
    promises.push(this._requestNodeWebkit('linux-x64', '.tar.gz', 'Linux64'));
  }
  if (this.Windows) {
    promises.push(this._requestNodeWebkit('win-ia32', '.zip', 'Windows'));
  }
  return promises;
};

NodeWebkitGenerator.prototype._requestNodeWebkit = function _requestNodeWebkit(versionString, extension, platform) {
  var defer = when.defer(),
    _this = this,
    contentType = extension === '.zip' ? 'application/zip' : 'application/octet-stream';
  if (!fs.existsSync('tmp/' + platform + extension)) {
    this.log.info('Downloading node-webkit for ' + platform);
    http.get(this.nodeWebkitBaseUrl + versionString + extension, function (res) {
      if (res.headers['content-type'] === contentType) {
        res.on('data', function (chunk) {
          fs.appendFileSync('tmp/' + platform + extension, chunk);
        }).on('end', function () {
          _this.log.ok('Node-webkit for ' + platform + ' downloaded');
          defer.resolve();
        }).on('error', function (error) {
          _this.log.conflict('Error while downloading node-webkit for ' + platform, error);
          defer.reject(error);
        });
      } else {
        _this.log.conflict('Wrong content type for %s', platform);
        defer.reject('Wrong content type for ' + platform);
      }
    }).on('error', function (error) {
      _this.log.conflict('Error while downloading node-webkit for ' + platform, error);
      defer.reject(error);
    });
  } else {
    this.log.ok('Node-webkit for ' + platform + ' already downloaded');
    defer.resolve();
  }
  return defer.promise;
};

NodeWebkitGenerator.prototype.unzipNodeWebkit = function unzipNodeWebkit() {
  var done = this.async();
  var successClbk = function () {
    done();
  };
  var failureClbk = function (error) {
    throw error;
  };
  when.all(this._unzipNodeWebkit()).then(successClbk, failureClbk);
};

NodeWebkitGenerator.prototype._unzipNodeWebkit = function _unzipNodeWebkit() {
  var promises = [];

  if (this.MacOS) {
    promises.push(this._extract('MacOS', '.zip'));
  }
  if (this.Linux64) {
    promises.push(this._extract('Linux64', '.tar.gz'));
  }
  if (this.Windows) {
    promises.push(this._extract('Windows', '.zip'));
  }
  return promises;
};

NodeWebkitGenerator.prototype._extract = function _extract(platform, extension) {
  var _this = this;
  var defer = when.defer();
  if ('.zip' === extension) {
    if (fs.existsSync('tmp/' + platform + extension)) {
      this.log.info('Unzip %s files.', platform);
      var unzipper = new DecompressZip('tmp/' + platform + extension);

      unzipper.on('error', function (error) {
        _this.log.conflict('Error while unzipping "tmp/' + platform + extension + '"', error);
        defer.reject(error);
      });

      unzipper.on('extract', function () {
        _this.log.ok('"tmp/%s.zip" successfully unzipped', platform);
        defer.resolve();
      });

      unzipper.extract({
        path: 'resources/node-webkit/' + platform
      });
    } else {
      defer.resolve();
    }
  } else if ('.tar.gz' === extension) {
    this.log.info('Un.tar.gz %s files.', platform);
    var src = 'tmp/' + platform + extension;
    var dst = 'resources/node-webkit/' + platform;
    fs.createReadStream(src).pipe(zlib.createGunzip()).pipe(tar.extract(dst)).on('finish', function (error) {
      if (!error) {
        fs.copy('resources/node-webkit/' + platform + '/node-webkit-v0.9.2-linux-x64', 'resources/node-webkit/' + platform, function (error) {
          if (error) {
            _this.log.conflict('Error while copying files for ' + platform + '!', error);
          } else {
            _this.log.ok('%s files successfully copied.', platform);
            fs.removeSync('resources/node-webkit/' + platform + '/node-webkit-v0.9.2-linux-x64');
            defer.resolve();
          }
        });
      }
    });
  }
  return defer.promise;
};

NodeWebkitGenerator.prototype._copyNodeWebkit = function _copyNodeWebkit(platform) {
  var _this = this;
  this.log.info('Copy %s files.', platform);
  switch (platform) {
  case 'MacOS':
    fs.copy('tmp/mac/node-webkit.app', 'resources/node-webkit/mac/node-webkit.app', function (error) {
      if (error) {
        _this.log.conflict('Error while copying files for ' + platform + '!', error);
      } else {
        _this.log.ok('%s files successfully copied.', platform);
      }
    });
    break;
  default:
    this.log.ok('No files to copy');
  }
};

NodeWebkitGenerator.prototype._cleanUp = function _cleanUp(platform) {
  var _this = this;
  this.log.info('Cleaning up tmp directories for %s.', platform);
  switch (platform) {
  case 'MacOS':
    fs.remove('tmp/mac', function (error) {
      if (error) {
        _this.log.conflict('Error while deleting tmp directory for ' + platform + '!', error);
      } else {
        _this.log.ok('Tmp directory for %s successfully removed.', platform);
      }
    });
    fs.remove('tmp/node-webkit-osx-ia32.zip', function (error) {
      if (error) {
        _this.log.conflict('Error while deleting zip file for ' + platform + '!', error);
      } else {
        _this.log.ok('Zip file for %s successfully removed.', platform);
      }
    });
    break;
  default:
    this.log.ok('No files to clean.');
  }
};

NodeWebkitGenerator.prototype.projectfiles = function projectfiles() {
  this.copy('editorconfig', '.editorconfig');
  this.copy('jshintrc', '.jshintrc');
};

NodeWebkitGenerator.prototype.copyFiles = function copyFiles() {
  this.copy('_bower.json', 'bower.json');
  this.copy('app/_main.css', 'app/css/main.css');
  this.copy('app/_index.js', 'app/js/index.js');
  this.template('_package.json', 'package.json');
  this.template('app/_package.json', 'app/package.json');
  this.template('app/_index.html', 'app/views/index.html');
  this.template('_Gruntfile.js', 'Gruntfile.js');
  this.template('mac/_Info.plist.tmp', 'resources/mac/Info.plist.tmp');
  this.template('mac/_Info.plist', 'resources/mac/Info.plist');
  this.copy('mac/dmgStyler.applescript', 'resources/mac/dmgStyler.applescript');
  this.copy('mac/package.sh', 'resources/mac/package.sh');
  this.copy('mac/background.png', 'resources/mac/background.png');
};
<|endoftext|>


<commit_before>var generators = require('yeoman-generator');
var gitUrl = require('git-remote-origin-url');

module.exports = generators.Base.extend({

    constructor: function () {
        generators.Base.apply(this, arguments);
        //this.argument('appname', {type: String, required: false});
    },

    getGitUrl: function () {
        var done = this.async();
        gitUrl('', function(err, url) {
            this.gitUrl = (!err && url) ? url : null;
            done();
        }.bind(this));
    },

    getAppName: function () {
        var done = this.async();
        this.prompt({
            type: 'input',
            name: 'name',
            message: 'Your project name',
            default: this.appname,
            store: true
        }, function (res) {
            this.appname = res.name;
            done();
        }.bind(this));
    },

    getDescription: function () {
        var done = this.async();
        this.prompt({
            type: 'input',
            name: 'description',
            message: 'A description of your project',
            store: true
        }, function (res) {
            this.description = res.description;
            done();
        }.bind(this));
    },

    copyFiles: function () {

        var files = [
            '.gitignore',
            'README.md',
            'package.json',
            'webpack.config.js',
            'src/index.html',
            'src/app.js'
        ];

        // TODO: Git user
        var tplVars = {
            appname: this.appname,
            description: this.description,
            gitUrl: this.gitUrl
        };

        files.forEach(function (file) {
            this.fs.copyTpl(
                this.templatePath(file),
                this.destinationPath(file),
                tplVars
            );
        }.bind(this));

    },

    installDeps: function () {
        this.npmInstall([
            'webpack',
            'webpack-dev-server',
            'babel',
            'babel-core',
            'babel-loader',
            'babel-preset-es2015',
            'css-loader',
            'style-loader',
            'html-loader',
            'postcss',
            'autoprefixer',
            'postcss-loader',
            'node-sass',
            'sass-loader'
        ],{
            'saveDev': true
        });
    },

    complete: function () {
        this.log('Setup complete. To start the app, run `npm start`.');
    }

});<commit_msg>fix(app): Do not store app name and description<commit_after>var generators = require('yeoman-generator');
var gitUrl = require('git-remote-origin-url');

module.exports = generators.Base.extend({

    constructor: function () {
        generators.Base.apply(this, arguments);
        //this.argument('appname', {type: String, required: false});
    },

    getGitUrl: function () {
        var done = this.async();
        gitUrl('', function(err, url) {
            this.gitUrl = (!err && url) ? url : null;
            done();
        }.bind(this));
    },

    getAppName: function () {
        var done = this.async();
        this.prompt({
            type: 'input',
            name: 'name',
            message: 'Your project name',
            default: this.appname
        }, function (res) {
            this.appname = res.name;
            done();
        }.bind(this));
    },

    getDescription: function () {
        var done = this.async();
        this.prompt({
            type: 'input',
            name: 'description',
            message: 'A description of your project'
        }, function (res) {
            this.description = res.description;
            done();
        }.bind(this));
    },

    copyFiles: function () {

        var files = [
            '.gitignore',
            'README.md',
            'package.json',
            'webpack.config.js',
            'src/index.html',
            'src/app.js'
        ];

        // TODO: Git user
        var tplVars = {
            appname: this.appname,
            description: this.description,
            gitUrl: this.gitUrl
        };

        files.forEach(function (file) {
            this.fs.copyTpl(
                this.templatePath(file),
                this.destinationPath(file),
                tplVars
            );
        }.bind(this));

    },

    installDeps: function () {
        this.npmInstall([
            'webpack',
            'webpack-dev-server',
            'babel',
            'babel-core',
            'babel-loader',
            'babel-preset-es2015',
            'css-loader',
            'style-loader',
            'html-loader',
            'postcss',
            'autoprefixer',
            'postcss-loader',
            'node-sass',
            'sass-loader'
        ],{
            'saveDev': true
        });
    },

    complete: function () {
        this.log('Setup complete. To start the app, run `npm start`.');
    }

});<|endoftext|>


<commit_before>/*
Language: PowerShell
Author: David Mohundro <david@mohundro.com>
Contributors: Nicholas Blumhardt <nblumhardt@nblumhardt.com>, Victor Zhou <OiCMudkips@users.noreply.github.com>
*/

function(hljs) {
  var backtickEscape = {
    begin: '`[\\s\\S]',
    relevance: 0
  };
  var VAR = {
    className: 'variable',
    variants: [
      {begin: /\$[\w\d][\w\d_:]*/}
    ]
  };
  var LITERAL = {
    className: 'literal',
    begin: /\$(null|true|false)\b/
  };
  var QUOTE_STRING = {
    className: 'string',
    begin: /"/, end: /"/,
    contains: [
      backtickEscape,
      VAR,
      {
        className: 'variable',
        begin: /\$[A-z]/, end: /[^A-z]/
      }
    ]
  };
  var APOS_STRING = {
    className: 'string',
    begin: /'/, end: /'/
  };

  var MULTILINE_COMMENT = {
    className: 'comment',
    begin: /<#/, end: /#>/
  }

  return {
    aliases: ['ps'],
    lexemes: /-?[A-z\.\-]+/,
    case_insensitive: true,
    keywords: {
      keyword: 'if else foreach return function do while until elseif begin for trap data dynamicparam end break throw param continue finally in switch exit filter try process catch',
      built_in: 'Add-Content Add-History Add-Member Add-PSSnapin Clear-Content Clear-Item Clear-Item Property Clear-Variable Compare-Object ConvertFrom-SecureString Convert-Path ConvertTo-Html ConvertTo-SecureString Copy-Item Copy-ItemProperty Export-Alias Export-Clixml Export-Console Export-Csv ForEach-Object Format-Custom Format-List Format-Table Format-Wide Get-Acl Get-Alias Get-AuthenticodeSignature Get-ChildItem Get-Command Get-Content Get-Credential Get-Culture Get-Date Get-EventLog Get-ExecutionPolicy Get-Help Get-History Get-Host Get-Item Get-ItemProperty Get-Location Get-Member Get-PfxCertificate Get-Process Get-PSDrive Get-PSProvider Get-PSSnapin Get-Service Get-TraceSource Get-UICulture Get-Unique Get-Variable Get-WmiObject Group-Object Import-Alias Import-Clixml Import-Csv Invoke-Expression Invoke-History Invoke-Item Join-Path Measure-Command Measure-Object Move-Item Move-ItemProperty New-Alias New-Item New-ItemProperty New-Object New-PSDrive New-Service New-TimeSpan New-Variable Out-Default Out-File Out-Host Out-Null Out-Printer Out-String Pop-Location Push-Location Read-Host Remove-Item Remove-ItemProperty Remove-PSDrive Remove-PSSnapin Remove-Variable Rename-Item Rename-ItemProperty Resolve-Path Restart-Service Resume-Service Select-Object Select-String Set-Acl Set-Alias Set-AuthenticodeSignature Set-Content Set-Date Set-ExecutionPolicy Set-Item Set-ItemProperty Set-Location Set-PSDebug Set-Service Set-TraceSource Set-Variable Sort-Object Split-Path Start-Service Start-Sleep Start-Transcript Stop-Process Stop-Service Stop-Transcript Suspend-Service Tee-Object Test-Path Trace-Command Update-FormatData Update-TypeData Where-Object Write-Debug Write-Error Write-Host Write-Output Write-Progress Write-Verbose Write-Warning',
      nomarkup: '-ne -eq -lt -gt -ge -le -not -like -notlike -match -notmatch -contains -notcontains -in -notin -replace'
    },
    contains: [
      hljs.HASH_COMMENT_MODE,
      hljs.NUMBER_MODE,
      QUOTE_STRING,
      APOS_STRING,
      LITERAL,
      VAR,
      MULTILINE_COMMENT
    ]
  };
}
<commit_msg>support help-based comments in powershell (see https://technet.microsoft.com/en-us/library/hh847834.aspx)<commit_after>/*
Language: PowerShell
Author: David Mohundro <david@mohundro.com>
Contributors: Nicholas Blumhardt <nblumhardt@nblumhardt.com>, Victor Zhou <OiCMudkips@users.noreply.github.com>
*/

function(hljs) {
  var backtickEscape = {
    begin: '`[\\s\\S]',
    relevance: 0
  };
  var VAR = {
    className: 'variable',
    variants: [
      {begin: /\$[\w\d][\w\d_:]*/}
    ]
  };
  var LITERAL = {
    className: 'literal',
    begin: /\$(null|true|false)\b/
  };
  var QUOTE_STRING = {
    className: 'string',
    begin: /"/, end: /"/,
    contains: [
      backtickEscape,
      VAR,
      {
        className: 'variable',
        begin: /\$[A-z]/, end: /[^A-z]/
      }
    ]
  };
  var APOS_STRING = {
    className: 'string',
    begin: /'/, end: /'/
  };

  var PS_HELPTAGS = {
    className: 'doctag',
    variants: [
      /* no paramater help tags */
      {
        begin: '\\.(synopsis|description|example|inputs|outputs|notes|link|component|role|functionality)'
      },
      /* one parameter help tags */
      {
        begin: '\\.(parameter|forwardhelptargetname|forwardhelpcategory|remotehelprunspace|externalhelp) \\S+'
      }
    ]
  };

  var PS_SINGLELINE_COMMENT = hljs.COMMENT(
    /#/ /* begin */,
    /$/ /* end */,
    {
      contains: [
        PS_HELPTAGS
      ]
    }
  );
  var PS_MULTILINE_COMMENT = hljs.COMMENT(
    /<#/ /* begin */,
    /#>/ /* end */,
    {
      contains: [
        PS_HELPTAGS
      ]
    }
  );

  return {
    aliases: ['ps'],
    lexemes: /-?[A-z\.\-]+/,
    case_insensitive: true,
    keywords: {
      keyword: 'if else foreach return function do while until elseif begin for trap data dynamicparam end break throw param continue finally in switch exit filter try process catch',
      built_in: 'Add-Content Add-History Add-Member Add-PSSnapin Clear-Content Clear-Item Clear-Item Property Clear-Variable Compare-Object ConvertFrom-SecureString Convert-Path ConvertTo-Html ConvertTo-SecureString Copy-Item Copy-ItemProperty Export-Alias Export-Clixml Export-Console Export-Csv ForEach-Object Format-Custom Format-List Format-Table Format-Wide Get-Acl Get-Alias Get-AuthenticodeSignature Get-ChildItem Get-Command Get-Content Get-Credential Get-Culture Get-Date Get-EventLog Get-ExecutionPolicy Get-Help Get-History Get-Host Get-Item Get-ItemProperty Get-Location Get-Member Get-PfxCertificate Get-Process Get-PSDrive Get-PSProvider Get-PSSnapin Get-Service Get-TraceSource Get-UICulture Get-Unique Get-Variable Get-WmiObject Group-Object Import-Alias Import-Clixml Import-Csv Invoke-Expression Invoke-History Invoke-Item Join-Path Measure-Command Measure-Object Move-Item Move-ItemProperty New-Alias New-Item New-ItemProperty New-Object New-PSDrive New-Service New-TimeSpan New-Variable Out-Default Out-File Out-Host Out-Null Out-Printer Out-String Pop-Location Push-Location Read-Host Remove-Item Remove-ItemProperty Remove-PSDrive Remove-PSSnapin Remove-Variable Rename-Item Rename-ItemProperty Resolve-Path Restart-Service Resume-Service Select-Object Select-String Set-Acl Set-Alias Set-AuthenticodeSignature Set-Content Set-Date Set-ExecutionPolicy Set-Item Set-ItemProperty Set-Location Set-PSDebug Set-Service Set-TraceSource Set-Variable Sort-Object Split-Path Start-Service Start-Sleep Start-Transcript Stop-Process Stop-Service Stop-Transcript Suspend-Service Tee-Object Test-Path Trace-Command Update-FormatData Update-TypeData Where-Object Write-Debug Write-Error Write-Host Write-Output Write-Progress Write-Verbose Write-Warning',
      nomarkup: '-ne -eq -lt -gt -ge -le -not -like -notlike -match -notmatch -contains -notcontains -in -notin -replace'
    },
    contains: [
      hljs.NUMBER_MODE,
      QUOTE_STRING,
      APOS_STRING,
      LITERAL,
      VAR,
      PS_SINGLELINE_COMMENT,
      PS_MULTILINE_COMMENT
    ]
  };
}
<|endoftext|>


<commit_before>DEBUG = false

Database = {
    url: "http://localhost:8000/api/v2/",

    getItem: function(key) {
        return localStorage.getItem(key);
    },

    setItem: function(key, value) {
        return localStorage.setItem(key, value);
    },

    get: function() {
        database = Array();

        for (let key of Object.keys(localStorage)) {
            if (key != ".temp" && key != ".veteran") {
                let value = localStorage.getItem(key);
                database.push(JSON.parse(value));
            }
        }

        return database;
    },

    insert: function(trial) {
        console.debug("[SUCCESS] Trial saved to localStorage:", trial);
        return localStorage.setItem(trial.trial.start_datetime, JSON.stringify(trial));
    },

    delete: function(trial) {
        console.debug("[SUCCESS] Trial deleted from localStorage", trial);
        return localStorage.removeItem(trial.trial.start_datetime);
    },

    clear: function() {
        console.debug("[SUCCESS] Database in localStorage cleared");
        localStorage.clear();
        localStorage.setItem('.veteran', true);
    },

    uploadResults: function() {
        for (let trial of Database.get()) {
            $.ajax({
                type: "POST",
                crossDomain: true,
                url: this.url,
                data: JSON.stringify(trial),

                success: function(response) {
                    let trial = JSON.parse(this.data);
                    console.debug("[SUCCESS] Trial results uploaded to the remote database:", trial);
                    console.debug("[SUCCESS] Received response", response)
                    Database.delete(trial);
                    return response
                },

                error: function() {
                    let trial = JSON.parse(this.data);
                    console.debug("[WARNING] Will try syncdb latter:", trial);
                }
            });
        }
    },

    syncdb: function() {
        if (DEBUG) {
            alert("You're in DEBUG mode! Will not `Database.syncdb()`");
            return;
        }

        $.ajax({
            type: "HEAD",
            crossDomain: true,
            url: this.url,

            success: function() {
                console.debug("[SUCCESS] Connection established to the remote database:", this.url);
                Database.uploadResults();
            },

            error: function() {
                console.debug("[WARNING] Will try syncdb latter. Unable connect to database:", this.url);
            }
        });
    }
}

Trial = {
    create: function() {
        let get = RequestArgumentsFromURL();

        this.set({
            "trial": {
                timeout: parseFloat(get["timeout"]),
                device: get["device"],
                polarization: get["polarization"],
                location: get["location"],
                regularity: get["regularity"],
                colors: shuffle(["red", "white", "blue"]),
                attempt: get["attempt"],
                start_datetime: new Date().toJSON(),
                end_datetime: null
            }
        });

        console.debug("[SUCCESS] Trial created", Trial.get());
        return Trial.get();
    },

    getResults: function(datetime) {
            $.ajax({
                type: "GET",
                crossDomain: true,
                url: this.url,
                data: {start_datetime: this.start_datetime},

                success: function(response) {
                    console.debug(this.url);
                    //console.debug("[SUCCESS] Received response", response);
                    return response
                },

                error: function() {
                    console.debug("[ERROR] Cannot receive results for:", this.data);
                }
            });
    },

    config: function(key, value) {
        var conf = this.get().trial;

        if (!key)
            return conf;

        if (value) {
            conf[key] = value;
            this.update("trial", conf);
        }

        return conf[key];
    },

    get: function() {
        let data = localStorage.getItem(".temp");
        return JSON.parse(data);
    },

    set: function(data) {
        return localStorage.setItem(".temp", JSON.stringify(data));
    },

    update: function(key, value) {
        var data = this.get();
        data[key] = value;
        return this.set(data);
    },

    clear: function() {
        return this.set({});
    },

    save: function() {
        if (DEBUG) {
            alert("You're in DEBUG mode! Will not `Trial.save()`");
            return;
        }
        let trial = this.get();
        return Database.insert(trial);
    }
}

function RequestArgumentsFromURL() {
    let url = window.location.href;

    if (! url.includes("?"))
        return Array();

    let params = url.split("?").pop();
    var arguments = {}

    for (let param of params.split("&")) {
        let arg = param.split("=");
        let key = arg[0];
        let value = arg[1].replace(/%20/g, " ").replace(/\+/g, " ")
        arguments[key] = value;
    }

    return arguments;
}

// Knuth Random Shuffle Algorithm
function shuffle(array) {
    var currentIndex = array.length, temporaryValue, randomIndex;
    while (0 !== currentIndex) {
      randomIndex = Math.floor(Math.random() * currentIndex);
      currentIndex -= 1;
      temporaryValue = array[currentIndex];
      array[currentIndex] = array[randomIndex];
      array[randomIndex] = temporaryValue;
    }
    return array;
}

function sleep(seconds) {
    let milliseconds = seconds * 1000;
    return new Promise(resolve => setTimeout(resolve, milliseconds));
}

function goto(filename) {
    let url = window.location.href;
    let current = url.split("/").pop();
    let next = url.replace(current, filename+".html");
    window.location.replace(next);
}

function fullscreen() {
    let bg = document.querySelector("body");

    if (bg.webkitRequestFullScreen)
        bg.webkitRequestFullScreen();
    else
        bg.mozRequestFullScreen();
}

function log(action, target) {
    var trial = Trial.get();

    if (!trial.events)
        trial.events = Array();

    trial.events.push({
        datetime: new Date().toJSON(),
        target: target,
        action: action,
    });

    return Trial.set(trial);
}

function click() {
    var trial = Trial.get();

    if (!trial.clicks)
        trial.clicks = Array();

    trial.clicks.push({
        datetime: new Date().toJSON(),
        color: document.body.style.backgroundColor
    });

    return Trial.set(trial);
}

if (location.hostname !== "localhost" && location.hostname !== "127.0.0.1") {
  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){
  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),
  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)
  })(window,document,'script','https://www.google-analytics.com/analytics.js','ga');
  ga('create', 'UA-92351316-5', 'auto');
  ga('send', 'pageview');
}
<commit_msg>Fix for server URL #time 1m<commit_after>DEBUG = false

Database = {
    url: "http://stpa.astrotech.io/api/v2/",

    getItem: function(key) {
        return localStorage.getItem(key);
    },

    setItem: function(key, value) {
        return localStorage.setItem(key, value);
    },

    get: function() {
        database = Array();

        for (let key of Object.keys(localStorage)) {
            if (key != ".temp" && key != ".veteran") {
                let value = localStorage.getItem(key);
                database.push(JSON.parse(value));
            }
        }

        return database;
    },

    insert: function(trial) {
        console.debug("[SUCCESS] Trial saved to localStorage:", trial);
        return localStorage.setItem(trial.trial.start_datetime, JSON.stringify(trial));
    },

    delete: function(trial) {
        console.debug("[SUCCESS] Trial deleted from localStorage", trial);
        return localStorage.removeItem(trial.trial.start_datetime);
    },

    clear: function() {
        console.debug("[SUCCESS] Database in localStorage cleared");
        localStorage.clear();
        localStorage.setItem('.veteran', true);
    },

    uploadResults: function() {
        for (let trial of Database.get()) {
            $.ajax({
                type: "POST",
                crossDomain: true,
                url: this.url,
                data: JSON.stringify(trial),

                success: function(response) {
                    let trial = JSON.parse(this.data);
                    console.debug("[SUCCESS] Trial results uploaded to the remote database:", trial);
                    console.debug("[SUCCESS] Received response", response)
                    Database.delete(trial);
                    return response
                },

                error: function() {
                    let trial = JSON.parse(this.data);
                    console.debug("[WARNING] Will try syncdb latter:", trial);
                }
            });
        }
    },

    syncdb: function() {
        if (DEBUG) {
            alert("You're in DEBUG mode! Will not `Database.syncdb()`");
            return;
        }

        $.ajax({
            type: "HEAD",
            crossDomain: true,
            url: this.url,

            success: function() {
                console.debug("[SUCCESS] Connection established to the remote database:", this.url);
                Database.uploadResults();
            },

            error: function() {
                console.debug("[WARNING] Will try syncdb latter. Unable connect to database:", this.url);
            }
        });
    }
}

Trial = {
    create: function() {
        let get = RequestArgumentsFromURL();

        this.set({
            "trial": {
                timeout: parseFloat(get["timeout"]),
                device: get["device"],
                polarization: get["polarization"],
                location: get["location"],
                regularity: get["regularity"],
                colors: shuffle(["red", "white", "blue"]),
                attempt: get["attempt"],
                start_datetime: new Date().toJSON(),
                end_datetime: null
            }
        });

        console.debug("[SUCCESS] Trial created", Trial.get());
        return Trial.get();
    },

    getResults: function(datetime) {
            $.ajax({
                type: "GET",
                crossDomain: true,
                url: this.url,
                data: {start_datetime: this.start_datetime},

                success: function(response) {
                    console.debug(this.url);
                    //console.debug("[SUCCESS] Received response", response);
                    return response
                },

                error: function() {
                    console.debug("[ERROR] Cannot receive results for:", this.data);
                }
            });
    },

    config: function(key, value) {
        var conf = this.get().trial;

        if (!key)
            return conf;

        if (value) {
            conf[key] = value;
            this.update("trial", conf);
        }

        return conf[key];
    },

    get: function() {
        let data = localStorage.getItem(".temp");
        return JSON.parse(data);
    },

    set: function(data) {
        return localStorage.setItem(".temp", JSON.stringify(data));
    },

    update: function(key, value) {
        var data = this.get();
        data[key] = value;
        return this.set(data);
    },

    clear: function() {
        return this.set({});
    },

    save: function() {
        if (DEBUG) {
            alert("You're in DEBUG mode! Will not `Trial.save()`");
            return;
        }
        let trial = this.get();
        return Database.insert(trial);
    }
}

function RequestArgumentsFromURL() {
    let url = window.location.href;

    if (! url.includes("?"))
        return Array();

    let params = url.split("?").pop();
    var arguments = {}

    for (let param of params.split("&")) {
        let arg = param.split("=");
        let key = arg[0];
        let value = arg[1].replace(/%20/g, " ").replace(/\+/g, " ")
        arguments[key] = value;
    }

    return arguments;
}

// Knuth Random Shuffle Algorithm
function shuffle(array) {
    var currentIndex = array.length, temporaryValue, randomIndex;
    while (0 !== currentIndex) {
      randomIndex = Math.floor(Math.random() * currentIndex);
      currentIndex -= 1;
      temporaryValue = array[currentIndex];
      array[currentIndex] = array[randomIndex];
      array[randomIndex] = temporaryValue;
    }
    return array;
}

function sleep(seconds) {
    let milliseconds = seconds * 1000;
    return new Promise(resolve => setTimeout(resolve, milliseconds));
}

function goto(filename) {
    let url = window.location.href;
    let current = url.split("/").pop();
    let next = url.replace(current, filename+".html");
    window.location.replace(next);
}

function fullscreen() {
    let bg = document.querySelector("body");

    if (bg.webkitRequestFullScreen)
        bg.webkitRequestFullScreen();
    else
        bg.mozRequestFullScreen();
}

function log(action, target) {
    var trial = Trial.get();

    if (!trial.events)
        trial.events = Array();

    trial.events.push({
        datetime: new Date().toJSON(),
        target: target,
        action: action,
    });

    return Trial.set(trial);
}

function click() {
    var trial = Trial.get();

    if (!trial.clicks)
        trial.clicks = Array();

    trial.clicks.push({
        datetime: new Date().toJSON(),
        color: document.body.style.backgroundColor
    });

    return Trial.set(trial);
}

if (location.hostname !== "localhost" && location.hostname !== "127.0.0.1") {
  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){
  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),
  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)
  })(window,document,'script','https://www.google-analytics.com/analytics.js','ga');
  ga('create', 'UA-92351316-5', 'auto');
  ga('send', 'pageview');
}
<|endoftext|>


<commit_before>'use strict';

let net = require('net');
let status = require('./status');

let go = function() {

  let clientListener = net.createServer(function(client) {
    console.log('client connected to proxy');

    client.setEncoding('utf8');

    client.on('end', function() {
      console.log('client disconnected from proxy');
    });

    client.on('data', function(packet) {
      status.fromClient(packet);
      server.send(packet);
    });

    client.on('error', function(error) {
      console.log('CLIENT ERROR:\n' + error);
    });

    let sayHello = {
      from: "root",
      applicationType: 'browser',
      traits: {
        sources: true
      }
    };

    client.send = function(data) {
      let packet;
      if (typeof data !== 'string') {
        packet = JSON.stringify(data, null, 2);
        packet = packet.length + ':' + packet;
      } else {
        packet = data;
      }
      status.toClient(packet);
      client.write(packet);
    };

    //client.send(sayHello);

    let server = net.connect({ port: 6000 }, function() {
      console.log('proxy connected to server');
    });

    server.setEncoding('utf8');

    server.on('end', function() {
      console.log('server disconnected from proxy');
    });

    server.on('data', function(packet) {
      status.fromServer(packet);
      client.send(packet);
    });

    server.on('error', function(error) {
      console.log('SERVER ERROR:\n' + error);
    });

    server.send = function(data) {
      let packet;
      if (typeof data !== 'string') {
        packet = JSON.stringify(data, null, 2);
        packet = packet.length + ':' + packet;
      } else {
        packet = data;
      }
      status.toServer(packet);
      server.write(packet);
    };
  });

  let clientListenerPort = 6002;
  clientListener.listen(clientListenerPort, function() {
    console.log('proxy waiting for client on ' + clientListenerPort);
  });

};

module.exports = go;
<commit_msg>Remove sayHello<commit_after>'use strict';

let net = require('net');
let status = require('./status');

let go = function() {

  let clientListener = net.createServer(function(client) {
    console.log('client connected to proxy');

    client.setEncoding('utf8');

    client.on('end', function() {
      console.log('client disconnected from proxy');
    });

    client.on('data', function(packet) {
      status.fromClient(packet);
      server.send(packet);
    });

    client.on('error', function(error) {
      console.log('CLIENT ERROR:\n' + error);
    });

    client.send = function(data) {
      let packet;
      if (typeof data !== 'string') {
        packet = JSON.stringify(data, null, 2);
        packet = packet.length + ':' + packet;
      } else {
        packet = data;
      }
      status.toClient(packet);
      client.write(packet);
    };

    let server = net.connect({ port: 6000 }, function() {
      console.log('proxy connected to server');
    });

    server.setEncoding('utf8');

    server.on('end', function() {
      console.log('server disconnected from proxy');
    });

    server.on('data', function(packet) {
      status.fromServer(packet);
      client.send(packet);
    });

    server.on('error', function(error) {
      console.log('SERVER ERROR:\n' + error);
    });

    server.send = function(data) {
      let packet;
      if (typeof data !== 'string') {
        packet = JSON.stringify(data, null, 2);
        packet = packet.length + ':' + packet;
      } else {
        packet = data;
      }
      status.toServer(packet);
      server.write(packet);
    };
  });

  let clientListenerPort = 6002;
  clientListener.listen(clientListenerPort, function() {
    console.log('proxy waiting for client on ' + clientListenerPort);
  });

};

module.exports = go;
<|endoftext|>


<commit_before>require('envloader').load();
var express = require('express');
var cors = require('cors');
var bodyParser = require('body-parser');
var compression = require('compression');
var api = require('sat-api-lib');
var app = express();

var search = function (action, req, res) {
  var s = new api(req);
  s[action](function (err, resp) {
    if (err) {
      return res.status(400).send({details: err.message});
    }
    return res.send(resp);
  });
};

/*----------------------------------
// START MIDDLEWARES
----------------------------------*/
app.use(cors());
app.use(compression())
app.use(bodyParser.json({ type: 'application/json' })); // for parsing application/json
app.use(function(err, req, res, next) {
  console.error(err.stack);
  if (err.status === 400 && err.name === 'SyntaxError' && err.body) {
    res.status(err.status).send({details: 'Invalid JSON'})
  }

  res.status(err.status).send({details: err.body.slice(0, 100).toString()});
});
/*----------------------------------
// END MIDDLEWARES
----------------------------------*/

/*----------------------------------
// START ENDPOINTS
----------------------------------*/

/**
 * @api {get} / GET
 * @apiName /
 * @apiGroup search
 * @apiDescription Primary search functionality. Parameters listed are shared across satellites (Landsat-8 and Sentinel-2).
 * Satellite specific parameters can be searched on the in the same fashion (exact match).
 *
 * @apiParam {Number} limit=1 Limit of results to return.
 * @apiParam {Number} skip=0 Results to skip in return.
 * @apiParam {Number} page=1 Results page to view.
 * @apiParam {String} fields Comma separated list of fields to include in the query results. Ex: `?fields=scene_id,date,cloud_coverage`.
 * @apiParam {String} contains Comma separated lists of form `longitude,latitude`. Returns results if the point  is within the bounding box of an image. Ex `?contains=40.23,70.76`.
 * @apiParam {String} intersects Valid GeoJSON, returns results that touch any point of the geometry.
 * @apiParam {String} scene_id Performs exact search on sceneID field.
 * @apiParam {Number} cloud_from The lower limit for cloud_coverage field.
 * @apiParam {Number} cloud_to The upper limit for cloud_coverage field.
 *
 * @apiSuccess {Object} meta Metadata about the search endpoint.
 * @apiSuccess {Number} meta.found Total number of results returned from this query.
 * @apiSuccess {String} meta.name API name.
 * @apiSuccess {String} meta.license API license.
 * @apiSuccess {String} meta.website API endpoint.
 * @apiSuccess {Number} meta.page Results page being viewed.
 * @apiSuccess {Number} meta.limit Limit of results to return.
 * @apiSuccess {Object[]} results Query results.
 * @apiSuccess {String} results.scene_id Scene ID.
 * @apiSuccess {String} results.satellite_name Satellite name.
 * @apiSuccess {Number} results.cloud_coverage Cloud coverage.
 * @apiSuccess {String} results.date Date when image was taken.
 * @apiSuccess {String} results.thumbnail Thumbnail for the scene.
 * @apiSuccess {Object} results.data_geometry GeoJSON representing the scene outline.
 * @apiSuccessExample {json} Minimal Success Response:
 * HTTP/1.1 200 OK
 * {
 *   "meta": {
 *     "found": 2257062,
 *     "name": "sat-api",
 *     "license": "CC0-1.0",
 *     "website": "https://api.developmentseed.org/satellites/",
 *     "page": 1,
 *     "limit": 1
 *   },
 *   "results": [
 *     {
 *       "scene_id": "LC81000202017030LGN00",
 *       "satellite_name": "landsat-8",
 *       "cloud_coverage": 19.53,
 *       "date": "2017-01-30",
 *       "thumbnail": "https://ad-thumbnails.s3.amazonaws.com/LC81000202017030LGN00.jpg",
 *       "data_geometry": {
 *         "crs": {
 *           "type": "name",
 *           "properties": {
 *             "name": "urn:ogc:def:crs:EPSG:8.9:4326"
 *           }
 *         },
 *         "type": "Polygon",
 *         "coordinates": [
 *           [
 *             [
 *               161.38522,
 *               57.878
 *             ],
 *             [
 *               158.27701,
 *               58.39804
 *             ],
 *             [
 *               157.37548,
 *               56.70892
 *             ],
 *             [
 *               160.35236,
 *               56.20273
 *             ],
 *             [
 *               161.38522,
 *               57.878
 *             ]
 *           ]
 *         ]
 *       }
 *     }
 *   ]
 * }
 * @apiSuccessExample {json} Full Success Response:
 * HTTP/1.1 200 OK
 * {
 *   "meta": {
 *     "found": 2257062,
 *     "name": "sat-api",
 *     "license": "CC0-1.0",
 *     "website": "https://api.developmentseed.org/satellites/",
 *     "page": 1,
 *     "limit": 1
 *   },
 *   "results": [
 *     {
 *       "scene_id": "LC81000202017030LGN00",
 *       "satellite_name": "landsat-8",
 *       "cloud_coverage": 19.53,
 *       "date": "2017-01-30",
 *       "thumbnail": "https://ad-thumbnails.s3.amazonaws.com/LC81000202017030LGN00.jpg",
 *       "data_geometry": {
 *         "crs": {
 *           "type": "name",
 *           "properties": {
 *             "name": "urn:ogc:def:crs:EPSG:8.9:4326"
 *           }
 *         },
 *         "type": "Polygon",
 *         "coordinates": [
 *           [
 *             [
 *               161.38522,
 *               57.878
 *             ],
 *             [
 *               158.27701,
 *               58.39804
 *             ],
 *             [
 *               157.37548,
 *               56.70892
 *             ],
 *             [
 *               160.35236,
 *               56.20273
 *             ],
 *             [
 *               161.38522,
 *               57.878
 *             ]
 *           ]
 *         ]
 *       },
 *       "browseAvailable": "Y",
 *       "browseURL": "http://earthexplorer.usgs.gov/browse/landsat_8/2017/100/020/LC81000202017030LGN00.jpg",
 *       "sceneID": "LC81000202017030LGN00",
 *       "sensor": "OLI_TIRS",
 *       "acquisitionDate": "2017-01-30",
 *       "dateUpdated": "2017-01-29",
 *       "path": 100,
 *       "row": 20,
 *       "upperLeftCornerLatitude": 58.39804,
 *       "upperLeftCornerLongitude": 158.27701,
 *       "upperRightCornerLatitude": 57.878,
 *       "upperRightCornerLongitude": 161.38522,
 *       "lowerLeftCornerLatitude": 56.70892,
 *       "lowerLeftCornerLongitude": 157.37548,
 *       "lowerRightCornerLatitude": 56.20273,
 *       "lowerRightCornerLongitude": 160.35236,
 *       "sceneCenterLatitude": 57.30952,
 *       "sceneCenterLongitude": 159.3503,
 *       "cloudCover": 1,
 *       "cloudCoverFull": 19.53,
 *       "dayOrNight": "DAY",
 *       "sunElevation": 13.6553746,
 *       "sunAzimuth": 163.05483232,
 *       "receivingStation": "LGN",
 *       "sceneStartTime": "2017:030:00:26:23.6556890",
 *       "sceneStopTime": "2017:030:00:26:55.4256860",
 *       "imageQuality1": 9,
 *       "DATA_TYPE_L1": "L1T",
 *       "cartURL": "http://earthexplorer.usgs.gov/order/process?dataset_name=LANDSAT_8&ordered=LC81000202017030LGN00",
 *       "ROLL_ANGLE": -0.001,
 *       "GEOMETRIC_RMSE_MODEL_X": 10.185,
 *       "GEOMETRIC_RMSE_MODEL_Y": 11.822,
 *       "FULL_PARTIAL_SCENE": "FULL",
 *       "NADIR_OFFNADIR": "NADIR",
 *       "PROCESSING_SOFTWARE_VERSION": "LPGS_2.6.2",
 *       "CPF_NAME": "L8CPF20170101_20170331.02",
 *       "RLUT_FILE_NAME": "L8RLUT20150303_20431231v11.h5",
 *       "BPF_NAME_OLI": "LO8BPF20170130002250_20170130010416.01",
 *       "BPF_NAME_TIRS": "LT8BPF20170126095930_20170126100746.01",
 *       "GROUND_CONTROL_POINTS_MODEL": 178,
 *       "GROUND_CONTROL_POINTS_VERSION": 4,
 *       "DATE_L1_GENERATED": "2017-01-29 22:17:21",
 *       "TIRS_SSM_MODEL": "PRELIMINARY"
 *     }
 *   ]
 * }
 */

app.get('/', function(req, res) {
  search('simple', req, res);
});

app.post('/', function (req, res) {
  search('simple', {query: req.body}, res);
});

app.get('/landsat', function(req, res) {
  search('landsat', req, res);
});

app.post('/landsat', function (req, res) {
  search('landast', {query: req.body}, res);
});

app.get('/sentinel', function(req, res) {
  search('sentinel', req, res);
});

app.post('/sentinel', function (req, res) {
  search('sentinel', {query: req.body}, res);
});

app.get('/count', function(req, res) {
  search('count', req, res);
});

app.get('/geojson', function(req, res) {
  search('geojson', req, res);
});

app.post('/geojson', function(req, res) {
  search('geojson', {query: req.body}, res);
});

app.get('/health', function(req, res) {
  search('health', req, res);
});
/*----------------------------------
// END ENDPOINTS
----------------------------------*/

var port = process.env.PORT || 8000;
app.listen(port, function() {
  console.log('Listening on ' + port);
});
<commit_msg>Add parameter match example + date range to docs<commit_after>require('envloader').load();
var express = require('express');
var cors = require('cors');
var bodyParser = require('body-parser');
var compression = require('compression');
var api = require('sat-api-lib');
var app = express();

var search = function (action, req, res) {
  var s = new api(req);
  s[action](function (err, resp) {
    if (err) {
      return res.status(400).send({details: err.message});
    }
    return res.send(resp);
  });
};

/*----------------------------------
// START MIDDLEWARES
----------------------------------*/
app.use(cors());
app.use(compression())
app.use(bodyParser.json({ type: 'application/json' })); // for parsing application/json
app.use(function(err, req, res, next) {
  console.error(err.stack);
  if (err.status === 400 && err.name === 'SyntaxError' && err.body) {
    res.status(err.status).send({details: 'Invalid JSON'})
  }

  res.status(err.status).send({details: err.body.slice(0, 100).toString()});
});
/*----------------------------------
// END MIDDLEWARES
----------------------------------*/

/*----------------------------------
// START ENDPOINTS
----------------------------------*/

/**
 * @api {get} / GET
 * @apiName /
 * @apiGroup search
 * @apiDescription Primary search functionality. Parameters listed are shared across satellites (Landsat-8 and Sentinel-2).
 * Satellite specific parameters can be searched on via exact match like `path=30`.
 *
 * @apiParam {Number} limit=1 Limit of results to return.
 * @apiParam {Number} skip=0 Results to skip in return.
 * @apiParam {Number} page=1 Results page to view.
 * @apiParam {String} fields Comma separated list of fields to include in the query results. Ex: `?fields=scene_id,date,cloud_coverage`.
 * @apiParam {String} contains Comma separated lists of form `longitude,latitude`. Returns results if the point  is within the bounding box of an image. Ex `?contains=40.23,70.76`.
 * @apiParam {String} intersects Valid GeoJSON, returns results that touch any point of the geometry.
 * @apiParam {String} scene_id Performs exact search on sceneID field.
 * @apiParam {Number} cloud_from The lower limit for cloud_coverage field.
 * @apiParam {Number} cloud_to The upper limit for cloud_coverage field.
 * @apiParam {Number} date_from The lower limit for date field.
 * @apiParam {Number} date_to The upper limit for date field.
 *
 * @apiSuccess {Object} meta Metadata about the search endpoint.
 * @apiSuccess {Number} meta.found Total number of results returned from this query.
 * @apiSuccess {String} meta.name API name.
 * @apiSuccess {String} meta.license API license.
 * @apiSuccess {String} meta.website API endpoint.
 * @apiSuccess {Number} meta.page Results page being viewed.
 * @apiSuccess {Number} meta.limit Limit of results to return.
 * @apiSuccess {Object[]} results Query results.
 * @apiSuccess {String} results.scene_id Scene ID.
 * @apiSuccess {String} results.satellite_name Satellite name.
 * @apiSuccess {Number} results.cloud_coverage Cloud coverage.
 * @apiSuccess {String} results.date Date when image was taken.
 * @apiSuccess {String} results.thumbnail Thumbnail for the scene.
 * @apiSuccess {Object} results.data_geometry GeoJSON representing the scene outline.
 * @apiSuccessExample {json} Minimal Success Response:
 * HTTP/1.1 200 OK
 * {
 *   "meta": {
 *     "found": 2257062,
 *     "name": "sat-api",
 *     "license": "CC0-1.0",
 *     "website": "https://api.developmentseed.org/satellites/",
 *     "page": 1,
 *     "limit": 1
 *   },
 *   "results": [
 *     {
 *       "scene_id": "LC81000202017030LGN00",
 *       "satellite_name": "landsat-8",
 *       "cloud_coverage": 19.53,
 *       "date": "2017-01-30",
 *       "thumbnail": "https://ad-thumbnails.s3.amazonaws.com/LC81000202017030LGN00.jpg",
 *       "data_geometry": {
 *         "crs": {
 *           "type": "name",
 *           "properties": {
 *             "name": "urn:ogc:def:crs:EPSG:8.9:4326"
 *           }
 *         },
 *         "type": "Polygon",
 *         "coordinates": [
 *           [
 *             [
 *               161.38522,
 *               57.878
 *             ],
 *             [
 *               158.27701,
 *               58.39804
 *             ],
 *             [
 *               157.37548,
 *               56.70892
 *             ],
 *             [
 *               160.35236,
 *               56.20273
 *             ],
 *             [
 *               161.38522,
 *               57.878
 *             ]
 *           ]
 *         ]
 *       }
 *     }
 *   ]
 * }
 * @apiSuccessExample {json} Full Success Response:
 * HTTP/1.1 200 OK
 * {
 *   "meta": {
 *     "found": 2257062,
 *     "name": "sat-api",
 *     "license": "CC0-1.0",
 *     "website": "https://api.developmentseed.org/satellites/",
 *     "page": 1,
 *     "limit": 1
 *   },
 *   "results": [
 *     {
 *       "scene_id": "LC81000202017030LGN00",
 *       "satellite_name": "landsat-8",
 *       "cloud_coverage": 19.53,
 *       "date": "2017-01-30",
 *       "thumbnail": "https://ad-thumbnails.s3.amazonaws.com/LC81000202017030LGN00.jpg",
 *       "data_geometry": {
 *         "crs": {
 *           "type": "name",
 *           "properties": {
 *             "name": "urn:ogc:def:crs:EPSG:8.9:4326"
 *           }
 *         },
 *         "type": "Polygon",
 *         "coordinates": [
 *           [
 *             [
 *               161.38522,
 *               57.878
 *             ],
 *             [
 *               158.27701,
 *               58.39804
 *             ],
 *             [
 *               157.37548,
 *               56.70892
 *             ],
 *             [
 *               160.35236,
 *               56.20273
 *             ],
 *             [
 *               161.38522,
 *               57.878
 *             ]
 *           ]
 *         ]
 *       },
 *       "browseAvailable": "Y",
 *       "browseURL": "http://earthexplorer.usgs.gov/browse/landsat_8/2017/100/020/LC81000202017030LGN00.jpg",
 *       "sceneID": "LC81000202017030LGN00",
 *       "sensor": "OLI_TIRS",
 *       "acquisitionDate": "2017-01-30",
 *       "dateUpdated": "2017-01-29",
 *       "path": 100,
 *       "row": 20,
 *       "upperLeftCornerLatitude": 58.39804,
 *       "upperLeftCornerLongitude": 158.27701,
 *       "upperRightCornerLatitude": 57.878,
 *       "upperRightCornerLongitude": 161.38522,
 *       "lowerLeftCornerLatitude": 56.70892,
 *       "lowerLeftCornerLongitude": 157.37548,
 *       "lowerRightCornerLatitude": 56.20273,
 *       "lowerRightCornerLongitude": 160.35236,
 *       "sceneCenterLatitude": 57.30952,
 *       "sceneCenterLongitude": 159.3503,
 *       "cloudCover": 1,
 *       "cloudCoverFull": 19.53,
 *       "dayOrNight": "DAY",
 *       "sunElevation": 13.6553746,
 *       "sunAzimuth": 163.05483232,
 *       "receivingStation": "LGN",
 *       "sceneStartTime": "2017:030:00:26:23.6556890",
 *       "sceneStopTime": "2017:030:00:26:55.4256860",
 *       "imageQuality1": 9,
 *       "DATA_TYPE_L1": "L1T",
 *       "cartURL": "http://earthexplorer.usgs.gov/order/process?dataset_name=LANDSAT_8&ordered=LC81000202017030LGN00",
 *       "ROLL_ANGLE": -0.001,
 *       "GEOMETRIC_RMSE_MODEL_X": 10.185,
 *       "GEOMETRIC_RMSE_MODEL_Y": 11.822,
 *       "FULL_PARTIAL_SCENE": "FULL",
 *       "NADIR_OFFNADIR": "NADIR",
 *       "PROCESSING_SOFTWARE_VERSION": "LPGS_2.6.2",
 *       "CPF_NAME": "L8CPF20170101_20170331.02",
 *       "RLUT_FILE_NAME": "L8RLUT20150303_20431231v11.h5",
 *       "BPF_NAME_OLI": "LO8BPF20170130002250_20170130010416.01",
 *       "BPF_NAME_TIRS": "LT8BPF20170126095930_20170126100746.01",
 *       "GROUND_CONTROL_POINTS_MODEL": 178,
 *       "GROUND_CONTROL_POINTS_VERSION": 4,
 *       "DATE_L1_GENERATED": "2017-01-29 22:17:21",
 *       "TIRS_SSM_MODEL": "PRELIMINARY"
 *     }
 *   ]
 * }
 */

app.get('/', function(req, res) {
  search('simple', req, res);
});

app.post('/', function (req, res) {
  search('simple', {query: req.body}, res);
});

app.get('/landsat', function(req, res) {
  search('landsat', req, res);
});

app.post('/landsat', function (req, res) {
  search('landast', {query: req.body}, res);
});

app.get('/sentinel', function(req, res) {
  search('sentinel', req, res);
});

app.post('/sentinel', function (req, res) {
  search('sentinel', {query: req.body}, res);
});

app.get('/count', function(req, res) {
  search('count', req, res);
});

app.get('/geojson', function(req, res) {
  search('geojson', req, res);
});

app.post('/geojson', function(req, res) {
  search('geojson', {query: req.body}, res);
});

app.get('/health', function(req, res) {
  search('health', req, res);
});
/*----------------------------------
// END ENDPOINTS
----------------------------------*/

var port = process.env.PORT || 8000;
app.listen(port, function() {
  console.log('Listening on ' + port);
});
<|endoftext|>


<commit_before>/*
 * L.DivIcon is a lightweight HTML-based icon class (as opposed to the image-based L.Icon)
 * to use with L.Marker.
 */

L.DivIcon = L.Icon.extend({
	options: {
		iconSize: [12, 12], // also can be set through CSS
		/*
		iconAnchor: (Point)
		popupAnchor: (Point)
		html: (String)
		bgPos: (Point)
		*/
		className: 'leaflet-div-icon'
	},

	createIcon: function () {
		var div = document.createElement('div'),
		    options = this.options;

		if (options.html) {
			div.innerHTML = options.html;
		}

		if (options.bgPos) {
			div.style.backgroundPosition =
			        (-options.bgPos.x) + 'px ' + (-options.bgPos.y) + 'px';
		}

		this._setIconStyles(div, 'icon');
		return div;
	},

	createShadow: function () {
		return null;
	}
});

L.divIcon = function (options) {
	return new L.DivIcon(options);
};
<commit_msg>Allow value of 0 in L.DivIcon's html parameter<commit_after>/*
 * L.DivIcon is a lightweight HTML-based icon class (as opposed to the image-based L.Icon)
 * to use with L.Marker.
 */

L.DivIcon = L.Icon.extend({
	options: {
		iconSize: [12, 12], // also can be set through CSS
		/*
		iconAnchor: (Point)
		popupAnchor: (Point)
		html: (String)
		bgPos: (Point)
		*/
		className: 'leaflet-div-icon',
		html: false
	},

	createIcon: function () {
		var div = document.createElement('div'),
		    options = this.options;

		if (options.html !== false) {
			div.innerHTML = options.html;
		}

		if (options.bgPos) {
			div.style.backgroundPosition =
			        (-options.bgPos.x) + 'px ' + (-options.bgPos.y) + 'px';
		}

		this._setIconStyles(div, 'icon');
		return div;
	},

	createShadow: function () {
		return null;
	}
});

L.divIcon = function (options) {
	return new L.DivIcon(options);
};
<|endoftext|>