<commit_before>/**
* @author       Richard Davey <rich@photonstorm.com>
* @copyright    2016 Photon Storm Ltd.
* @license      {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/

/**
* The LoadTexture component manages the loading of a texture into the Game Object and the changing of frames.
*
* @class
*/
Phaser.Component.LoadTexture = function () {};

Phaser.Component.LoadTexture.prototype = {

    /**
    * @property {boolean} customRender - Does this texture require a custom render call? (as set by BitmapData, Video, etc)
    * @private
    */
    customRender: false,

    /**
    * @property {Phaser.Rectangle} _frame - Internal cache var.
    * @private
    */
    _frame: null,

    /**
    * Changes the base texture the Game Object is using. The old texture is removed and the new one is referenced or fetched from the Cache.
    *
    * If your Game Object is using a frame from a texture atlas and you just wish to change to another frame, then see the `frame` or `frameName` properties instead.
    *
    * You should only use `loadTexture` if you want to replace the base texture entirely.
    *
    * Calling this method causes a WebGL texture update, so use sparingly or in low-intensity portions of your game, or if you know the new texture is already on the GPU.
    *
    * You can use the new const `Phaser.PENDING_ATLAS` as the texture key for any sprite.
    * Doing this then sets the key to be the `frame` argument (the frame is set to zero).
    *
    * This allows you to create sprites using `load.image` during development, and then change them
    * to use a Texture Atlas later in development by simply searching your code for 'PENDING_ATLAS'
    * and swapping it to be the key of the atlas data.
    *
    * @method
    * @param {string|Phaser.RenderTexture|Phaser.BitmapData|Phaser.Video|PIXI.Texture} key - This is the image or texture used by the Sprite during rendering. It can be a string which is a reference to the Cache Image entry, or an instance of a RenderTexture, BitmapData, Video or PIXI.Texture.
    * @param {string|number} [frame] - If this Sprite is using part of a sprite sheet or texture atlas you can specify the exact frame to use by giving a string or numeric index.
    * @param {boolean} [stopAnimation=true] - If an animation is already playing on this Sprite you can choose to stop it or let it carry on playing.
    */
    loadTexture: function (key, frame, stopAnimation) {

        if (key === Phaser.PENDING_ATLAS)
        {
            key = frame;
            frame = 0;
        }
        else
        {
            frame = frame || 0;
        }

        if ((stopAnimation || stopAnimation === undefined) && this.animations)
        {
            this.animations.stop();
        }

        this.key = key;
        this.customRender = false;
        var cache = this.game.cache;

        var setFrame = true;
        var smoothed = !this.texture.baseTexture.scaleMode;

        if (Phaser.RenderTexture && key instanceof Phaser.RenderTexture)
        {
            this.key = key.key;
            this.setTexture(key);
        }
        else if (Phaser.BitmapData && key instanceof Phaser.BitmapData)
        {
            this.customRender = true;

            this.setTexture(key.texture);

            if (cache.hasFrameData(key.key, Phaser.Cache.BITMAPDATA))
            {
                setFrame = !this.animations.loadFrameData(cache.getFrameData(key.key, Phaser.Cache.BITMAPDATA), frame);
            }
            else
            {
                setFrame = !this.animations.loadFrameData(key.frameData, 0);
            }
        }
        else if (Phaser.Video && key instanceof Phaser.Video)
        {
            this.customRender = true;

            //  This works from a reference, which probably isn't what we need here
            var valid = key.texture.valid;
            this.setTexture(key.texture);
            this.setFrame(key.texture.frame.clone());
            key.onChangeSource.add(this.resizeFrame, this);
            this.texture.valid = valid;
        }
        else if (key instanceof PIXI.Texture)
        {
            this.setTexture(key);
        }
        else
        {
            var img = cache.getImage(key, true);

            this.key = img.key;
            this.setTexture(new PIXI.Texture(img.base));

            if (key === '__default')
            {
                this.texture.baseTexture.skipRender = true;
            }
            else
            {
                this.texture.baseTexture.skipRender = false;
            }

            setFrame = !this.animations.loadFrameData(img.frameData, frame);
        }

        if (setFrame)
        {
            this._frame = Phaser.Rectangle.clone(this.texture.frame);
        }

        if (!smoothed)
        {
            this.texture.baseTexture.scaleMode = 1;
        }

    },

    /**
    * Sets the texture frame the Game Object uses for rendering.
    *
    * This is primarily an internal method used by `loadTexture`, but is exposed for the use of plugins and custom classes.
    *
    * @method
    * @param {Phaser.Frame} frame - The Frame to be used by the texture.
    */
    setFrame: function (frame) {

        this._frame = frame;

        this.texture.frame.x = frame.x;
        this.texture.frame.y = frame.y;
        this.texture.frame.width = frame.width;
        this.texture.frame.height = frame.height;

        this.texture.crop.x = frame.x;
        this.texture.crop.y = frame.y;
        this.texture.crop.width = frame.width;
        this.texture.crop.height = frame.height;

        if (frame.trimmed)
        {
            if (this.texture.trim)
            {
                this.texture.trim.x = frame.spriteSourceSizeX;
                this.texture.trim.y = frame.spriteSourceSizeY;
                this.texture.trim.width = frame.sourceSizeW;
                this.texture.trim.height = frame.sourceSizeH;
            }
            else
            {
                this.texture.trim = { x: frame.spriteSourceSizeX, y: frame.spriteSourceSizeY, width: frame.sourceSizeW, height: frame.sourceSizeH };
            }

            this.texture.width = frame.sourceSizeW;
            this.texture.height = frame.sourceSizeH;
            this.texture.frame.width = frame.sourceSizeW;
            this.texture.frame.height = frame.sourceSizeH;
        }
        else if (!frame.trimmed && this.texture.trim)
        {
            this.texture.trim = null;
        }

        if (this.cropRect)
        {
            this.updateCrop();
        }

        this.texture.requiresReTint = true;

        this.texture._updateUvs();

        if (this.tilingTexture)
        {
            this.refreshTexture = true;
        }

    },

    /**
    * Resizes the Frame dimensions that the Game Object uses for rendering.
    *
    * You shouldn't normally need to ever call this, but in the case of special texture types such as Video or BitmapData
    * it can be useful to adjust the dimensions directly in this way.
    *
    * @method
    * @param {object} parent - The parent texture object that caused the resize, i.e. a Phaser.Video object.
    * @param {integer} width - The new width of the texture.
    * @param {integer} height - The new height of the texture.
    */
    resizeFrame: function (parent, width, height) {

        this.texture.frame.resize(width, height);
        this.texture.setFrame(this.texture.frame);

    },

    /**
    * Resets the texture frame dimensions that the Game Object uses for rendering.
    *
    * @method
    */
    resetFrame: function () {

        if (this._frame)
        {
            this.setFrame(this._frame);
        }

    },

    /**
    * Gets or sets the current frame index of the texture being used to render this Game Object.
    *
    * To change the frame set `frame` to the index of the new frame in the sprite sheet you wish this Game Object to use,
    * for example: `player.frame = 4`.
    *
    * If the frame index given doesn't exist it will revert to the first frame found in the texture.
    *
    * If you are using a texture atlas then you should use the `frameName` property instead.
    *
    * If you wish to fully replace the texture being used see `loadTexture`.
    * @property {integer} frame
    */
    frame: {

        get: function () {
            return this.animations.frame;
        },

        set: function (value) {
            this.animations.frame = value;
        }

    },

    /**
    * Gets or sets the current frame name of the texture being used to render this Game Object.
    *
    * To change the frame set `frameName` to the name of the new frame in the texture atlas you wish this Game Object to use,
    * for example: `player.frameName = "idle"`.
    *
    * If the frame name given doesn't exist it will revert to the first frame found in the texture and throw a console warning.
    *
    * If you are using a sprite sheet then you should use the `frame` property instead.
    *
    * If you wish to fully replace the texture being used see `loadTexture`.
    * @property {string} frameName
    */
    frameName: {

        get: function () {
            return this.animations.frameName;
        },

        set: function (value) {
            this.animations.frameName = value;
        }

    }

};
<commit_msg>jsdocs update #2384<commit_after>/**
* @author       Richard Davey <rich@photonstorm.com>
* @copyright    2016 Photon Storm Ltd.
* @license      {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/

/**
* The LoadTexture component manages the loading of a texture into the Game Object and the changing of frames.
*
* @class
*/
Phaser.Component.LoadTexture = function () {};

Phaser.Component.LoadTexture.prototype = {

    /**
    * @property {boolean} customRender - Does this texture require a custom render call? (as set by BitmapData, Video, etc)
    * @private
    */
    customRender: false,

    /**
    * @property {Phaser.Rectangle} _frame - Internal cache var.
    * @private
    */
    _frame: null,

    /**
    * Changes the base texture the Game Object is using. The old texture is removed and the new one is referenced or fetched from the Cache.
    *
    * If your Game Object is using a frame from a texture atlas and you just wish to change to another frame, then see the `frame` or `frameName` properties instead.
    *
    * You should only use `loadTexture` if you want to replace the base texture entirely.
    *
    * Calling this method causes a WebGL texture update, so use sparingly or in low-intensity portions of your game, or if you know the new texture is already on the GPU.
    *
    * You can use the new const `Phaser.PENDING_ATLAS` as the texture key for any sprite.
    * Doing this then sets the key to be the `frame` argument (the frame is set to zero).
    *
    * This allows you to create sprites using `load.image` during development, and then change them
    * to use a Texture Atlas later in development by simply searching your code for 'PENDING_ATLAS'
    * and swapping it to be the key of the atlas data.
    *
    * Note: You cannot use a RenderTexture as a texture for a TileSprite.
    *
    * @method
    * @param {string|Phaser.RenderTexture|Phaser.BitmapData|Phaser.Video|PIXI.Texture} key - This is the image or texture used by the Sprite during rendering. It can be a string which is a reference to the Cache Image entry, or an instance of a RenderTexture, BitmapData, Video or PIXI.Texture.
    * @param {string|number} [frame] - If this Sprite is using part of a sprite sheet or texture atlas you can specify the exact frame to use by giving a string or numeric index.
    * @param {boolean} [stopAnimation=true] - If an animation is already playing on this Sprite you can choose to stop it or let it carry on playing.
    */
    loadTexture: function (key, frame, stopAnimation) {

        if (key === Phaser.PENDING_ATLAS)
        {
            key = frame;
            frame = 0;
        }
        else
        {
            frame = frame || 0;
        }

        if ((stopAnimation || stopAnimation === undefined) && this.animations)
        {
            this.animations.stop();
        }

        this.key = key;
        this.customRender = false;
        var cache = this.game.cache;

        var setFrame = true;
        var smoothed = !this.texture.baseTexture.scaleMode;

        if (Phaser.RenderTexture && key instanceof Phaser.RenderTexture)
        {
            this.key = key.key;
            this.setTexture(key);
        }
        else if (Phaser.BitmapData && key instanceof Phaser.BitmapData)
        {
            this.customRender = true;

            this.setTexture(key.texture);

            if (cache.hasFrameData(key.key, Phaser.Cache.BITMAPDATA))
            {
                setFrame = !this.animations.loadFrameData(cache.getFrameData(key.key, Phaser.Cache.BITMAPDATA), frame);
            }
            else
            {
                setFrame = !this.animations.loadFrameData(key.frameData, 0);
            }
        }
        else if (Phaser.Video && key instanceof Phaser.Video)
        {
            this.customRender = true;

            //  This works from a reference, which probably isn't what we need here
            var valid = key.texture.valid;
            this.setTexture(key.texture);
            this.setFrame(key.texture.frame.clone());
            key.onChangeSource.add(this.resizeFrame, this);
            this.texture.valid = valid;
        }
        else if (key instanceof PIXI.Texture)
        {
            this.setTexture(key);
        }
        else
        {
            var img = cache.getImage(key, true);

            this.key = img.key;
            this.setTexture(new PIXI.Texture(img.base));

            if (key === '__default')
            {
                this.texture.baseTexture.skipRender = true;
            }
            else
            {
                this.texture.baseTexture.skipRender = false;
            }

            setFrame = !this.animations.loadFrameData(img.frameData, frame);
        }

        if (setFrame)
        {
            this._frame = Phaser.Rectangle.clone(this.texture.frame);
        }

        if (!smoothed)
        {
            this.texture.baseTexture.scaleMode = 1;
        }

    },

    /**
    * Sets the texture frame the Game Object uses for rendering.
    *
    * This is primarily an internal method used by `loadTexture`, but is exposed for the use of plugins and custom classes.
    *
    * @method
    * @param {Phaser.Frame} frame - The Frame to be used by the texture.
    */
    setFrame: function (frame) {

        this._frame = frame;

        this.texture.frame.x = frame.x;
        this.texture.frame.y = frame.y;
        this.texture.frame.width = frame.width;
        this.texture.frame.height = frame.height;

        this.texture.crop.x = frame.x;
        this.texture.crop.y = frame.y;
        this.texture.crop.width = frame.width;
        this.texture.crop.height = frame.height;

        if (frame.trimmed)
        {
            if (this.texture.trim)
            {
                this.texture.trim.x = frame.spriteSourceSizeX;
                this.texture.trim.y = frame.spriteSourceSizeY;
                this.texture.trim.width = frame.sourceSizeW;
                this.texture.trim.height = frame.sourceSizeH;
            }
            else
            {
                this.texture.trim = { x: frame.spriteSourceSizeX, y: frame.spriteSourceSizeY, width: frame.sourceSizeW, height: frame.sourceSizeH };
            }

            this.texture.width = frame.sourceSizeW;
            this.texture.height = frame.sourceSizeH;
            this.texture.frame.width = frame.sourceSizeW;
            this.texture.frame.height = frame.sourceSizeH;
        }
        else if (!frame.trimmed && this.texture.trim)
        {
            this.texture.trim = null;
        }

        if (this.cropRect)
        {
            this.updateCrop();
        }

        this.texture.requiresReTint = true;

        this.texture._updateUvs();

        if (this.tilingTexture)
        {
            this.refreshTexture = true;
        }

    },

    /**
    * Resizes the Frame dimensions that the Game Object uses for rendering.
    *
    * You shouldn't normally need to ever call this, but in the case of special texture types such as Video or BitmapData
    * it can be useful to adjust the dimensions directly in this way.
    *
    * @method
    * @param {object} parent - The parent texture object that caused the resize, i.e. a Phaser.Video object.
    * @param {integer} width - The new width of the texture.
    * @param {integer} height - The new height of the texture.
    */
    resizeFrame: function (parent, width, height) {

        this.texture.frame.resize(width, height);
        this.texture.setFrame(this.texture.frame);

    },

    /**
    * Resets the texture frame dimensions that the Game Object uses for rendering.
    *
    * @method
    */
    resetFrame: function () {

        if (this._frame)
        {
            this.setFrame(this._frame);
        }

    },

    /**
    * Gets or sets the current frame index of the texture being used to render this Game Object.
    *
    * To change the frame set `frame` to the index of the new frame in the sprite sheet you wish this Game Object to use,
    * for example: `player.frame = 4`.
    *
    * If the frame index given doesn't exist it will revert to the first frame found in the texture.
    *
    * If you are using a texture atlas then you should use the `frameName` property instead.
    *
    * If you wish to fully replace the texture being used see `loadTexture`.
    * @property {integer} frame
    */
    frame: {

        get: function () {
            return this.animations.frame;
        },

        set: function (value) {
            this.animations.frame = value;
        }

    },

    /**
    * Gets or sets the current frame name of the texture being used to render this Game Object.
    *
    * To change the frame set `frameName` to the name of the new frame in the texture atlas you wish this Game Object to use,
    * for example: `player.frameName = "idle"`.
    *
    * If the frame name given doesn't exist it will revert to the first frame found in the texture and throw a console warning.
    *
    * If you are using a sprite sheet then you should use the `frame` property instead.
    *
    * If you wish to fully replace the texture being used see `loadTexture`.
    * @property {string} frameName
    */
    frameName: {

        get: function () {
            return this.animations.frameName;
        },

        set: function (value) {
            this.animations.frameName = value;
        }

    }

};
<|endoftext|>


<commit_before>define([
	'goo/loaders/handlers/ConfigHandler',
	'goo/loaders/handlers/ComponentHandler',
	'goo/util/rsvp',
	'goo/util/StringUtils',
	'goo/util/PromiseUtils'
], function (
	ConfigHandler,
	ComponentHandler,
	RSVP,
	StringUtils,
	PromiseUtils
) {
	'use strict';

	/**
	 * Handler for loading entities into engine
	 * @extends ConfigHandler
	 * @param {World} world
	 * @param {Function} getConfig
	 * @param {Function} updateObject
	 * @private
	 */
	function EntityHandler() {
		ConfigHandler.apply(this, arguments);
		this._componentHandlers = {};
	}

	EntityHandler.prototype = Object.create(ConfigHandler.prototype);
	EntityHandler.prototype.constructor = EntityHandler;
	ConfigHandler._registerClass('entity', EntityHandler);

	/**
	 * Creates an empty entity
	 * @param {string} ref will be the entity's id
	 * @returns {Entity}
	 * @private
	 */
	EntityHandler.prototype._create = function () {
		return this.world.createEntity();
	};

	/**
	 * Removes an entity
	 * @param {ref}
	 * @private
	 */
	EntityHandler.prototype._remove = function (ref) {
		var entity = this._objects.get(ref);
		var that = this;
		if (entity) {
			// Remove components
			var promises = [];
			var components = entity._components.slice(0);
			for (var i = 0; i < components.length; i++) {
				var type = this._getComponentType(components[i]);
				var p = this._updateComponent(entity, type, null);
				if (p instanceof RSVP.Promise) {
					promises.push(p);
				}
			}
			return RSVP.all(promises)
			.then(function () {
				entity.removeFromWorld();
				that._objects.delete(ref);
			});
		}
	};

	function updateTags(entity, tags) {
		entity._tags.clear();
		if (!tags) { return; }

		for (var tag in tags) {
			entity.setTag(tag);
		}
	}

	function updateAttributes(entity, attributes) {
		entity._attributes.clear();
		if (!attributes) { return; }

		for (var attribute in attributes) {
			entity.setAttribute(attribute, attributes[attribute]);
		}
	}

	/**
	 * Adds/updates/removes an entity
	 * @param {string} ref
	 * @param {Object} config
	 * @param {Object} options
	 * @returns {RSVP.Promise} Resolves with the updated entity or null if removed
	 */
	EntityHandler.prototype._update = function (ref, config, options) {
		var that = this;
		return ConfigHandler.prototype._update.call(this, ref, config, options).then(function (entity) {
			if (!entity) { return; }
			entity.id = ref;
			entity.name = config.name;
			entity.static = !!config.static;

			updateTags(entity, config.tags);
			updateAttributes(entity, config.meta);

			var promises = [];

			// Adding/updating components
			for (var type in config.components) {
				if (config.components[type]) {
					var p = that._updateComponent(entity, type, config.components[type], options);
					if (p) { promises.push(p); }
					else {
						console.error('Error handling component ' + type);
					}
				}
			}

			// Removing components
			var components = entity._components;
			for (var i = 0; i < components.length; i++) {
				var type = that._getComponentType(components[i]);
				if (!config.components[type]) {
					that._updateComponent(entity, type, null, options);
				}
			}
			// When all is done, hide or show and return
			return PromiseUtils.optimisticAll(promises).then(function (/*components*/) {
				if (config.hidden) {
					entity.hide();
				} else {
					entity.show();
				}
				return entity;
			});
		});
	};

	/**
	 * Adds/updates/removes a component on an entity
	 * @param {Entity} entity
	 * @param {string} type
	 * @param {Object} config
	 * @param {Object} options
	 * @returns {RSVP.Promise} Resolves with updated entity
	 * @private
	 */
	EntityHandler.prototype._updateComponent = function (entity, type, config, options) {
		var handler = this._getHandler(type);
		if (!handler) { return null; }

		var p = handler.update(entity, config, options);
		if (!p || !p.then) { return null; }

		return p;
	};

	/**
	 * Get the type for the component. Needed to match engine components against data model
	 * component types.
	 * @param {Component} component
	 * @returns {string}
	 * @private
	 */
	EntityHandler.prototype._getComponentType = function (component) {
		var type = component.type;
		type = type.slice(0, type.lastIndexOf('Component'));
		type = StringUtils.uncapitalize(type);
		if (type === 'howler') { type = 'sound'; } // HowlerComponent should be renamed
		return type;
	};

	/**
	 * Gets the handler for a component type or creates a new one if necessary
	 * @param {string} type
	 * @returns {ComponentHandler}
	 */
	EntityHandler.prototype._getHandler = function (type) {
		if (!this._componentHandlers[type]) {
			var Handler = ComponentHandler.getHandler(type);
			if (Handler) {
				this._componentHandlers[type] = new Handler(
					this.world,
					this.getConfig,
					this.updateObject,
					this.loadObject
				);
			}
		}
		return this._componentHandlers[type];
	};

	return EntityHandler;
});
<commit_msg>Rename entityConfig.meta to entityConfig.attributes.<commit_after>define([
	'goo/loaders/handlers/ConfigHandler',
	'goo/loaders/handlers/ComponentHandler',
	'goo/util/rsvp',
	'goo/util/StringUtils',
	'goo/util/PromiseUtils'
], function (
	ConfigHandler,
	ComponentHandler,
	RSVP,
	StringUtils,
	PromiseUtils
) {
	'use strict';

	/**
	 * Handler for loading entities into engine
	 * @extends ConfigHandler
	 * @param {World} world
	 * @param {Function} getConfig
	 * @param {Function} updateObject
	 * @private
	 */
	function EntityHandler() {
		ConfigHandler.apply(this, arguments);
		this._componentHandlers = {};
	}

	EntityHandler.prototype = Object.create(ConfigHandler.prototype);
	EntityHandler.prototype.constructor = EntityHandler;
	ConfigHandler._registerClass('entity', EntityHandler);

	/**
	 * Creates an empty entity
	 * @param {string} ref will be the entity's id
	 * @returns {Entity}
	 * @private
	 */
	EntityHandler.prototype._create = function () {
		return this.world.createEntity();
	};

	/**
	 * Removes an entity
	 * @param {ref}
	 * @private
	 */
	EntityHandler.prototype._remove = function (ref) {
		var entity = this._objects.get(ref);
		var that = this;
		if (entity) {
			// Remove components
			var promises = [];
			var components = entity._components.slice(0);
			for (var i = 0; i < components.length; i++) {
				var type = this._getComponentType(components[i]);
				var p = this._updateComponent(entity, type, null);
				if (p instanceof RSVP.Promise) {
					promises.push(p);
				}
			}
			return RSVP.all(promises)
			.then(function () {
				entity.removeFromWorld();
				that._objects.delete(ref);
			});
		}
	};

	function updateTags(entity, tags) {
		entity._tags.clear();
		if (!tags) { return; }

		for (var tag in tags) {
			entity.setTag(tag);
		}
	}

	function updateAttributes(entity, attributes) {
		entity._attributes.clear();
		if (!attributes) { return; }

		for (var attribute in attributes) {
			entity.setAttribute(attribute, attributes[attribute]);
		}
	}

	/**
	 * Adds/updates/removes an entity
	 * @param {string} ref
	 * @param {Object} config
	 * @param {Object} options
	 * @returns {RSVP.Promise} Resolves with the updated entity or null if removed
	 */
	EntityHandler.prototype._update = function (ref, config, options) {
		var that = this;
		return ConfigHandler.prototype._update.call(this, ref, config, options).then(function (entity) {
			if (!entity) { return; }
			entity.id = ref;
			entity.name = config.name;
			entity.static = !!config.static;

			updateTags(entity, config.tags);
			updateAttributes(entity, config.attributes);

			var promises = [];

			// Adding/updating components
			for (var type in config.components) {
				if (config.components[type]) {
					var p = that._updateComponent(entity, type, config.components[type], options);
					if (p) { promises.push(p); }
					else {
						console.error('Error handling component ' + type);
					}
				}
			}

			// Removing components
			var components = entity._components;
			for (var i = 0; i < components.length; i++) {
				var type = that._getComponentType(components[i]);
				if (!config.components[type]) {
					that._updateComponent(entity, type, null, options);
				}
			}
			// When all is done, hide or show and return
			return PromiseUtils.optimisticAll(promises).then(function (/*components*/) {
				if (config.hidden) {
					entity.hide();
				} else {
					entity.show();
				}
				return entity;
			});
		});
	};

	/**
	 * Adds/updates/removes a component on an entity
	 * @param {Entity} entity
	 * @param {string} type
	 * @param {Object} config
	 * @param {Object} options
	 * @returns {RSVP.Promise} Resolves with updated entity
	 * @private
	 */
	EntityHandler.prototype._updateComponent = function (entity, type, config, options) {
		var handler = this._getHandler(type);
		if (!handler) { return null; }

		var p = handler.update(entity, config, options);
		if (!p || !p.then) { return null; }

		return p;
	};

	/**
	 * Get the type for the component. Needed to match engine components against data model
	 * component types.
	 * @param {Component} component
	 * @returns {string}
	 * @private
	 */
	EntityHandler.prototype._getComponentType = function (component) {
		var type = component.type;
		type = type.slice(0, type.lastIndexOf('Component'));
		type = StringUtils.uncapitalize(type);
		if (type === 'howler') { type = 'sound'; } // HowlerComponent should be renamed
		return type;
	};

	/**
	 * Gets the handler for a component type or creates a new one if necessary
	 * @param {string} type
	 * @returns {ComponentHandler}
	 */
	EntityHandler.prototype._getHandler = function (type) {
		if (!this._componentHandlers[type]) {
			var Handler = ComponentHandler.getHandler(type);
			if (Handler) {
				this._componentHandlers[type] = new Handler(
					this.world,
					this.getConfig,
					this.updateObject,
					this.loadObject
				);
			}
		}
		return this._componentHandlers[type];
	};

	return EntityHandler;
});
<|endoftext|>


<commit_before>var _ = require('lodash');
var url_utils = require('url');

var utils = require('../utils');
var BaseError = utils.BaseError;
var Extendable = utils.Extendable;

var events = require('../events');
var Eventable = events.Eventable;

var HttpApiError = BaseError.extend(function(self) {
    /**class:HttpApiError()

    Thrown when an error occurs while making and checking an HTTP request and
    the corresponding API reply.
    */
    self.name = "HttpApiError";
});

var HttpRequestError = BaseError.extend(function(self, request, reason) {
    /**class:HttpRequestError(request, reason)

    Thrown when an error occurs while making and checking an HTTP request.

    :param HttpRequest request: the request.
    :param string reason: the reason for the failure. Optional.
    */
    self.name = "HttpRequestError";
    self.request = request;
    self.reason = reason || null;

    if (self.reason) {
        self.message = [self.reason, self.request].join(' ');
    } else {
        self.message = self.request.toString();
    }
});

var HttpResponseError = BaseError.extend(function(self, response, reason) {
    /**class:HttpResponseError(response, reason)

    Thrown when an error response is returned by an HTTP request or if the HTTP
    response body cannot be parsed.

    :param HttpResponse response: the response.
    :param string reason: the reason for the failure. Optional.
    */
    self.name = "HttpResponseError";
    self.response = response;
    self.reason = reason || null;

    if (self.reason) {
        self.message = [self.reason, self.response].join(' ');
    } else {
        self.message = self.response.toString();
    }
});

var HttpRequest = Extendable.extend(function(self, method, url, opts) {
    /**class:HttpRequest(request, code, opts)

    Encapsulates information about an HTTP request made by the
    :class:`HttpApi`. Once :meth:`HttpRequest.encode` has been invoked,
    the request's data is encoded and made available as the request's body.

    :param string method:
        the HTTP request method.
    :param string url:
        the url to send the request to.
    :param string opts.data:
        the request's data to be encoded as the request's body. Optional.
    :param opts.params:
        An object of key-value pairs to append to the URL as query
        parameters. Can be in any form accepted by node.js's querystring
        module
    :param string opts.verify_options:
        A list of options to verify when doing an HTTPS request. Optional.
    :param string opts.ssl_method:
        A request for a specific ssl method to be attempted. Optional.
    */
    Extendable.call(self);

    opts = _.defaults(opts || {}, {
        headers: null,
        body: null,
        data: null,
        params: {},
        encoder: _.identity,
        verify_options: null,
        ssl_method: null
    });

    self.url = url;
    if (_.isString(self.url)) {
        self.url = url_utils.format(url_utils.parse(url));
    }

    self.method = method.toUpperCase();
    self.headers = opts.headers;
    self.data = opts.data;
    self.body = opts.body;
    self.params = opts.params;
    self.encoder = opts.encoder;
    self.verify_options = opts.verify_options;
    self.ssl_method = opts.ssl_method;

    self.encode = function() {
        /**:HttpRequest.encode()

        Encodes the request data (if available).
        */
        if (self.data !== null) {
            try {
                self.body = self.encoder(self.data);
            }
            catch (e) {
                throw new HttpRequestError(
                    self, "Could not parse request (" + e.toString() + ")");
            }
        }
    };

    self.to_cmd = function() {
        /**:HttpRequest.to_cmd()

        Returns a sandbox API command that can be used to initiate this request
        via the sandbox API.
        */
        var cmd = {};
        cmd.data = {};
        cmd.name = 'http.' + self.method.toLowerCase();

        var url_data = url_utils.parse(self.url);
        url_data.query = self.params;
        cmd.data.url = url_utils.format(url_data);

        if (self.headers !== null) {
            cmd.data.headers = self.headers;
        }

        if (self.body !== null) {
            cmd.data.data = self.body;
        }

        if (self.verify_options !== null) {
            cmd.data.verify_options = self.verify_options;
        }

        if (self.ssl_method !== null) {
            cmd.data.ssl_method = self.ssl_method;
        }

        return cmd;
    };

    self.toString = function() {
        var parts = [
            'HttpRequest:',
            self.method,
            self.url];

        if (self.body !== null) {
            parts.push('(body: ' + self.body + ')');
        }

        if (_.size(self.params)) {
            parts.push('(params: ' + JSON.stringify(self.params) + ')');
        }

        return '[' + parts.join(' ') + ']';
    };

});

var HttpResponse = Extendable.extend(function(self, request, code, opts) {
    /**class:HttpResponse(request, code, opts)

    Encapsulates information about an HTTP response given to the
    :class:`HttpApi`. Once :meth:`HttpResponse.decode` has been invoked,
    the response's body is decoded and made available as the response's data.

    :param HttpRequest request:
        the request that caused the response.
    :param integer code:
        the status code for the HTTP response.
    :param string opts.body:
        the response's body to be decoded as the response's data. Optional.
    */
    Extendable.call(self);

    opts = _.defaults(opts || {}, {
        data: null,
        body: null,
        decoder: _.identity
    });

    self.request = request;
    self.code = code;
    self.data = opts.data;
    self.body = opts.body;
    self.decoder = opts.decoder;

    self.decode = function() {
        /**:HttpResponse.decode()

        Decodes the responses body (if available).
        */
        if (self.body !== null) {

            try {
                self.data = self.decoder(self.body);
            }
            catch (e) {
                throw new HttpResponseError(
                    self, "Could not parse response (" + e.toString() + ")");
            }
        }
    };

    self.toString = function() {
        var parts = [
            'HttpResponse:',
            self.code];

        if (self.body !== null) {
            parts.push('(body: ' + self.body + ')');
        }

        parts.push('(request: ' + self.request + ')');
        return parts.join(' ');
    };
});

var HttpApi = Eventable.extend(function(self, im, opts) {
    /**class:HttpApi(im, opts)

    A helper class for making HTTP requests via the HTTP sandbox resource.

    :param InteractionMachine im:
        The interaction machine to use when making requests.
    :param object opts.headers:
        Default headers to use in HTTP requests.
    :param object opts.auth:
        Adds a HTTP Basic authentication to the default headers. Should
        contain ``username`` and ``password`` attributes.
    */
    opts = _.defaults(opts || {}, {headers: {}});

    self.im = im;
    self.defaults = _.pick({
        headers: opts.headers,
        auth: opts.auth
    }, utils.exists);

    self.make_auth = utils.basic_auth;

    self.decode_response_body = function(body) {
        /**:HttpApi.decode_response_body(body)

        :param string body:
            The body to decode.

        Sub-classes should override this to decode the response body and throw
        an exception if the body cannot be parsed. This base implementation
        returns the body as-is (i.e. decoding is left to the code calling the
        :class:`HttpApi`).
        */
        return body;
    };

    self.encode_request_data = function(data) {
        /**:HttpApi.encode_request_data(data)

        :param object data:
            The data to enoptscode.

        Sub-classes should override this to encode the request body and throw
        an exception if the data cannot be encoded. This base implementation
        returns the data as-is (i.e. encoding is left to code calling the
        :class:`HttpApi`).
        */
        return data;
    };

    self.set_defaults = function(opts) {
        var headers = _.extend({}, self.defaults.headers);

        if (self.defaults.auth) {
            headers.Authorization = [self.make_auth(
                self.defaults.auth.username,
                self.defaults.auth.password)];
        }

        opts = opts || {};
        return _.defaults(opts, _.omit(self.defaults, 'headers', 'auth'), {
            encoder: self.encode_request_data,
            headers: _.defaults(opts.headers || {}, headers)
        });
    };

    self.parse_reply = function(reply, request) {
        /**:HttpApi.parse_reply(reply, request)

        Check an HTTP reply and throw an :class:`HttpRequestError` if the
        sandbox API command was unsuccessful, or otherwise parse the sandbox's
        reply into a response.  If the response status code is not in the 200
        range or the reply body cannot be decoded, throw an
        :class:`HttpResponseError`.

        Logs an error via the sandbox logging resource in an error is raised.

        :param object reply:
            Raw response to the sandbox API command.
        :param HttpRequest request:
            The request that initiated the sandbox API command.

        Returns an :class:`HttpResponse` or throws an :class:`HttpApiError`
        (either the :class:`HttpRequestError` or :class:`HttpResponseError`
        derivative, depending on what error occured).
        */
        var response = new HttpResponse(request, reply.code, {
            body: reply.body,
            decoder: self.decode_response_body
        });

        response.decode();

        if (response.code < 200 || response.code >= 300) {
            throw new HttpResponseError(response);
        }

        return response;
    };

    self.request = function(method, url, opts) {
        /**:HttpApi.request(method, url, opts)

        :param string method:
            The HTTP method to use (e.g. `GET`, `POST`).
        :param string url:
            The URL to make the request to. If you pass in query parameters
            using ``opts.params``, don't include any in the URL itself.
        :param opts.params:
            An object of key-value pairs to append to the URL as query
            parameters. Can be in any form accepted by node.js's querystring
            module
        :param object opts.data:
            Data to pass as the request body. Will be encoded using
            :func:`HttpApi.encode_request_data` before being sent.
        :param object opts.headers:
            Additional headers to add to the default headers.

        Returns a :class:`HttpResponse` via a promise. Failures while making
        and checking the request will be thrown as :class:`HttpApiError`s, and
        can be caught with a Q errback. See :meth:`HttpApi.parse_reply` for
        more on the response parsing and error throwing.
        */
        var request = new HttpRequest(method, url, self.set_defaults(opts));
        request.encode();

        var cmd = request.to_cmd();
        return self
            .im.api_request(cmd.name, cmd.data)
            .then(
                function(reply) {
                    return self.parse_reply(reply, request);
                }, function(e) {
                    throw new HttpRequestError(request, e.reply.reason);
                });

    };

    self.get = function(url, opts) {
        /**:HttpApi.get(url, opts)

        Make an HTTP GET request.

        :param string url:
            The URL to make the request to.
        :param object opts:
            Options to pass to :func:`HttpApi.request`.

        Returns a promise which fires with the decoded value of the
        response body or an object with an error attribute containing
        the error message.
        */
        return self.request('GET', url, opts);
    };

    self.head = function(url, opts) {
        /**:HttpApi.head(url, opts)

        Make an HTTP HEAD request.

        :param string url:
            The URL to make the request to.
        :param object opts:
            Options to pass to :func:`HttpApi.request`.

        Returns a promise which fires with the decoded value of the
        response body or an object with an error attribute containing
        the error message.
        */
        return self.request('HEAD', url, opts);
    };

    self.post = function(url, opts) {
        /**:HttpApi.post(url, opts)

        Make an HTTP POST request.

        :param string url:
            The URL to make the request to.
        :param object opts:
            Options to pass to :func:`HttpApi.request`.

        Returns a promise which fires with the decoded value of the
        response body or an object with an error attribute containing
        the error message.
        */
        return self.request('POST', url, opts);
    };

    self.put = function(url, opts) {
        /**:HttpApi.put(url, opts)

        Make an HTTP PUT request.

        :param string url:
            The URL to make the request to.
        :param object opts:
            Options to pass to :func:`HttpApi.request`.

        Returns a promise which fires with the decoded value of the
        response body or an object with an error attribute containing
        the error message.
        */
        return self.request('PUT', url, opts);
    };

    self.delete = function(url, opts) {
        /**:HttpApi.delete(url, opts)

        Make an HTTP DELETE request.

        :param string url:
            The URL to make the request to.
        :param object opts:
            Options to pass to :func:`HttpApi.request`.

        Returns a promise which fires with the decoded value of the
        response body or an object with an error attribute containing
        the error message.
        */
        return self.request('DELETE', url, opts);
    };
});

var JsonApi = HttpApi.extend(function(self, im, opts) {
    /**class:JsonApi(im, opts)

    A helper class for making HTTP requests that send and receive JSON
    encoded data.

    :param InteractionMachine im:
        The interaction machine to use when making requests.
    :param object opts.headers:
        Default headers to use in HTTP requests. The ``Content-Type``
        header is overridden to be ``application/json; charset=utf-8``.
    :param object opts.auth:
        Adds a HTTP Basic authentication to the default headers. Should
        contain ``username`` and ``password`` attributes.
    */
    HttpApi.call(self, im, opts);

    self.defaults.headers['Content-Type'] = ['application/json; charset=utf-8'];

    self.decode_response_body = function(body) {
        /**:JsonApi.decode_response_body(body)

        Decode an HTTP response body using ``JSON.parse()``.

        :param string body:
            Raw HTTP response body to parse.

        Returns the decoded response body.
        */
        return JSON.parse(body);
    };

    self.encode_request_data = function(data) {
        /**:JsonApi.encode_request_data(data)

        Encode an object as JSON using ``JSON.stringify()``.

        :param object data:
            Object to encode to JSON.

        Returns the serialized object as a string.
        */
        return JSON.stringify(data);
    };
});

this.HttpApi = HttpApi;
this.JsonApi = JsonApi;

this.HttpApiError = HttpApiError;
this.HttpRequestError = HttpRequestError;
this.HttpResponseError = HttpResponseError;
this.HttpRequest = HttpRequest;
this.HttpResponse = HttpResponse;
<commit_msg>Support defaults for verify_options and ssl_method in HttpApi<commit_after>var _ = require('lodash');
var url_utils = require('url');

var utils = require('../utils');
var BaseError = utils.BaseError;
var Extendable = utils.Extendable;

var events = require('../events');
var Eventable = events.Eventable;

var HttpApiError = BaseError.extend(function(self) {
    /**class:HttpApiError()

    Thrown when an error occurs while making and checking an HTTP request and
    the corresponding API reply.
    */
    self.name = "HttpApiError";
});

var HttpRequestError = BaseError.extend(function(self, request, reason) {
    /**class:HttpRequestError(request, reason)

    Thrown when an error occurs while making and checking an HTTP request.

    :param HttpRequest request: the request.
    :param string reason: the reason for the failure. Optional.
    */
    self.name = "HttpRequestError";
    self.request = request;
    self.reason = reason || null;

    if (self.reason) {
        self.message = [self.reason, self.request].join(' ');
    } else {
        self.message = self.request.toString();
    }
});

var HttpResponseError = BaseError.extend(function(self, response, reason) {
    /**class:HttpResponseError(response, reason)

    Thrown when an error response is returned by an HTTP request or if the HTTP
    response body cannot be parsed.

    :param HttpResponse response: the response.
    :param string reason: the reason for the failure. Optional.
    */
    self.name = "HttpResponseError";
    self.response = response;
    self.reason = reason || null;

    if (self.reason) {
        self.message = [self.reason, self.response].join(' ');
    } else {
        self.message = self.response.toString();
    }
});

var HttpRequest = Extendable.extend(function(self, method, url, opts) {
    /**class:HttpRequest(request, code, opts)

    Encapsulates information about an HTTP request made by the
    :class:`HttpApi`. Once :meth:`HttpRequest.encode` has been invoked,
    the request's data is encoded and made available as the request's body.

    :param string method:
        the HTTP request method.
    :param string url:
        the url to send the request to.
    :param string opts.data:
        the request's data to be encoded as the request's body. Optional.
    :param opts.params:
        An object of key-value pairs to append to the URL as query
        parameters. Can be in any form accepted by node.js's querystring
        module
    :param string opts.verify_options:
        A list of options to verify when doing an HTTPS request. Optional.
    :param string opts.ssl_method:
        A request for a specific ssl method to be attempted. Optional.
    */
    Extendable.call(self);

    opts = _.defaults(opts || {}, {
        headers: null,
        body: null,
        data: null,
        params: {},
        encoder: _.identity,
        verify_options: null,
        ssl_method: null
    });

    self.url = url;
    if (_.isString(self.url)) {
        self.url = url_utils.format(url_utils.parse(url));
    }

    self.method = method.toUpperCase();
    self.headers = opts.headers;
    self.data = opts.data;
    self.body = opts.body;
    self.params = opts.params;
    self.encoder = opts.encoder;
    self.verify_options = opts.verify_options;
    self.ssl_method = opts.ssl_method;

    self.encode = function() {
        /**:HttpRequest.encode()

        Encodes the request data (if available).
        */
        if (self.data !== null) {
            try {
                self.body = self.encoder(self.data);
            }
            catch (e) {
                throw new HttpRequestError(
                    self, "Could not parse request (" + e.toString() + ")");
            }
        }
    };

    self.to_cmd = function() {
        /**:HttpRequest.to_cmd()

        Returns a sandbox API command that can be used to initiate this request
        via the sandbox API.
        */
        var cmd = {};
        cmd.data = {};
        cmd.name = 'http.' + self.method.toLowerCase();

        var url_data = url_utils.parse(self.url);
        url_data.query = self.params;
        cmd.data.url = url_utils.format(url_data);

        if (self.headers !== null) {
            cmd.data.headers = self.headers;
        }

        if (self.body !== null) {
            cmd.data.data = self.body;
        }

        if (self.verify_options !== null) {
            cmd.data.verify_options = self.verify_options;
        }

        if (self.ssl_method !== null) {
            cmd.data.ssl_method = self.ssl_method;
        }

        return cmd;
    };

    self.toString = function() {
        var parts = [
            'HttpRequest:',
            self.method,
            self.url];

        if (self.body !== null) {
            parts.push('(body: ' + self.body + ')');
        }

        if (_.size(self.params)) {
            parts.push('(params: ' + JSON.stringify(self.params) + ')');
        }

        return '[' + parts.join(' ') + ']';
    };

});

var HttpResponse = Extendable.extend(function(self, request, code, opts) {
    /**class:HttpResponse(request, code, opts)

    Encapsulates information about an HTTP response given to the
    :class:`HttpApi`. Once :meth:`HttpResponse.decode` has been invoked,
    the response's body is decoded and made available as the response's data.

    :param HttpRequest request:
        the request that caused the response.
    :param integer code:
        the status code for the HTTP response.
    :param string opts.body:
        the response's body to be decoded as the response's data. Optional.
    */
    Extendable.call(self);

    opts = _.defaults(opts || {}, {
        data: null,
        body: null,
        decoder: _.identity
    });

    self.request = request;
    self.code = code;
    self.data = opts.data;
    self.body = opts.body;
    self.decoder = opts.decoder;

    self.decode = function() {
        /**:HttpResponse.decode()

        Decodes the responses body (if available).
        */
        if (self.body !== null) {

            try {
                self.data = self.decoder(self.body);
            }
            catch (e) {
                throw new HttpResponseError(
                    self, "Could not parse response (" + e.toString() + ")");
            }
        }
    };

    self.toString = function() {
        var parts = [
            'HttpResponse:',
            self.code];

        if (self.body !== null) {
            parts.push('(body: ' + self.body + ')');
        }

        parts.push('(request: ' + self.request + ')');
        return parts.join(' ');
    };
});

var HttpApi = Eventable.extend(function(self, im, opts) {
    /**class:HttpApi(im, opts)

    A helper class for making HTTP requests via the HTTP sandbox resource.

    :param InteractionMachine im:
        The interaction machine to use when making requests.
    :param object opts.headers:
        Default headers to use in HTTP requests.
    :param object opts.auth:
        Adds a HTTP Basic authentication to the default headers. Should
        contain ``username`` and ``password`` attributes.
    :param string opts.verify_options:
        The default list of options to verify when doing HTTPS requests.
        Optional.
    :param string opts.ssl_method:
       The default ssl method to attempt for HTTPS requests. Optional.
    */
    opts = _.defaults(opts || {}, {headers: {}});

    self.im = im;
    self.defaults = _.pick({
        headers: opts.headers,
        auth: opts.auth,
        verify_options: opts.verify_options,
        ssl_method: opts.ssl_method
    }, utils.exists);

    self.make_auth = utils.basic_auth;

    self.decode_response_body = function(body) {
        /**:HttpApi.decode_response_body(body)

        :param string body:
            The body to decode.

        Sub-classes should override this to decode the response body and throw
        an exception if the body cannot be parsed. This base implementation
        returns the body as-is (i.e. decoding is left to the code calling the
        :class:`HttpApi`).
        */
        return body;
    };

    self.encode_request_data = function(data) {
        /**:HttpApi.encode_request_data(data)

        :param object data:
            The data to enoptscode.

        Sub-classes should override this to encode the request body and throw
        an exception if the data cannot be encoded. This base implementation
        returns the data as-is (i.e. encoding is left to code calling the
        :class:`HttpApi`).
        */
        return data;
    };

    self.set_defaults = function(opts) {
        var headers = _.extend({}, self.defaults.headers);

        if (self.defaults.auth) {
            headers.Authorization = [self.make_auth(
                self.defaults.auth.username,
                self.defaults.auth.password)];
        }

        opts = opts || {};
        return _.defaults(opts, _.omit(self.defaults, 'headers', 'auth'), {
            encoder: self.encode_request_data,
            headers: _.defaults(opts.headers || {}, headers)
        });
    };

    self.parse_reply = function(reply, request) {
        /**:HttpApi.parse_reply(reply, request)

        Check an HTTP reply and throw an :class:`HttpRequestError` if the
        sandbox API command was unsuccessful, or otherwise parse the sandbox's
        reply into a response.  If the response status code is not in the 200
        range or the reply body cannot be decoded, throw an
        :class:`HttpResponseError`.

        Logs an error via the sandbox logging resource in an error is raised.

        :param object reply:
            Raw response to the sandbox API command.
        :param HttpRequest request:
            The request that initiated the sandbox API command.

        Returns an :class:`HttpResponse` or throws an :class:`HttpApiError`
        (either the :class:`HttpRequestError` or :class:`HttpResponseError`
        derivative, depending on what error occured).
        */
        var response = new HttpResponse(request, reply.code, {
            body: reply.body,
            decoder: self.decode_response_body
        });

        response.decode();

        if (response.code < 200 || response.code >= 300) {
            throw new HttpResponseError(response);
        }

        return response;
    };

    self.request = function(method, url, opts) {
        /**:HttpApi.request(method, url, opts)

        :param string method:
            The HTTP method to use (e.g. `GET`, `POST`).
        :param string url:
            The URL to make the request to. If you pass in query parameters
            using ``opts.params``, don't include any in the URL itself.
        :param opts.params:
            An object of key-value pairs to append to the URL as query
            parameters. Can be in any form accepted by node.js's querystring
            module
        :param object opts.data:
            Data to pass as the request body. Will be encoded using
            :func:`HttpApi.encode_request_data` before being sent.
        :param object opts.headers:
            Additional headers to add to the default headers.

        Returns a :class:`HttpResponse` via a promise. Failures while making
        and checking the request will be thrown as :class:`HttpApiError`s, and
        can be caught with a Q errback. See :meth:`HttpApi.parse_reply` for
        more on the response parsing and error throwing.
        */
        var request = new HttpRequest(method, url, self.set_defaults(opts));
        request.encode();

        var cmd = request.to_cmd();
        return self
            .im.api_request(cmd.name, cmd.data)
            .then(
                function(reply) {
                    return self.parse_reply(reply, request);
                }, function(e) {
                    throw new HttpRequestError(request, e.reply.reason);
                });

    };

    self.get = function(url, opts) {
        /**:HttpApi.get(url, opts)

        Make an HTTP GET request.

        :param string url:
            The URL to make the request to.
        :param object opts:
            Options to pass to :func:`HttpApi.request`.

        Returns a promise which fires with the decoded value of the
        response body or an object with an error attribute containing
        the error message.
        */
        return self.request('GET', url, opts);
    };

    self.head = function(url, opts) {
        /**:HttpApi.head(url, opts)

        Make an HTTP HEAD request.

        :param string url:
            The URL to make the request to.
        :param object opts:
            Options to pass to :func:`HttpApi.request`.

        Returns a promise which fires with the decoded value of the
        response body or an object with an error attribute containing
        the error message.
        */
        return self.request('HEAD', url, opts);
    };

    self.post = function(url, opts) {
        /**:HttpApi.post(url, opts)

        Make an HTTP POST request.

        :param string url:
            The URL to make the request to.
        :param object opts:
            Options to pass to :func:`HttpApi.request`.

        Returns a promise which fires with the decoded value of the
        response body or an object with an error attribute containing
        the error message.
        */
        return self.request('POST', url, opts);
    };

    self.put = function(url, opts) {
        /**:HttpApi.put(url, opts)

        Make an HTTP PUT request.

        :param string url:
            The URL to make the request to.
        :param object opts:
            Options to pass to :func:`HttpApi.request`.

        Returns a promise which fires with the decoded value of the
        response body or an object with an error attribute containing
        the error message.
        */
        return self.request('PUT', url, opts);
    };

    self.delete = function(url, opts) {
        /**:HttpApi.delete(url, opts)

        Make an HTTP DELETE request.

        :param string url:
            The URL to make the request to.
        :param object opts:
            Options to pass to :func:`HttpApi.request`.

        Returns a promise which fires with the decoded value of the
        response body or an object with an error attribute containing
        the error message.
        */
        return self.request('DELETE', url, opts);
    };
});

var JsonApi = HttpApi.extend(function(self, im, opts) {
    /**class:JsonApi(im, opts)

    A helper class for making HTTP requests that send and receive JSON
    encoded data.

    :param InteractionMachine im:
        The interaction machine to use when making requests.
    :param object opts.headers:
        Default headers to use in HTTP requests. The ``Content-Type``
        header is overridden to be ``application/json; charset=utf-8``.
    :param object opts.auth:
        Adds a HTTP Basic authentication to the default headers. Should
        contain ``username`` and ``password`` attributes.
    */
    HttpApi.call(self, im, opts);

    self.defaults.headers['Content-Type'] = ['application/json; charset=utf-8'];

    self.decode_response_body = function(body) {
        /**:JsonApi.decode_response_body(body)

        Decode an HTTP response body using ``JSON.parse()``.

        :param string body:
            Raw HTTP response body to parse.

        Returns the decoded response body.
        */
        return JSON.parse(body);
    };

    self.encode_request_data = function(data) {
        /**:JsonApi.encode_request_data(data)

        Encode an object as JSON using ``JSON.stringify()``.

        :param object data:
            Object to encode to JSON.

        Returns the serialized object as a string.
        */
        return JSON.stringify(data);
    };
});

this.HttpApi = HttpApi;
this.JsonApi = JsonApi;

this.HttpApiError = HttpApiError;
this.HttpRequestError = HttpRequestError;
this.HttpResponseError = HttpResponseError;
this.HttpRequest = HttpRequest;
this.HttpResponse = HttpResponse;
<|endoftext|>


<commit_before>'use babel'

import childProcess from 'child_process'
import readline from 'readline'

const separatorPattern = /(?:\s|[,:])+/

export default class Hunspell {
  constructor () {
    this.process = childProcess.spawn('/usr/bin/hunspell', ['-a', '-t'])

    this.process.on('exit', (code) => {
      console.log(`Child exited with code ${code}`)
    })

    this.process.stdin.write('!\n') // Put into terse mode

    this.readline = readline.createInterface({
      input: this.process.stdout
    })
  }

  check (text) {
    if (text) {
      let foo = this.process
      let bar = this.readline
      return new Promise(function (resolve, reject) {
        let words = []
        function onLine (line) {
          if (line) {
            const parts = line.split(separatorPattern)
            console.log(parts)
            switch (parts[0]) {
              case '&':
                words.push({
                  original: parts[1],
                  offset: parseInt(parts[3], 10),
                  misses: parts.slice(4)
                })
                break
              case '#':
                words.push({
                  original: parts[1],
                  offset: parseInt(parts[2], 10),
                  misses: []
                })
            }
          } else {
            bar.removeListener('line', onLine)
            resolve(words)
          }
        }
        bar.on('line', onLine)
        foo.stdin.write(text + '\n')
      })
    } else {
      return []
    }
  }

}
<commit_msg>Added command pattern<commit_after>'use babel'

import childProcess from 'child_process'
import readline from 'readline'

const separatorPattern = /(?:\s|[,:])+/
const commandPattern = /^[-*&@+~#!%`]/

export default class Hunspell {
  constructor () {
    this.process = childProcess.spawn('/usr/bin/hunspell', ['-a', '-t'])

    this.process.on('exit', (code) => {
      console.log(`Child exited with code ${code}`)
    })

    this.process.stdin.write('!\n') // Put into terse mode

    this.readline = readline.createInterface({
      input: this.process.stdout
    })
  }

  check (text) {
    if (text) {
      let foo = this.process
      let bar = this.readline
      return new Promise(function (resolve, reject) {
        let words = []
        function onLine (line) {
          if (line) {
            const parts = line.split(separatorPattern)
            console.log(parts)
            switch (parts[0]) {
              case '&':
                words.push({
                  original: parts[1],
                  offset: parseInt(parts[3], 10),
                  misses: parts.slice(4)
                })
                break
              case '#':
                words.push({
                  original: parts[1],
                  offset: parseInt(parts[2], 10),
                  misses: []
                })
            }
          } else {
            bar.removeListener('line', onLine)
            resolve(words)
          }
        }
        bar.on('line', onLine)
        foo.stdin.write(text.replace(commandPattern, '^$&') + '\n')
      })
    } else {
      return []
    }
  }

}
<|endoftext|>


<commit_before>var get = require('lodash.get')

function getAcceptedLanguage (request) {
  if (!request || typeof request.get !== 'function') {
    return
  }

  var header = request.get('accept-language') || ''
  var acceptedLanguages = header.split(';')

  return acceptedLanguages[0]
}

function getQueryFromRequest (request) {
  return function (param, key) {
    return decodeURIComponent(get(request, `query.${key}`, '')) || param
  }
}

function getLocaleFromRequest (options) {
  var cookieName = get(options, 'cookieName', 'locale')
  var params = get(options, 'queryParams', ['locale'])
  var queryParams = typeof params === 'string' ? [params] : params

  return function (request) {
    var query = queryParams.reduce(getQueryFromRequest(request), null)
    var locale = (
      query ||
      get(request, ['cookies', cookieName]) ||
      getAcceptedLanguage(request) ||
      get(request, 'acceptedLanguages') ||
      get(request, 'hostname.locale')
    )

    return Array.isArray(locale) ? locale[0] : locale
  }
}

module.exports = getLocaleFromRequest
<commit_msg>Remove default value. Use a thing straight, don't stuff it to var<commit_after>var get = require('lodash.get')

function getAcceptedLanguage (request) {
  if (!request || typeof request.get !== 'function') {
    return
  }

  var header = request.get('accept-language') || ''
  var acceptedLanguages = header.split(';')

  return acceptedLanguages[0]
}

function getQueryFromRequest (request) {
  return function (param, key) {
    return decodeURIComponent(get(request, `query.${key}`)) || param
  }
}

function getLocaleFromRequest (options) {
  var cookieName = get(options, 'cookieName', 'locale')
  var params = get(options, 'queryParams', ['locale'])
  var queryParams = typeof params === 'string' ? [params] : params

  return function (request) {
    var locale = (
      queryParams.reduce(getQueryFromRequest(request), null) ||
      get(request, ['cookies', cookieName]) ||
      getAcceptedLanguage(request) ||
      get(request, 'acceptedLanguages') ||
      get(request, 'hostname.locale')
    )

    return Array.isArray(locale) ? locale[0] : locale
  }
}

module.exports = getLocaleFromRequest
<|endoftext|>


<commit_before>/**
 * @fileoverview Type annotations for the React library.
 *
 * Will be automatically included as a source (not externs) file by
 * ReactCompilerPass. The contents of this file should be inert (i.e. interfaces
 * and typedefs only) such that it compiles down to nothing.
 *
 * Based on https://github.com/facebook/flow/blob/master/lib/react.js and
 * https://github.com/borisyankov/DefinitelyTyped/blob/master/react/react.d.ts.
 */

/**
 * @interface
 * @template T
 */
function ReactClass() {}

/**
 * @type {Object.<ReactPropsChainableTypeChecker>|undefined}
 */
ReactClass.prototype.propTypes;

/**
 * @type {string|undefined}
 */
ReactClass.prototype.displayName;

/**
 * @type {ReactProps|undefined}
 */
ReactClass.prototype.defaultProps;

/**
 * @return {ReactProps}
 */
ReactClass.prototype.getDefaultProps = function() {};

/**
 * @typedef {!Object|{children: (Object|undefined)}}
 */
var ReactProps;

/**
 * @interface
 * @template T
 */
function ReactElement() {}

/**
 * @type {ReactClass.<T>}
 */
ReactElement.prototype.type;

/**
 * @type {ReactProps}
 */
ReactElement.prototype.props;

/**
 * @type {string|number}
 */
ReactElement.prototype.key;

/**
 * @type {string}
 */
ReactElement.prototype.ref;

/**
 * @interface
 * @extends {ReactElement}
 */
function ReactDOMElement() {}

/**
 * @type {string}
 */
ReactDOMElement.prototype.type;

/**
 * @interface
 */
function ReactComponent() {}

/**
 * @type {ReactProps}
 * @const
 */
ReactComponent.prototype.props;

/**
 * @type {Object}
 * @const
 */
ReactComponent.prototype.state;

/**
 * @dict
 */
ReactComponent.prototype.refs;

/**
 * @return {Object}
 */
ReactComponent.prototype.getInitialState = function() {};

/**
 * @param {Object} props
 * @param {function(): void=} callback
 * @return {void}
 */
ReactComponent.prototype.setProps = function(props, callback) {};

/**
 * @param {Object} props
 * @param {function(): void=} callback
 * @return {void}
 */
ReactComponent.prototype.replaceProps = function(props, callback) {};

/**
 * @param {Object} state
 * @param {function(): void=} callback
 * @return {void}
 */
ReactComponent.prototype.setState = function(state, callback) {};

/**
 * @param {Object} state
 * @param {function(): void=} callback
 * @return {void}
 */
ReactComponent.prototype.replaceState = function(state, callback) {};

/**
 * @return {ReactElement}
 */
ReactComponent.prototype.render = function() {};

/**
 * @param {function(): void=} callback
 * @return {void}
 */
ReactComponent.prototype.forceUpdate = function(callback) {};

/**
 * @return {Element}
 */
ReactComponent.prototype.getDOMNode = function() {};

/**
 * @return {boolean}
 */
ReactComponent.prototype.isMounted = function() {};

// Component lifecycle/delegate methods that may be implemented. Intentionally
// does not include the context parameter that is passed to some methods, since
// it's undocumented. Implementations can still add it (and it will not be
// flagged as an error).

/**
 * @return {void}
 */
ReactComponent.prototype.componentWillMount = function() {};

/**
 * @return {void}
 */
ReactComponent.prototype.componentDidMount = function() {};

/**
 * @param {Object} nextProps
 * @return {void}
 */
ReactComponent.prototype.componentWillReceiveProps = function(nextProps) {};

/**
 * @param {Object} nextProps
 * @param {Object} nextState
 * @return {boolean}
 */
ReactComponent.prototype.shouldComponentUpdate = function(nextProps, nextState) {};

/**
 * @param {Object} nextProps
 * @param {Object} nextState
 * @return {void}
 */
ReactComponent.prototype.componentWillUpdate = function(nextProps, nextState) {};

/**
 * @param {Object} prevProps
 * @param {Object} prevState
 * @return {void}
 */
ReactComponent.prototype.componentDidUpdate = function(prevProps, prevState) {};

/**
 * @return {void}
 */
ReactComponent.prototype.componentWillUnmount = function() {};

/**
 * @typedef {boolean|number|string|ReactElement}
 */
var ReactChild;

/**
 * @typedef {
 *   ReactChild|
 *   Array.<boolean>|Array.<number>|Array.<string>|Array.<ReactElement>
 * }
 */
var ReactChildrenArgument;

/**
 * @interface
 */
function ReactChildren() {};

/**
 * @param {Object|undefined} children
 * @param {function(*, number)} func
 * @param {*=} context
 * @return {Object|undefined}
 */
ReactChildren.prototype.map = function(children, func, context) {};

/**
 * @param {Object|undefined} children
 * @param {function(*, number)} func
 * @param {*=} context
 */
ReactChildren.prototype.forEach = function(children, func, context) {};

/**
 * @param {Object|undefined} children
 * @return {number}
 */
ReactChildren.prototype.count = function(children) {};

/**
 * @param {Object|undefined} children
 * @return {ReactChild}
 */
ReactChildren.prototype.only = function(children) {};

/**
 * Factory functions for each HTML and SVG tag are generated by
 * ReactCompilerPass.
 *
 * @interface
 */
function ReactDOM() {};

/**
 * Parameters are: props, propName, componentName, location.
 * @typedef {function(Object, string, string, string): Error}
 */
var ReactPropsChainableTypeChecker = function() {};

/**
 * @interface
 */
function ReactPropTypes() {};
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.array;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.array.isRequired;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.bool;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.bool.isRequired;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.func;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.func.isRequired;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.number;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.number.isRequired;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.object;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.object.isRequired;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.string;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.string.isRequired;

/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.any;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.any.isRequired;
/**
 * @param {ReactPropsChainableTypeChecker} typeChecker
 * @return {ReactPropsChainableTypeChecker}
 */
ReactPropTypes.prototype.arrayOf = function(typeChecker) {};
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.element;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.element.isRequired;
/**
 * @param {Function} expectedClass
 * @return {ReactPropsChainableTypeChecker}
 */
ReactPropTypes.prototype.instanceOf = function(expectedClass) {};
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.node;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.node.isRequired;
/**
 * @param {ReactPropsChainableTypeChecker} typeChecker
 * @return {ReactPropsChainableTypeChecker}
 */
ReactPropTypes.prototype.objectOf = function(typeChecker) {};
/**
 * @param {Array} expectedValues
 * @return {ReactPropsChainableTypeChecker}
 */
ReactPropTypes.prototype.oneOf = function(expectedValues) {};
/**
 * @param {Array.<ReactPropsChainableTypeChecker>} arrayOfTypeCheckers
 * @return {ReactPropsChainableTypeChecker}
 */
ReactPropTypes.prototype.oneOfType = function(arrayOfTypeCheckers) {};
/**
 * @param {Object.<ReactPropsChainableTypeChecker>} shapeTypes
 * @return {ReactPropsChainableTypeChecker}
 */
ReactPropTypes.prototype.shape = function(shapeTypes) {};

/**
 * @interface
 */
function ReactAddons() {};

/**
 * @type {Object}
 */
ReactAddons.prototype.PureRenderMixin;

/**
 * @param {Function} callback
 * @param {*=} a
 * @param {*=} b
 * @param {*=} c
 * @param {*=} d
 */
ReactAddons.prototype.batchedUpdates = function(callback, a, b, c, d) {};

/**
 * @param {Object|string} objectOrClassName
 * @param {...string} classNames
 * @return {string}
 * @deprecated
 */
ReactAddons.prototype.classSet = function(objectOrClassName, classNames) {};

/**
 * @param {ReactElement.<T>} element
 * @param {Object=} extraProps
 * @return {ReactElement.<T>}
 * @template T
 */
ReactAddons.prototype.cloneWithProps = function(element, extraProps) {};

/**
 * @param {Object.<string, ReactElement>} object
 * @return {*}
 */
ReactAddons.prototype.createFragment = function(object) {};

/**
 * @typedef {{
 *     $push: (Array|undefined),
 *     $unshift: (Array|undefined),
 *     $splice: (Array.<Array>|undefined),
 *     $set: (Object|undefined),
 *     $merge: (Object|undefined),
 *     $apply: (function(Object): Object|undefined)
 * }}
 */
ReactAddons.UpdateSpec;

/**
 * @param {Object|Array} value
 * @param {ReactAddons.UpdateSpec} updateSpec
 * @return {Object|Array}
 */
ReactAddons.prototype.update = function(value, updateSpec) {};

/**
 * @interface
 */
function ReactModule() {}

/**
 * @type {ReactChildren}
 * @const
 */
ReactModule.prototype.Children;

/**
 * @typedef {ReactComponent}
 */
ReactModule.prototype.Component;

/**
 * @type {ReactDOM}
 * @const
 */
ReactModule.prototype.DOM;

/**
 * @type {ReactPropTypes}
 * @const
 */
ReactModule.prototype.PropTypes;

/**
 * @param {boolean} shouldUseTouch
 * @return {void}
 */
ReactModule.prototype.initializeTouchEvents = function(shouldUseTouch) {};

/**
 * @param {{
 *     render: function(): ReactElement,
 *     displayName: (string|undefined),
 *     propTypes: (Object.<ReactPropsChainableTypeChecker>|undefined),
 *     mixins: (Array.<Object>|undefined),
 *     statics: (Object|undefined)
 * }} specification
 * @return {ReactClass}
 */
ReactModule.prototype.createClass = function(specification) {};

/**
 * @param {T} mixin
 * @return {T}
 * @template T
 */
ReactModule.prototype.createMixin = function(mixin) {};

/**
 * @param {ReactClass.<T>|string} type
 * @param {Object=} props
 * @param {...ReactChildrenArgument} children
 * @return {ReactElement.<T>}
 * @template T
 */
ReactModule.prototype.createElement = function(type, props, children) {};

/**
 * @param {ReactElement.<T>} element
 * @param {Object=} props
 * @param {...ReactChildrenArgument} children
 * @return {ReactElement.<T>}
 * @template T
 */
ReactModule.prototype.cloneElement = function(element, props, children) {};

/**
 * @param {ReactClass.<T>|string} type
 * @return {function(Object=, ...ReactChildrenArgument): ReactElement.<T>}
 * @template T
 */
ReactModule.prototype.createFactory = function(type) {};

/**
 * @param {ReactElement|Element} componentOrElement
 * @return {Element}
 */
ReactModule.prototype.findDOMNode = function(componentOrElement) {};

/**
 * @param {ReactElement.<T>} element
 * @param {Element} container
 * @param {function()=} callback
 * @return {T}
 * @template T
 */
ReactModule.prototype.render = function(element, container, callback) {};

/**
 * @param {ReactElement} element
 * @return {string}
 */
ReactModule.prototype.renderToString = function(element) {};

/**
 * @param {ReactElement} element
 * @return {string}
 */
ReactModule.prototype.renderToStaticMarkup = function(element) {};

/**
 * @param {Element} container
 * @return {boolean}
 */
ReactModule.prototype.unmountComponentAtNode = function(container) {};

/**
 * @param {Object} element
 * @return {boolean}
 */
ReactModule.prototype.isValidElement = function(element) {};

/**
 * @type {ReactAddons}
 * @const
 */
ReactModule.prototype.addons;
<commit_msg>Add React.addons.Perf.<commit_after>/**
 * @fileoverview Type annotations for the React library.
 *
 * Will be automatically included as a source (not externs) file by
 * ReactCompilerPass. The contents of this file should be inert (i.e. interfaces
 * and typedefs only) such that it compiles down to nothing.
 *
 * Based on https://github.com/facebook/flow/blob/master/lib/react.js and
 * https://github.com/borisyankov/DefinitelyTyped/blob/master/react/react.d.ts.
 */

/**
 * @interface
 * @template T
 */
function ReactClass() {}

/**
 * @type {Object.<ReactPropsChainableTypeChecker>|undefined}
 */
ReactClass.prototype.propTypes;

/**
 * @type {string|undefined}
 */
ReactClass.prototype.displayName;

/**
 * @type {ReactProps|undefined}
 */
ReactClass.prototype.defaultProps;

/**
 * @return {ReactProps}
 */
ReactClass.prototype.getDefaultProps = function() {};

/**
 * @typedef {!Object|{children: (Object|undefined)}}
 */
var ReactProps;

/**
 * @interface
 * @template T
 */
function ReactElement() {}

/**
 * @type {ReactClass.<T>}
 */
ReactElement.prototype.type;

/**
 * @type {ReactProps}
 */
ReactElement.prototype.props;

/**
 * @type {string|number}
 */
ReactElement.prototype.key;

/**
 * @type {string}
 */
ReactElement.prototype.ref;

/**
 * @interface
 * @extends {ReactElement}
 */
function ReactDOMElement() {}

/**
 * @type {string}
 */
ReactDOMElement.prototype.type;

/**
 * @interface
 */
function ReactComponent() {}

/**
 * @type {ReactProps}
 * @const
 */
ReactComponent.prototype.props;

/**
 * @type {Object}
 * @const
 */
ReactComponent.prototype.state;

/**
 * @dict
 */
ReactComponent.prototype.refs;

/**
 * @return {Object}
 */
ReactComponent.prototype.getInitialState = function() {};

/**
 * @param {Object} props
 * @param {function(): void=} callback
 * @return {void}
 */
ReactComponent.prototype.setProps = function(props, callback) {};

/**
 * @param {Object} props
 * @param {function(): void=} callback
 * @return {void}
 */
ReactComponent.prototype.replaceProps = function(props, callback) {};

/**
 * @param {Object} state
 * @param {function(): void=} callback
 * @return {void}
 */
ReactComponent.prototype.setState = function(state, callback) {};

/**
 * @param {Object} state
 * @param {function(): void=} callback
 * @return {void}
 */
ReactComponent.prototype.replaceState = function(state, callback) {};

/**
 * @return {ReactElement}
 */
ReactComponent.prototype.render = function() {};

/**
 * @param {function(): void=} callback
 * @return {void}
 */
ReactComponent.prototype.forceUpdate = function(callback) {};

/**
 * @return {Element}
 */
ReactComponent.prototype.getDOMNode = function() {};

/**
 * @return {boolean}
 */
ReactComponent.prototype.isMounted = function() {};

// Component lifecycle/delegate methods that may be implemented. Intentionally
// does not include the context parameter that is passed to some methods, since
// it's undocumented. Implementations can still add it (and it will not be
// flagged as an error).

/**
 * @return {void}
 */
ReactComponent.prototype.componentWillMount = function() {};

/**
 * @return {void}
 */
ReactComponent.prototype.componentDidMount = function() {};

/**
 * @param {Object} nextProps
 * @return {void}
 */
ReactComponent.prototype.componentWillReceiveProps = function(nextProps) {};

/**
 * @param {Object} nextProps
 * @param {Object} nextState
 * @return {boolean}
 */
ReactComponent.prototype.shouldComponentUpdate = function(nextProps, nextState) {};

/**
 * @param {Object} nextProps
 * @param {Object} nextState
 * @return {void}
 */
ReactComponent.prototype.componentWillUpdate = function(nextProps, nextState) {};

/**
 * @param {Object} prevProps
 * @param {Object} prevState
 * @return {void}
 */
ReactComponent.prototype.componentDidUpdate = function(prevProps, prevState) {};

/**
 * @return {void}
 */
ReactComponent.prototype.componentWillUnmount = function() {};

/**
 * @typedef {boolean|number|string|ReactElement}
 */
var ReactChild;

/**
 * @typedef {
 *   ReactChild|
 *   Array.<boolean>|Array.<number>|Array.<string>|Array.<ReactElement>
 * }
 */
var ReactChildrenArgument;

/**
 * @interface
 */
function ReactChildren() {};

/**
 * @param {Object|undefined} children
 * @param {function(*, number)} func
 * @param {*=} context
 * @return {Object|undefined}
 */
ReactChildren.prototype.map = function(children, func, context) {};

/**
 * @param {Object|undefined} children
 * @param {function(*, number)} func
 * @param {*=} context
 */
ReactChildren.prototype.forEach = function(children, func, context) {};

/**
 * @param {Object|undefined} children
 * @return {number}
 */
ReactChildren.prototype.count = function(children) {};

/**
 * @param {Object|undefined} children
 * @return {ReactChild}
 */
ReactChildren.prototype.only = function(children) {};

/**
 * Factory functions for each HTML and SVG tag are generated by
 * ReactCompilerPass.
 *
 * @interface
 */
function ReactDOM() {};

/**
 * Parameters are: props, propName, componentName, location.
 * @typedef {function(Object, string, string, string): Error}
 */
var ReactPropsChainableTypeChecker = function() {};

/**
 * @interface
 */
function ReactPropTypes() {};
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.array;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.array.isRequired;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.bool;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.bool.isRequired;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.func;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.func.isRequired;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.number;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.number.isRequired;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.object;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.object.isRequired;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.string;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.string.isRequired;

/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.any;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.any.isRequired;
/**
 * @param {ReactPropsChainableTypeChecker} typeChecker
 * @return {ReactPropsChainableTypeChecker}
 */
ReactPropTypes.prototype.arrayOf = function(typeChecker) {};
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.element;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.element.isRequired;
/**
 * @param {Function} expectedClass
 * @return {ReactPropsChainableTypeChecker}
 */
ReactPropTypes.prototype.instanceOf = function(expectedClass) {};
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.node;
/** @type {ReactPropsChainableTypeChecker} */ ReactPropTypes.prototype.node.isRequired;
/**
 * @param {ReactPropsChainableTypeChecker} typeChecker
 * @return {ReactPropsChainableTypeChecker}
 */
ReactPropTypes.prototype.objectOf = function(typeChecker) {};
/**
 * @param {Array} expectedValues
 * @return {ReactPropsChainableTypeChecker}
 */
ReactPropTypes.prototype.oneOf = function(expectedValues) {};
/**
 * @param {Array.<ReactPropsChainableTypeChecker>} arrayOfTypeCheckers
 * @return {ReactPropsChainableTypeChecker}
 */
ReactPropTypes.prototype.oneOfType = function(arrayOfTypeCheckers) {};
/**
 * @param {Object.<ReactPropsChainableTypeChecker>} shapeTypes
 * @return {ReactPropsChainableTypeChecker}
 */
ReactPropTypes.prototype.shape = function(shapeTypes) {};

/**
 * @interface
 */
function ReactAddonsPerf() {}

ReactAddonsPerf.prototype.start = function() {};

ReactAddonsPerf.prototype.stop = function() {};

/**
 * @return {Array.<ReactAddonsPerf.Measurement>}
 */
ReactAddonsPerf.prototype.getLastMeasurements = function() {};

/**
 * @param {ReactAddonsPerf.Measurement=} measurements
 */
ReactAddonsPerf.prototype.printExclusive = function(measurements) {};

/**
 * @param {ReactAddonsPerf.Measurement=} measurements
 */
ReactAddonsPerf.prototype.printInclusive = function(measurements) {};

/**
 * @param {ReactAddonsPerf.Measurement=} measurements
 */
ReactAddonsPerf.prototype.printWasted = function(measurements) {};

/**
 * @typedef {{
 *     exclusive: !Object.<string, number>,
 *     inclusive: !Object.<string, number>,
 *     render: !Object.<string, number>,
 *     counts: !Object.<string, number>,
 *     writes: !Object.<string, {type: string, time: number, args: Array}>,
 *     displayNames: !Object.<string, {current: string, owner: string}>,
 *     totalTime: number
 * }}
 */
ReactAddonsPerf.Measurement;

/**
 * @interface
 */
function ReactAddons() {}

/**
 * @type {ReactAddonsPerf}
 */
ReactAddons.prototype.Perf;

/**
 * @type {Object}
 */
ReactAddons.prototype.PureRenderMixin;

/**
 * @param {Function} callback
 * @param {*=} a
 * @param {*=} b
 * @param {*=} c
 * @param {*=} d
 */
ReactAddons.prototype.batchedUpdates = function(callback, a, b, c, d) {};

/**
 * @param {Object|string} objectOrClassName
 * @param {...string} classNames
 * @return {string}
 * @deprecated
 */
ReactAddons.prototype.classSet = function(objectOrClassName, classNames) {};

/**
 * @param {ReactElement.<T>} element
 * @param {Object=} extraProps
 * @return {ReactElement.<T>}
 * @template T
 */
ReactAddons.prototype.cloneWithProps = function(element, extraProps) {};

/**
 * @param {Object.<string, ReactElement>} object
 * @return {*}
 */
ReactAddons.prototype.createFragment = function(object) {};

/**
 * @typedef {{
 *     $push: (Array|undefined),
 *     $unshift: (Array|undefined),
 *     $splice: (Array.<Array>|undefined),
 *     $set: (Object|undefined),
 *     $merge: (Object|undefined),
 *     $apply: (function(Object): Object|undefined)
 * }}
 */
ReactAddons.UpdateSpec;

/**
 * @param {Object|Array} value
 * @param {ReactAddons.UpdateSpec} updateSpec
 * @return {Object|Array}
 */
ReactAddons.prototype.update = function(value, updateSpec) {};

/**
 * @interface
 */
function ReactModule() {}

/**
 * @type {ReactChildren}
 * @const
 */
ReactModule.prototype.Children;

/**
 * @typedef {ReactComponent}
 */
ReactModule.prototype.Component;

/**
 * @type {ReactDOM}
 * @const
 */
ReactModule.prototype.DOM;

/**
 * @type {ReactPropTypes}
 * @const
 */
ReactModule.prototype.PropTypes;

/**
 * @param {boolean} shouldUseTouch
 * @return {void}
 */
ReactModule.prototype.initializeTouchEvents = function(shouldUseTouch) {};

/**
 * @param {{
 *     render: function(): ReactElement,
 *     displayName: (string|undefined),
 *     propTypes: (Object.<ReactPropsChainableTypeChecker>|undefined),
 *     mixins: (Array.<Object>|undefined),
 *     statics: (Object|undefined)
 * }} specification
 * @return {ReactClass}
 */
ReactModule.prototype.createClass = function(specification) {};

/**
 * @param {T} mixin
 * @return {T}
 * @template T
 */
ReactModule.prototype.createMixin = function(mixin) {};

/**
 * @param {ReactClass.<T>|string} type
 * @param {Object=} props
 * @param {...ReactChildrenArgument} children
 * @return {ReactElement.<T>}
 * @template T
 */
ReactModule.prototype.createElement = function(type, props, children) {};

/**
 * @param {ReactElement.<T>} element
 * @param {Object=} props
 * @param {...ReactChildrenArgument} children
 * @return {ReactElement.<T>}
 * @template T
 */
ReactModule.prototype.cloneElement = function(element, props, children) {};

/**
 * @param {ReactClass.<T>|string} type
 * @return {function(Object=, ...ReactChildrenArgument): ReactElement.<T>}
 * @template T
 */
ReactModule.prototype.createFactory = function(type) {};

/**
 * @param {ReactElement|Element} componentOrElement
 * @return {Element}
 */
ReactModule.prototype.findDOMNode = function(componentOrElement) {};

/**
 * @param {ReactElement.<T>} element
 * @param {Element} container
 * @param {function()=} callback
 * @return {T}
 * @template T
 */
ReactModule.prototype.render = function(element, container, callback) {};

/**
 * @param {ReactElement} element
 * @return {string}
 */
ReactModule.prototype.renderToString = function(element) {};

/**
 * @param {ReactElement} element
 * @return {string}
 */
ReactModule.prototype.renderToStaticMarkup = function(element) {};

/**
 * @param {Element} container
 * @return {boolean}
 */
ReactModule.prototype.unmountComponentAtNode = function(container) {};

/**
 * @param {Object} element
 * @return {boolean}
 */
ReactModule.prototype.isValidElement = function(element) {};

/**
 * @type {ReactAddons}
 * @const
 */
ReactModule.prototype.addons;
<|endoftext|>


<commit_before>var nconf = require('nconf');

nconf.env('||')
     .file({ file: __dirname + '/../config.json', logicalSeparator: '||' })
     .defaults({
        PORT:              4000,
        SESSION_SECRET:    'a1b2c3d4567',
        AUTHENTICATION:    'FORM',
        LDAP_SEARCH_QUERY: '(&(objectCategory=person)(|(anr=*{q}*)(mail=*{q}*)))'
     });
<commit_msg>updated query (changed Contains to StartsWith)<commit_after>var nconf = require('nconf');

nconf.env('||')
     .file({ file: __dirname + '/../config.json', logicalSeparator: '||' })
     .defaults({
        PORT:              4000,
        SESSION_SECRET:    'a1b2c3d4567',
        AUTHENTICATION:    'FORM',
        LDAP_SEARCH_QUERY: '(&(objectCategory=person)(|(anr={q}*)(mail={q}*)))'
     });
<|endoftext|>