<commit_before>'use strict'

const exists = require('fs').access;
const libob = require('libobject');
const exec = require('child_process').exec;
const LRU = require('lru-cache');
const API = require('flow-api/lib/cayley');
const toArray= require('flow-api/lib/utils').toArray;
const flow_streams = require('flow-streams');
const cache_options = {max: 500};
const RE_method_path = /^<([^\/]+)\/([^#]+)(?:#([^\?]+))?\?(.*)>$/;

function saveRequire (module, method, callback) {
    try {
        if (!(method = libob.path(method, require(module)))) {
            return callback(new Error('Flow-nodejs.adapter.require: Method not found.'));
        }
        callback(null, method);
    } catch (err) {
        callback(err);
    }
}

module.exports = (entrypoint) => {

    entrypoint.module_root = entrypoint.base + '/node_modules/';

    const state = {};
    API.connect(entrypoint, state);

    return {
        cache: LRU(cache_options),
        seq: (scope, sequence_id, role) => {

            // get cayley streams
            let chunk = {readable: API.flow(state.g, sequence_id, role)};

            // combine json object streams
            chunk = flow_streams.combine(scope, null, {readable: 'readable'}, chunk);

            // parse cayley http response streams
            chunk = flow_streams.json.parse(scope, null, {readable: 'result.*'}, chunk);

            // parse triple data, emit event per triple
            chunk = toArray(scope, null, null, chunk);

            return chunk.readable;
        },

        fn: (method_iri, role, cb) => {

            method_iri = method_iri.match(RE_method_path);
            if (!method_iri || !method_iri[1] || !method_iri[2] || !method_iri[4]) {
                return cb(new Error('Flow-nodejs.adapter.fn: Invalid method path.'));
            }

            let path = entrypoint.module_root + method_iri[2];
            exists(path, (err) => {

                if (err) {
                    return exec('npm i --prefix ' + entrypoint.base + ' ' + method_iri[2] + (module_iri[3] ? '#' + method_iri[3]: ''), err => {

                        if (err) {
                            return cb(err);
                        }

                        saveRequire(path, method_iri[4], cb);
                    });
                }

                saveRequire(path, method_iri[4], cb);
            });
        }
    };
};
<commit_msg>tell which method is not found<commit_after>'use strict'

const exists = require('fs').access;
const libob = require('libobject');
const exec = require('child_process').exec;
const LRU = require('lru-cache');
const API = require('flow-api/lib/cayley');
const toArray= require('flow-api/lib/utils').toArray;
const flow_streams = require('flow-streams');
const cache_options = {max: 500};
const RE_method_path = /^<([^\/]+)\/([^#]+)(?:#([^\?]+))?\?(.*)>$/;

function saveRequire (module, method, callback) {
    try {
        let msg_method = method;
        if (!(method = libob.path(method, require(module)))) {
            return callback(new Error('Flow-nodejs.adapter.require: Method "' + msg_method + '"not found on module "' + module + '".'));
        }
        callback(null, method);
    } catch (err) {
        callback(err);
    }
}

module.exports = (entrypoint) => {

    entrypoint.module_root = entrypoint.base + '/node_modules/';

    const state = {};
    API.connect(entrypoint, state);

    return {
        cache: LRU(cache_options),
        seq: (scope, sequence_id, role) => {

            // get cayley streams
            let chunk = {readable: API.flow(state.g, sequence_id, role)};

            // combine json object streams
            chunk = flow_streams.combine(scope, null, {readable: 'readable'}, chunk);

            // parse cayley http response streams
            chunk = flow_streams.json.parse(scope, null, {readable: 'result.*'}, chunk);

            // parse triple data, emit event per triple
            chunk = toArray(scope, null, null, chunk);

            return chunk.readable;
        },

        fn: (method_iri, role, cb) => {

            method_iri = method_iri.match(RE_method_path);
            if (!method_iri || !method_iri[1] || !method_iri[2] || !method_iri[4]) {
                return cb(new Error('Flow-nodejs.adapter.fn: Invalid method path.'));
            }

            let path = entrypoint.module_root + method_iri[2];
            exists(path, (err) => {

                if (err) {
                    return exec('npm i --prefix ' + entrypoint.base + ' ' + method_iri[2] + (module_iri[3] ? '#' + method_iri[3]: ''), err => {

                        if (err) {
                            return cb(err);
                        }

                        saveRequire(path, method_iri[4], cb);
                    });
                }

                saveRequire(path, method_iri[4], cb);
            });
        }
    };
};
<|endoftext|>


<commit_before>(function (root, factory) {
    if (typeof define === 'function' && define.amd) {
        define(factory);
    } else if (typeof exports === 'object') {
        module.exports = factory();
    } else {
        root.deepmerge = factory();
    }
}(this, function () {

function isMergeableObject(val) {
    var nonNullObject = val && typeof val === 'object'

    return nonNullObject
        && Object.prototype.toString.call(val) !== '[object RegExp]'
        && Object.prototype.toString.call(val) !== '[object Date]'
}

function emptyTarget(val) {
    return Array.isArray(val) ? [] : {}
}

function cloneIfNecessary(value, optionsArgument) {
    var clone = optionsArgument && optionsArgument.clone === true
    return (clone && isMergeableObject(value)) ? deepmerge(emptyTarget(value), value) : value
}

function defaultArrayMerge(target, source, optionsArgument) {
    var destination = target.slice()
    source.forEach(function(e, i) {
        if (typeof destination[i] === 'undefined') {
            destination[i] = cloneIfNecessary(e, optionsArgument)
        } else if (isMergeableObject(e)) {
            destination[i] = deepmerge(target[i], e, optionsArgument)
        } else if (target.indexOf(e) === -1) {
            destination.push(cloneIfNecessary(e, optionsArgument))
        }
    })
    return destination
}

function mergeObject(target, source, optionsArgument) {
    var destination = {}
    if (isMergeableObject(target)) {
        Object.keys(target).forEach(function (key) {
            destination[key] = cloneIfNecessary(target[key], optionsArgument)
        })
    }
    Object.keys(source).forEach(function (key) {
        if (!isMergeableObject(source[key]) || !target[key]) {
            destination[key] = cloneIfNecessary(source[key], optionsArgument)
        } else {
            destination[key] = deepmerge(target[key], source[key], optionsArgument)
        }
    })
    return destination
}

function deepmerge(target, source, optionsArgument) {
    var array = Array.isArray(source);
    var options = optionsArgument || { arrayMerge: defaultArrayMerge }
    var arrayMerge = options.arrayMerge || defaultArrayMerge

    if (array) {
        return Array.isArray(target) ? arrayMerge(target, source, optionsArgument) : source.slice()
    } else {
        return mergeObject(target, source, optionsArgument)
    }
}

return deepmerge

}));
<commit_msg>Fix array clone case<commit_after>(function (root, factory) {
    if (typeof define === 'function' && define.amd) {
        define(factory);
    } else if (typeof exports === 'object') {
        module.exports = factory();
    } else {
        root.deepmerge = factory();
    }
}(this, function () {

function isMergeableObject(val) {
    var nonNullObject = val && typeof val === 'object'

    return nonNullObject
        && Object.prototype.toString.call(val) !== '[object RegExp]'
        && Object.prototype.toString.call(val) !== '[object Date]'
}

function emptyTarget(val) {
    return Array.isArray(val) ? [] : {}
}

function cloneIfNecessary(value, optionsArgument) {
    var clone = optionsArgument && optionsArgument.clone === true
    return (clone && isMergeableObject(value)) ? deepmerge(emptyTarget(value), value, optionsArgument) : value
}

function defaultArrayMerge(target, source, optionsArgument) {
    var destination = target.slice()
    source.forEach(function(e, i) {
        if (typeof destination[i] === 'undefined') {
            destination[i] = cloneIfNecessary(e, optionsArgument)
        } else if (isMergeableObject(e)) {
            destination[i] = deepmerge(target[i], e, optionsArgument)
        } else if (target.indexOf(e) === -1) {
            destination.push(cloneIfNecessary(e, optionsArgument))
        }
    })
    return destination
}

function mergeObject(target, source, optionsArgument) {
    var destination = {}
    if (isMergeableObject(target)) {
        Object.keys(target).forEach(function (key) {
            destination[key] = cloneIfNecessary(target[key], optionsArgument)
        })
    }
    Object.keys(source).forEach(function (key) {
        if (!isMergeableObject(source[key]) || !target[key]) {
            destination[key] = cloneIfNecessary(source[key], optionsArgument)
        } else {
            destination[key] = deepmerge(target[key], source[key], optionsArgument)
        }
    })
    return destination
}

function deepmerge(target, source, optionsArgument) {
    var array = Array.isArray(source);
    var options = optionsArgument || { arrayMerge: defaultArrayMerge }
    var arrayMerge = options.arrayMerge || defaultArrayMerge

    if (array) {
        return Array.isArray(target) ? arrayMerge(target, source, optionsArgument) : cloneIfNecessary(source, optionsArgument)
    } else {
        return mergeObject(target, source, optionsArgument)
    }
}

return deepmerge

}));
<|endoftext|>


<commit_before>'use strict';

var http = require('http');
var net  = require('net');
var tls  = require('tls');
var util = require('util');
var https = require('https');

function getArgs(args) {
  var res = [9050, 'localhost'];
  if (typeof args[0] === 'object') {
    res[3] = args[0];
  } else {
    res[0] = args[0];
    if (typeof args[1] === 'string') {
      res[1] = args[1];
      res[2] = args[2];
    }
    else {
      res[2] = args[1];
    }
  }
  return res;
}

function SocksWrapper() {
  var args = getArgs(arguments);

  net.Socket.call(this, args[3]);

  var self          = this,
      socket        = new net.Socket(),
      socksResponse = null;

  function createSocksRequest(port, host) {
    var data = new Buffer(9);

    data[0] = 4;
    data[1] = 1;
    data[2] = 0xFF & (port >> 8)
    data[3] = 0xFF & port;
    data[8] = 0;

    if (4 == net.isIP(host)) {
      var groups = host.split('.');
      for (var i = 0; i < groups.length; i++) {
        data[4 + i] = parseInt(groups[i], 10);
      }
    }
    else {
      data[4] = 0;
      data[5] = 0;
      data[6] = 0;
      data[7] = 1;

      var hostData = new Buffer(host);
      var nullByte = new Buffer(1);

      nullByte[0] = 0;

      data = Buffer.concat([data, hostData, nullByte]);
    }

    return data;
  }

  exports.SocksWrapper = SocksWrapper;

  function handleSocksResponse(data) {
    socksResponse = socksResponse ? Buffer.concat(socksResponse, data) : data;

    if (socksResponse.length >= 8) {
      if (socksResponse[1] != 0x5A) {
        socket.destroy();
      }
      else {
        socket.removeListener('data', handleSocksResponse);

        self._handle       = socket._handle;
        self._handle.owner = self;
        self.readable      = socket.readable;
        self.writable      = socket.writable;
        self.connecting    = false;

        self.emit('connect');
      }
    }
  }

  this.connect = function(options) {
    this.connecting = true;
    socket.connect(args[0], args[1], function() {
      var socksRequest = createSocksRequest(options.port, options.host);
      socket.write(socksRequest);
      socket.on('data', handleSocksResponse);
    });

    return this;
  }
}

util.inherits(SocksWrapper, net.Socket);

exports.HttpAgent = function() {
  var args = getArgs(arguments);
  http.Agent.call(this, args[2]);
  this.createConnection = function(options) {
    options.port = options.port || 80;
    return new SocksWrapper(args[0], args[1]).connect(options);
  }
}

util.inherits(exports.HttpAgent, http.Agent);

exports.HttpsAgent = function() {
  var args = getArgs(arguments);
  https.Agent.call(this, args[2]);
  this.createConnection = function(options) {
    options.port = options.port || 443;
    options.socket = new SocksWrapper(args[0], args[1]).connect(options);
    return tls.connect(options)
  }
}

util.inherits(exports.HttpsAgent, http.Agent);
<commit_msg>Export SocksWrapper<commit_after>'use strict';

var http = require('http');
var net  = require('net');
var tls  = require('tls');
var util = require('util');
var https = require('https');

function getArgs(args) {
  var res = [9050, 'localhost'];
  if (typeof args[0] === 'object') {
    res[3] = args[0];
  } else {
    res[0] = args[0];
    if (typeof args[1] === 'string') {
      res[1] = args[1];
      res[2] = args[2];
    }
    else {
      res[2] = args[1];
    }
  }
  return res;
}

function SocksWrapper() {
  var args = getArgs(arguments);

  net.Socket.call(this, args[3]);

  var self          = this,
      socket        = new net.Socket(),
      socksResponse = null;

  function createSocksRequest(port, host) {
    var data = new Buffer(9);

    data[0] = 4;
    data[1] = 1;
    data[2] = 0xFF & (port >> 8)
    data[3] = 0xFF & port;
    data[8] = 0;

    if (4 == net.isIP(host)) {
      var groups = host.split('.');
      for (var i = 0; i < groups.length; i++) {
        data[4 + i] = parseInt(groups[i], 10);
      }
    }
    else {
      data[4] = 0;
      data[5] = 0;
      data[6] = 0;
      data[7] = 1;

      var hostData = new Buffer(host);
      var nullByte = new Buffer(1);

      nullByte[0] = 0;

      data = Buffer.concat([data, hostData, nullByte]);
    }

    return data;
  }

  function handleSocksResponse(data) {
    socksResponse = socksResponse ? Buffer.concat(socksResponse, data) : data;
    if (socksResponse.length >= 8) {
      if (socksResponse[1] != 0x5A) {
        socket.destroy();
        self.emit('error', { code: socksResponse[1] } )
      }
      else {
        socket.removeListener('data', handleSocksResponse);

        self._handle       = socket._handle;
        self._handle.owner = self;
        self.readable      = socket.readable;
        self.writable      = socket.writable;
        self.connecting    = false;

        self.emit('connect');
      }
    }
  }

  this.connect = function(options) {
    this.connecting = true;
    socket.connect(args[0], args[1], function() {
      var socksRequest = createSocksRequest(options.port, options.host);
      socket.write(socksRequest);
      socket.on('data', handleSocksResponse);
    });

    socket.on('error', err => { this.emit('error', err) });

    return this;
  }
}

exports.SocksWrapper = SocksWrapper;

util.inherits(SocksWrapper, net.Socket);

exports.HttpAgent = function() {
  var args = getArgs(arguments);
  http.Agent.call(this, args[2]);
  this.createConnection = function(options) {
    options.port = options.port || 80;
    return new SocksWrapper(args[0], args[1]).connect(options);
  }
}

util.inherits(exports.HttpAgent, http.Agent);

exports.HttpsAgent = function() {
  var args = getArgs(arguments);
  https.Agent.call(this, args[2]);
  this.createConnection = function(options) {
    options.port = options.port || 443;
    options.socket = new SocksWrapper(args[0], args[1]).connect(options);
    return tls.connect(options)
  }
}

util.inherits(exports.HttpsAgent, http.Agent);

<|endoftext|>


<commit_before>var request = require("request");
var moment = require("moment");

var sunbaseURL = "http://api.sunrise-sunset.org/json?";
var lat = 43.048122;
var long = -76.147424;

var alexa = require('alexa-app');
var app = new alexa.app('astronomer');

app.launch(function(request, response){
  response.say("I can tell you when the sun will rise or set.");
});

app.intent('GetSunrise',
  function(alexaRequest, alexaResponse){
    var url = sunbaseURL + "lat=" + lat + "&lng=" + long;
    request({
      url: url,
      json: true
    }, (function(error, response, body) {
        if(!error && response.statusCode === 200){
          alexaResponse.say(moment(body.results.sunrise, "HH:mm:ss A").subtract(4, "hours").format('LTS'));
        }
    });
  }
);

app.intent('GetSunset',
  function(alexaRequest, alexaResponse){
    var url = sunbaseURL + "lat=" + lat + "&lng=" + long;
    request({
      url: url,
      json: true
    }, function(error, response, body) {
        if(!error && response.statusCode === 200){
          alexaResponse.say(moment(body.results.sunset, "HH:mm:ss A").subtract(4, "hours").format('LTS'));
        }
    });
  }
);

exports.handler = app.lambda();
<commit_msg>WHEEEE<commit_after>var request = require("request");
var moment = require("moment");

var sunbaseURL = "http://api.sunrise-sunset.org/json?";
var lat = 43.048122;
var long = -76.147424;

var alexa = require('alexa-app');
var app = new alexa.app('astronomer');

app.launch(function(request, response){
  response.say("I can tell you when the sun will rise or set.");
});

app.intent('GetSunrise',
  function(alexaRequest, alexaResponse){
    var url = sunbaseURL + "lat=" + lat + "&lng=" + long;
    request({
      url: url,
      json: true
    }, (function(error, response, body) {
        if(!error && response.statusCode === 200){
          alexaResponse.say(moment(body.results.sunrise, "HH:mm:ss A").subtract(4, "hours").format('LTS'));
        }
    }));
  }
);

app.intent('GetSunset',
  function(alexaRequest, alexaResponse){
    var url = sunbaseURL + "lat=" + lat + "&lng=" + long;
    request({
      url: url,
      json: true
    }, function(error, response, body) {
        if(!error && response.statusCode === 200){
          alexaResponse.say(moment(body.results.sunset, "HH:mm:ss A").subtract(4, "hours").format('LTS'));
        }
    }));
  }
);

exports.handler = app.lambda();
<|endoftext|>


<commit_before>export {
  version
} from "./build/package";

export {
  Axis,
  AxisBottom,
  AxisLeft,
  AxisRight,
  AxisTop,
  date
} from "d3plus-axis";

export {
  add as colorAdd,
  assign as colorAssign,
  contrast as colorContrast,
  defaults as colorDefaults,
  legible as colorLegible,
  lighter as colorLighter,
  subtract as colorSubtract
} from "d3plus-color";

export {
  accessor,
  assign,
  attrize,
  BaseClass,
  closest,
  constant,
  elem,
  isObject,
  locale,
  merge,
  prefix,
  stylize
} from "d3plus-common";

export {
  Geomap
} from "d3plus-geomap";

export {
  Donut,
  Pie,
  Tree,
  Treemap
} from "d3plus-hierarchy";

export {
  Legend
} from "d3plus-legend";

export {
  Network
} from "d3plus-network";

export {
  AreaPlot,
  BarChart,
  LinePlot,
  Plot,
  StackedArea
} from "d3plus-plot";

export {
  Priestley
} from "d3plus-priestley";

export {
  Area,
  Bar,
  Circle,
  Image,
  Line,
  Path,
  pointDistance,
  Rect,
  Shape
} from "d3plus-shape";

export {
  stringify,
  strip,
  TextBox,
  textSplit,
  textWidth,
  textWrap,
  titleCase
} from "d3plus-text";

export {
  Timeline
} from "d3plus-timeline";

export {
  Tooltip
} from "d3plus-tooltip";

export {
  Viz
} from "d3plus-viz";
<commit_msg>adds fontExists export for d3plus-text<commit_after>export {
  version
} from "./build/package";

export {
  Axis,
  AxisBottom,
  AxisLeft,
  AxisRight,
  AxisTop,
  date
} from "d3plus-axis";

export {
  add as colorAdd,
  assign as colorAssign,
  contrast as colorContrast,
  defaults as colorDefaults,
  legible as colorLegible,
  lighter as colorLighter,
  subtract as colorSubtract
} from "d3plus-color";

export {
  accessor,
  assign,
  attrize,
  BaseClass,
  closest,
  constant,
  elem,
  isObject,
  locale,
  merge,
  prefix,
  stylize
} from "d3plus-common";

export {
  Geomap
} from "d3plus-geomap";

export {
  Donut,
  Pie,
  Tree,
  Treemap
} from "d3plus-hierarchy";

export {
  Legend
} from "d3plus-legend";

export {
  Network
} from "d3plus-network";

export {
  AreaPlot,
  BarChart,
  LinePlot,
  Plot,
  StackedArea
} from "d3plus-plot";

export {
  Priestley
} from "d3plus-priestley";

export {
  Area,
  Bar,
  Circle,
  Image,
  Line,
  Path,
  pointDistance,
  Rect,
  Shape
} from "d3plus-shape";

export {
  fontExists,
  stringify,
  strip,
  TextBox,
  textSplit,
  textWidth,
  textWrap,
  titleCase
} from "d3plus-text";

export {
  Timeline
} from "d3plus-timeline";

export {
  Tooltip
} from "d3plus-tooltip";

export {
  Viz
} from "d3plus-viz";
<|endoftext|>


<commit_before>(function (root, factory) {
    if(typeof define === "function" && define.amd) {
        define(["q","cheerio","curlrequest"], function(Q,cheerio,curlrequest){
            return (root.blocks = factory(Q,cheerio,curlrequest));
        });
    } else if(typeof module === "object" && module.exports) {
        module.exports = (root.blocks = factory(require("q"),require("cheerio"),require("curlrequest")));
    } else {
        root.blocks = factory(root.q,root.cheerio,root.curlrequest);
    }
}(this, function(Q,cheerio,curlrequest) {
    var module = {};

    function extractResults(html,config){
        var $ = cheerio.load(html);
        var results = [];

        var blockSelector = config.blockSelector ? config.blockSelector:"body";
        var blocks = $(blockSelector);
        blocks.each(function(index, element){
            var result = {};
            for(var key in config.scrape){
                var mapping = config.scrape[key];
                var elem = mapping['selector'] === '.' ? $(this) : $(this).find(mapping['selector']);
                if(mapping["extract"] instanceof RegExp) {
                    result[key] = elem.html() ? elem.html().match(mapping["extract"]) : "";
                }else if(mapping["extract"] === "html"){
                    result[key] = elem.html();
                }else if(mapping["extract"].toLowerCase() === "outerhtml"){
                    result[key] = $.html(elem);
                }else if(mapping["extract"] === "text"){
                    result[key] = elem.text();
                }else{
                    result[key] = elem.attr(mapping["extract"]);
                }
            }
            results.push(result);
        });

        return results;
    }

    module.scrape = function(config){
        var deferred = Q.defer();

        //validating config
        if(!config.url){
            var errorMsg = "Incorrect config, missing 'url'";

            deferred.reject(errorMsg);
        }else{
            var mappingErrors = [];

            for(var key in config.scrape) {
                var mapping = config.scrape[key];

                if (!mapping["selector"] || !mapping["extract"]) {
                    var errorMsg = "Incorrect scraper mapping, each item must have a 'selector' and an 'extract' attribute.\n";
                    errorMsg += key + ":" + JSON.stringify(mapping);

                    mappingErrors.push(errorMsg);
                }
            }

            if(mappingErrors.length > 0){
                deferred.reject(mappingErrors);
            }else{
                //curl based scraper
                var curlOptions = {
                    url: config.url
                };

                console.log(curlOptions);
                console.log('----');

                curlrequest.request(curlOptions, function (err, html) {
                    var results = extractResults(html,config);

                    deferred.resolve(results);
                });
            }
        }

        return deferred.promise;
    };

    return module;
}));<commit_msg>remove console log<commit_after>(function (root, factory) {
    if(typeof define === "function" && define.amd) {
        define(["q","cheerio","curlrequest"], function(Q,cheerio,curlrequest){
            return (root.blocks = factory(Q,cheerio,curlrequest));
        });
    } else if(typeof module === "object" && module.exports) {
        module.exports = (root.blocks = factory(require("q"),require("cheerio"),require("curlrequest")));
    } else {
        root.blocks = factory(root.q,root.cheerio,root.curlrequest);
    }
}(this, function(Q,cheerio,curlrequest) {
    var module = {};

    function extractResults(html,config){
        var $ = cheerio.load(html);
        var results = [];

        var blockSelector = config.blockSelector ? config.blockSelector:"body";
        var blocks = $(blockSelector);
        blocks.each(function(index, element){
            var result = {};
            for(var key in config.scrape){
                var mapping = config.scrape[key];
                var elem = mapping['selector'] === '.' ? $(this) : $(this).find(mapping['selector']);
                if(mapping["extract"] instanceof RegExp) {
                    result[key] = elem.html() ? elem.html().match(mapping["extract"]) : "";
                }else if(mapping["extract"] === "html"){
                    result[key] = elem.html();
                }else if(mapping["extract"].toLowerCase() === "outerhtml"){
                    result[key] = $.html(elem);
                }else if(mapping["extract"] === "text"){
                    result[key] = elem.text();
                }else{
                    result[key] = elem.attr(mapping["extract"]);
                }
            }
            results.push(result);
        });

        return results;
    }

    module.scrape = function(config){
        var deferred = Q.defer();

        //validating config
        if(!config.url){
            var errorMsg = "Incorrect config, missing 'url'";

            deferred.reject(errorMsg);
        }else{
            var mappingErrors = [];

            for(var key in config.scrape) {
                var mapping = config.scrape[key];

                if (!mapping["selector"] || !mapping["extract"]) {
                    var errorMsg = "Incorrect scraper mapping, each item must have a 'selector' and an 'extract' attribute.\n";
                    errorMsg += key + ":" + JSON.stringify(mapping);

                    mappingErrors.push(errorMsg);
                }
            }

            if(mappingErrors.length > 0){
                deferred.reject(mappingErrors);
            }else{
                //curl based scraper
                var curlOptions = {
                    url: config.url
                };

                curlrequest.request(curlOptions, function (err, html) {
                    var results = extractResults(html,config);

                    deferred.resolve(results);
                });
            }
        }

        return deferred.promise;
    };

    return module;
}));<|endoftext|>


<commit_before>'use strict';

module.exports = {
	Sequence: require('./sequence'),
	Stream: require('./stream'),
	Track: require('./track'),
	Message: require('./message')
};<commit_msg>added writer to top level object<commit_after>'use strict';

module.exports = {
	Sequence: require('./sequence'),
	Stream: require('./stream'),
	Track: require('./track'),
	Message: require('./message'),
	Writer: require('./writer')
};<|endoftext|>


<commit_before>var execSync = require('child_process').execSync;
var moduleBin = require('module-bin');
var path = require('path');
var callsite = require('callsite');

function glslifySync(filePath) {
    var glslifyBinPath = moduleBin('glslify');
    var glslifyBinAbsolutePath = path.resolve('/', glslifyBinPath);

    var stack = callsite();
    var caller = stack[1].getFileName();

    filePath = path.resolve(path.dirname(caller), filePath)

    console.log(filePath);

    return execSync(glslifyBinAbsolutePath + ' ' + filePath, { encoding: 'utf8' });
}

module.exports = glslifySync;<commit_msg>Remove console log<commit_after>var execSync = require('child_process').execSync;
var moduleBin = require('module-bin');
var path = require('path');
var callsite = require('callsite');

function glslifySync(filePath) {
    var glslifyBinPath = moduleBin('glslify');
    var glslifyBinAbsolutePath = path.resolve('/', glslifyBinPath);

    var stack = callsite();
    var caller = stack[1].getFileName();

    filePath = path.resolve(path.dirname(caller), filePath)

    return execSync(glslifyBinAbsolutePath + ' ' + filePath, { encoding: 'utf8' });
}

module.exports = glslifySync;<|endoftext|>


<commit_before>/* jshint node: true */
'use strict';

var EventEmitter = require('events').EventEmitter;
var rtc = require('rtc');
var debug = rtc.logger('rtc-quickconnect');
var signaller = require('rtc-signaller');
var defaults = require('cog/defaults');
var extend = require('cog/extend');
var reTrailingSlash = /\/$/;
var CHANNEL_HEARTBEAT = '__heartbeat';

/**
  # rtc-quickconnect

  This is a high level helper module designed to help you get up
  an running with WebRTC really, really quickly.  By using this module you
  are trading off some flexibility, so if you need a more flexible
  configuration you should drill down into lower level components of the
  [rtc.io](http://www.rtc.io) suite.  In particular you should check out
  [rtc](https://github.com/rtc-io/rtc).

  ## Example Usage

  In the simplest case you simply call quickconnect with a single string
  argument which tells quickconnect which server to use for signaling:

  <<< examples/simple.js

  ## Example Usage (using data channels)

  When working with WebRTC data channels, you can call the `createDataChannel`
  function helper that is attached to the object returned from the
  `quickconnect` call.  The `createDataChannel` function signature matches
  the signature of the `RTCPeerConnection` `createDataChannel` function.

  At the minimum it requires a label for the channel, but you can also pass
  through a dictionary of options that can be used to fine tune the
  data channel behaviour.  For more information on these options, I'd
  recommend having a quick look at the WebRTC spec:

  http://dev.w3.org/2011/webrtc/editor/webrtc.html#dictionary-rtcdatachannelinit-members

  If in doubt, I'd recommend not passing through options.

  <<< examples/datachannel.js

  __NOTE:__ Data channel interoperability has been tested between Chrome 32
  and Firefox 26, which both make use of SCTP data channels.

  __NOTE:__ The current stable version of Chrome is 31, so interoperability
  with Firefox right now will be hard to achieve.

  ## Example Usage (using captured media)

  Another example is displayed below, and this example demonstrates how
  to use `rtc-quickconnect` to create a simple video conferencing application:

  <<< examples/conference.js

  ## Regarding Signalling and a Signalling Server

  Signaling is an important part of setting up a WebRTC connection and for
  our examples we use our own test instance of the
  [rtc-switchboard](https://github.com/rtc-io/rtc-switchboard). For your
  testing and development you are more than welcome to use this also, but
  just be aware that we use this for our testing so it may go up and down
  a little.  If you need something more stable, why not consider deploying
  an instance of the switchboard yourself - it's pretty easy :)

  ## Handling Peer Disconnection

  __NOTE:__ This functionality is experimental and still in testing, it is
  recommended that you continue to use the `peer:leave` events at this stage.

  Since version `0.11` the following events are also emitted by quickconnect
  objects:

  - `peer:disconnect`
  - `%label%:close` where `%label%` is the label of the channel
     you provided in a `createDataChannel` call.

  Basically the `peer:disconnect` can be used as a more accurate version
  of the `peer:leave` message.  While the `peer:leave` event triggers when
  the background signaller disconnects, the `peer:disconnect` event is
  trigger when the actual WebRTC peer connection is closed.

  At present (due to limited browser support for handling peer close events
  and the like) this is implemented by creating a heartbeat data channel
  which sends messages on a regular basis between the peers.  When these
  messages are stopped being received the connection is considered closed.

  ## Reference

  ```
  quickconnect(signalhost, opts?) => rtc-sigaller instance (+ helpers)
  ```

  ### Valid Quick Connect Options

  The options provided to the `rtc-quickconnect` module function influence the
  behaviour of some of the underlying components used from the rtc.io suite.

  Listed below are some of the commonly used options:

  - `ns` (default: '')

    An optional namespace for your signalling room.  While quickconnect
    will generate a unique hash for the room, this can be made to be more
    unique by providing a namespace.  Using a namespace means two demos
    that have generated the same hash but use a different namespace will be
    in different rooms.

  - `room` (default: null) _added 0.6_

    Rather than use the internal hash generation
    (plus optional namespace) for room name generation, simply use this room
    name instead.  __NOTE:__ Use of the `room` option takes precendence over
    `ns`.

  - `debug` (default: false)

  Write rtc.io suite debug output to the browser console.

  #### Options for Peer Connection Creation

  Options that are passed onto the
  [rtc.createConnection](https://github.com/rtc-io/rtc#createconnectionopts-constraints)
  function:

  - `constraints`

    Used to provide specific constraints when creating a new
    peer connection.

  #### Options for P2P negotiation

  Under the hood, quickconnect uses the
  [rtc/couple](https://github.com/rtc-io/rtc#rtccouple) logic, and the options
  passed to quickconnect are also passed onto this function.

**/
module.exports = function(signalhost, opts) {
  var hash = location.hash.slice(1);
  var signaller = require('rtc-signaller')(signalhost);

  // init configurable vars
  var ns = (opts || {}).ns || '';
  var room = (opts || {}).room;
  var debugging = (opts || {}).debug;
  var disableHeartbeat = (opts || {}).disableHeartbeat;
  var heartbeatInterval = (opts || {}).heartbeatInterval || 500;
  var heartbeatTimeout = (opts || {}).heartbeatTimeout || heartbeatInterval * 10;
  var profile = {};

  // collect the local streams
  var localStreams = [];

  // create the peers registry
  var peers = {};

  // create the known data channels registry
  var channels = {};

  function gotPeerChannel(channel, pc, data) {
    // create the channelOpen function
    var emitChannelOpen = signaller.emit.bind(
      signaller,
      channel.label + ':open',
      channel,
      data.id,
      data,
      pc
    );

    debug('channel ' + channel.label + ' discovered for peer: ' + data.id, channel);
    if (channel.readyState === 'open') {
      return emitChannelOpen();
    }

    channel.onopen = emitChannelOpen;
  }

  function initHeartbeat(channel, pc, data) {
    var hbTimeoutTimer;
    var hbTimer;

    function timeoutConnection() {
      console.log('connection with ' + data.id + ' timed out');

      // trigger a peer disconnect event
      signaller.emit('peer:disconnect', data.id);

      // trigger close events for each of the channels
      Object.keys(channels).forEach(function(channel) {
        signaller.emit(channel + ':close');
      });

      // clear the peer reference
      peers[data.id] = undefined;

      // stop trying to send heartbeat messages
      clearInterval(hbTimer);
    }

    debug('created heartbeat channel for peer: ' + data.id);

    // start monitoring using the heartbeat channel to keep tabs on our
    // peers availability
    channel.onmessage = function(evt) {
      // console.log('received hearbeat message: ' + evt.data)
      if (evt.data === '!HB') {
        clearTimeout(hbTimeoutTimer);
        hbTimeoutTimer = setTimeout(timeoutConnection, heartbeatTimeout);
      }
    };

    hbTimer  = setInterval(function() {
      // if the channel is no longer open, then abort
      if (channel.readyState !== 'open') {
        return clearInterval(hbTimer);
      }

      channel.send('!HB');
    }, heartbeatInterval);

    // start the heartbeat timer
    hbTimeoutTimer = setTimeout(timeoutConnection, heartbeatTimeout);
  }

  // if the room is not defined, then generate the room name
  if (! room) {
    // if the hash is not assigned, then create a random hash value
    if (! hash) {
      hash = location.hash = '' + (Math.pow(2, 53) * Math.random());
    }

    room = ns + '#' + hash;
  }

  if (debugging) {
    rtc.logger.enable.apply(rtc.logger, Array.isArray(debug) ? debugging : ['*']);
  }

  signaller.on('peer:announce', function(data) {
    var pc;
    var monitor;

    // if the room is not a match, abort
    if (data.room !== room) {
      return;
    }

    // create a peer connection
    pc = peers[data.id] = rtc.createConnection(opts, (opts || {}).constraints);

    // add the local streams
    localStreams.forEach(function(stream) {
      pc.addStream(stream);
    });

    // add the data channels
    // do this differently based on whether the connection is a
    // master or a slave connection
    if (signaller.isMaster(data.id)) {
      debug('is master, creating data channels: ', Object.keys(channels));

      // unless the heartbeat is disabled then create a heartbeat datachannel
      if (! disableHeartbeat) {
        initHeartbeat(
          pc.createDataChannel(CHANNEL_HEARTBEAT, { reliable: true}),
          pc,
          data
        );
      }

      // create the channels
      Object.keys(channels).forEach(function(label) {
        gotPeerChannel(pc.createDataChannel(label, channels[label]), pc, data);
      });
    }
    else {
      pc.ondatachannel = function(evt) {
        var channel = evt && evt.channel;

        // if we have no channel, abort
        if (! channel) {
          return;
        }

        // if the channel is the heartbeat, then init the heartbeat
        if (channel.label === CHANNEL_HEARTBEAT) {
          initHeartbeat(channel, pc, data);
        }
        // otherwise, if this is a known channel, initialise it
        else if (channels[channel.label] !== undefined) {
          gotPeerChannel(channel, pc, data);
        }
      };
    }

    // couple the connections
    monitor = rtc.couple(pc, data.id, signaller, opts);

    // emit the peer event as per <= rtc-quickconnect@0.7
    signaller.emit('peer', pc, data.id, data, monitor);

    // once active, trigger the peer connect event
    monitor.once('active', function() {
      signaller.emit('peer:connect', pc, data.id, data);
    });

    // if we are the master connnection, create the offer
    // NOTE: this only really for the sake of politeness, as rtc couple
    // implementation handles the slave attempting to create an offer
    if (signaller.isMaster(data.id)) {
      monitor.createOffer();
    }
  });

  // announce ourselves to our new friend
  setTimeout(function() {
    var data = extend({}, profile, { room: room });

    // announce and emit the local announce event
    signaller.announce(data);
    signaller.emit('local:announce', data);
  }, 0);

  /**
    ### Quickconnect Broadcast and Data Channel Helper Functions

    The following are functions that are patched into the `rtc-signaller`
    instance that make working with and creating functional WebRTC applications
    a lot simpler.

  **/

  /**
    #### broadcast(stream)

    Add the stream to the set of local streams that we will broadcast
    to other peers.

  **/
  signaller.broadcast = function(stream) {
    localStreams.push(stream);
    return signaller;
  };

  /**
    #### close()

    The `close` function provides a convenient way of closing all associated
    peer connections.
  **/
  signaller.close = function() {
    Object.keys(peers).forEach(function(id) {
      if (peers[id]) {
        peers[id].close();
      }
    });

    // reset the peer references
    peers = {};
  };

  /**
    #### createDataChannel(label, config)

    Request that a data channel with the specified `label` is created on
    the peer connection.  When the data channel is open and available, an
    event will be triggered using the label of the data channel.

    For example, if a new data channel was requested using the following
    call:

    ```js
    var qc = quickconnect('http://rtc.io/switchboard').createDataChannel('test');
    ```

    Then when the data channel is ready for use, a `test:open` event would
    be emitted by `qc`.

  **/
  signaller.createDataChannel = function(label, opts) {
    // save the data channel opts in the local channels dictionary
    channels[label] = opts || null;
    return signaller;
  };

  /**
    #### profile(data)

    Update the profile data with the attached information, so when
    the signaller announces it includes this data in addition to any
    room and id information.

  **/
  signaller.profile = function(data) {
    extend(profile, data);
    return signaller;
  };

  // pass the signaller on
  return signaller;
};<commit_msg>Tweaks to heartbeat channel behaviour to ensure connectivity before monitoring for time outs<commit_after>/* jshint node: true */
'use strict';

var EventEmitter = require('events').EventEmitter;
var rtc = require('rtc');
var debug = rtc.logger('rtc-quickconnect');
var signaller = require('rtc-signaller');
var defaults = require('cog/defaults');
var extend = require('cog/extend');
var reTrailingSlash = /\/$/;
var CHANNEL_HEARTBEAT = '__heartbeat';
var HEARTBEAT = new Uint8Array([0x10]);

/**
  # rtc-quickconnect

  This is a high level helper module designed to help you get up
  an running with WebRTC really, really quickly.  By using this module you
  are trading off some flexibility, so if you need a more flexible
  configuration you should drill down into lower level components of the
  [rtc.io](http://www.rtc.io) suite.  In particular you should check out
  [rtc](https://github.com/rtc-io/rtc).

  ## Example Usage

  In the simplest case you simply call quickconnect with a single string
  argument which tells quickconnect which server to use for signaling:

  <<< examples/simple.js

  ## Example Usage (using data channels)

  When working with WebRTC data channels, you can call the `createDataChannel`
  function helper that is attached to the object returned from the
  `quickconnect` call.  The `createDataChannel` function signature matches
  the signature of the `RTCPeerConnection` `createDataChannel` function.

  At the minimum it requires a label for the channel, but you can also pass
  through a dictionary of options that can be used to fine tune the
  data channel behaviour.  For more information on these options, I'd
  recommend having a quick look at the WebRTC spec:

  http://dev.w3.org/2011/webrtc/editor/webrtc.html#dictionary-rtcdatachannelinit-members

  If in doubt, I'd recommend not passing through options.

  <<< examples/datachannel.js

  __NOTE:__ Data channel interoperability has been tested between Chrome 32
  and Firefox 26, which both make use of SCTP data channels.

  __NOTE:__ The current stable version of Chrome is 31, so interoperability
  with Firefox right now will be hard to achieve.

  ## Example Usage (using captured media)

  Another example is displayed below, and this example demonstrates how
  to use `rtc-quickconnect` to create a simple video conferencing application:

  <<< examples/conference.js

  ## Regarding Signalling and a Signalling Server

  Signaling is an important part of setting up a WebRTC connection and for
  our examples we use our own test instance of the
  [rtc-switchboard](https://github.com/rtc-io/rtc-switchboard). For your
  testing and development you are more than welcome to use this also, but
  just be aware that we use this for our testing so it may go up and down
  a little.  If you need something more stable, why not consider deploying
  an instance of the switchboard yourself - it's pretty easy :)

  ## Handling Peer Disconnection

  __NOTE:__ This functionality is experimental and still in testing, it is
  recommended that you continue to use the `peer:leave` events at this stage.

  Since version `0.11` the following events are also emitted by quickconnect
  objects:

  - `peer:disconnect`
  - `%label%:close` where `%label%` is the label of the channel
     you provided in a `createDataChannel` call.

  Basically the `peer:disconnect` can be used as a more accurate version
  of the `peer:leave` message.  While the `peer:leave` event triggers when
  the background signaller disconnects, the `peer:disconnect` event is
  trigger when the actual WebRTC peer connection is closed.

  At present (due to limited browser support for handling peer close events
  and the like) this is implemented by creating a heartbeat data channel
  which sends messages on a regular basis between the peers.  When these
  messages are stopped being received the connection is considered closed.

  ## Reference

  ```
  quickconnect(signalhost, opts?) => rtc-sigaller instance (+ helpers)
  ```

  ### Valid Quick Connect Options

  The options provided to the `rtc-quickconnect` module function influence the
  behaviour of some of the underlying components used from the rtc.io suite.

  Listed below are some of the commonly used options:

  - `ns` (default: '')

    An optional namespace for your signalling room.  While quickconnect
    will generate a unique hash for the room, this can be made to be more
    unique by providing a namespace.  Using a namespace means two demos
    that have generated the same hash but use a different namespace will be
    in different rooms.

  - `room` (default: null) _added 0.6_

    Rather than use the internal hash generation
    (plus optional namespace) for room name generation, simply use this room
    name instead.  __NOTE:__ Use of the `room` option takes precendence over
    `ns`.

  - `debug` (default: false)

  Write rtc.io suite debug output to the browser console.

  #### Options for Peer Connection Creation

  Options that are passed onto the
  [rtc.createConnection](https://github.com/rtc-io/rtc#createconnectionopts-constraints)
  function:

  - `constraints`

    Used to provide specific constraints when creating a new
    peer connection.

  #### Options for P2P negotiation

  Under the hood, quickconnect uses the
  [rtc/couple](https://github.com/rtc-io/rtc#rtccouple) logic, and the options
  passed to quickconnect are also passed onto this function.

**/
module.exports = function(signalhost, opts) {
  var hash = location.hash.slice(1);
  var signaller = require('rtc-signaller')(signalhost);

  // init configurable vars
  var ns = (opts || {}).ns || '';
  var room = (opts || {}).room;
  var debugging = (opts || {}).debug;
  var disableHeartbeat = (opts || {}).disableHeartbeat;
  var heartbeatInterval = (opts || {}).heartbeatInterval || 1000;
  var heartbeatTimeout = (opts || {}).heartbeatTimeout || heartbeatInterval * 3;
  var profile = {};

  // collect the local streams
  var localStreams = [];

  // create the peers registry
  var peers = {};

  // create the known data channels registry
  var channels = {};

  function gotPeerChannel(channel, pc, data) {
    // create the channelOpen function
    var emitChannelOpen = signaller.emit.bind(
      signaller,
      channel.label + ':open',
      channel,
      data.id,
      data,
      pc
    );

    debug('channel ' + channel.label + ' discovered for peer: ' + data.id, channel);
    if (channel.readyState === 'open') {
      return emitChannelOpen();
    }

    channel.onopen = emitChannelOpen;
  }

  function initHeartbeat(channel, pc, data) {
    var hbTimeoutTimer;
    var hbTimer;

    function timeoutConnection() {
      // console.log(Date.now() + ', connection with ' + data.id + ' timed out');

      // trigger a peer disconnect event
      signaller.emit('peer:disconnect', data.id);

      // trigger close events for each of the channels
      Object.keys(channels).forEach(function(channel) {
        signaller.emit(channel + ':close');
      });

      // clear the peer reference
      peers[data.id] = undefined;

      // stop trying to send heartbeat messages
      clearInterval(hbTimer);
    }

    // console.log('created heartbeat channel for peer: ' + data.id);

    // start monitoring using the heartbeat channel to keep tabs on our
    // peers availability
    channel.onmessage = function(evt) {
      // console.log(Date.now() + ', ' + data.id + ': ' + evt.data);

      // console.log('received hearbeat message: ' + evt.data)
      clearTimeout(hbTimeoutTimer);
      hbTimeoutTimer = setTimeout(timeoutConnection, heartbeatTimeout);

      // emit the heartbeat for the appropriate connection
      signaller.emit('hb:' + data.id);
    };

    hbTimer  = setInterval(function() {
      // if the channel is not yet, open then abort
      if (channel.readyState !== 'open') {
        // TODO: clear the interval if we have previously been sending
        // messages
        return;
      }

      channel.send(HEARTBEAT);
    }, heartbeatInterval);
  }

  // if the room is not defined, then generate the room name
  if (! room) {
    // if the hash is not assigned, then create a random hash value
    if (! hash) {
      hash = location.hash = '' + (Math.pow(2, 53) * Math.random());
    }

    room = ns + '#' + hash;
  }

  if (debugging) {
    rtc.logger.enable.apply(rtc.logger, Array.isArray(debug) ? debugging : ['*']);
  }

  signaller.on('peer:announce', function(data) {
    var pc;
    var monitor;

    // if the room is not a match, abort
    if (data.room !== room) {
      return;
    }

    // create a peer connection
    pc = peers[data.id] = rtc.createConnection(opts, (opts || {}).constraints);

    // add the local streams
    localStreams.forEach(function(stream) {
      pc.addStream(stream);
    });

    // add the data channels
    // do this differently based on whether the connection is a
    // master or a slave connection
    if (signaller.isMaster(data.id)) {
      debug('is master, creating data channels: ', Object.keys(channels));

      // unless the heartbeat is disabled then create a heartbeat datachannel
      if (! disableHeartbeat) {
        initHeartbeat(
          pc.createDataChannel(CHANNEL_HEARTBEAT, {
            ordered: false
          }),
          pc,
          data
        );
      }

      // create the channels
      Object.keys(channels).forEach(function(label) {
        gotPeerChannel(pc.createDataChannel(label, channels[label]), pc, data);
      });
    }
    else {
      pc.ondatachannel = function(evt) {
        var channel = evt && evt.channel;

        // if we have no channel, abort
        if (! channel) {
          return;
        }

        // if the channel is the heartbeat, then init the heartbeat
        if (channel.label === CHANNEL_HEARTBEAT) {
          initHeartbeat(channel, pc, data);
        }
        // otherwise, if this is a known channel, initialise it
        else if (channels[channel.label] !== undefined) {
          gotPeerChannel(channel, pc, data);
        }
      };
    }

    // couple the connections
    monitor = rtc.couple(pc, data.id, signaller, opts);

    // emit the peer event as per <= rtc-quickconnect@0.7
    signaller.emit('peer', pc, data.id, data, monitor);

    // once active, trigger the peer connect event
    monitor.once('active', function() {
      signaller.emit('peer:connect', pc, data.id, data);
    });

    // if we are the master connnection, create the offer
    // NOTE: this only really for the sake of politeness, as rtc couple
    // implementation handles the slave attempting to create an offer
    if (signaller.isMaster(data.id)) {
      monitor.createOffer();
    }
  });

  // announce ourselves to our new friend
  setTimeout(function() {
    var data = extend({}, profile, { room: room });

    // announce and emit the local announce event
    signaller.announce(data);
    signaller.emit('local:announce', data);
  }, 0);

  /**
    ### Quickconnect Broadcast and Data Channel Helper Functions

    The following are functions that are patched into the `rtc-signaller`
    instance that make working with and creating functional WebRTC applications
    a lot simpler.

  **/

  /**
    #### broadcast(stream)

    Add the stream to the set of local streams that we will broadcast
    to other peers.

  **/
  signaller.broadcast = function(stream) {
    localStreams.push(stream);
    return signaller;
  };

  /**
    #### close()

    The `close` function provides a convenient way of closing all associated
    peer connections.
  **/
  signaller.close = function() {
    Object.keys(peers).forEach(function(id) {
      if (peers[id]) {
        peers[id].close();
      }
    });

    // reset the peer references
    peers = {};
  };

  /**
    #### createDataChannel(label, config)

    Request that a data channel with the specified `label` is created on
    the peer connection.  When the data channel is open and available, an
    event will be triggered using the label of the data channel.

    For example, if a new data channel was requested using the following
    call:

    ```js
    var qc = quickconnect('http://rtc.io/switchboard').createDataChannel('test');
    ```

    Then when the data channel is ready for use, a `test:open` event would
    be emitted by `qc`.

  **/
  signaller.createDataChannel = function(label, opts) {
    // save the data channel opts in the local channels dictionary
    channels[label] = opts || null;
    return signaller;
  };

  /**
    #### profile(data)

    Update the profile data with the attached information, so when
    the signaller announces it includes this data in addition to any
    room and id information.

  **/
  signaller.profile = function(data) {
    extend(profile, data);
    return signaller;
  };

  // pass the signaller on
  return signaller;
};<|endoftext|>


<commit_before>"use strict";

var gulp = require("gulp"),
	gutil = require("gulp-util"),
	through2 = require("through2"),
	util = require("util"),
	fs = require("fs"),
	toposort = require("toposort-class"),
	concat = require("gulp-concat");

module.exports = function(filename, sources) {
	if (!filename) {
		throw new gutil.PluginError("gulp-concat-vendor", "Required parameter filename is missing");
	}

	var mySources = {},
		myLibs = [],
		myFiles = [],
		myInfo = [];

	var bufferContents = function(file, enc, callback) {
		if(file.isStream()) {
			this.emit("error", new gutil.PluginError("gulp-concat-vendor", "Streaming not supported"));
			return callback();
		}

		if(!file.isNull()) {
			myFiles.push(file.path);
			return callback();
		}

		var myPath = util.format("%s/.bower.json", file.path);
		fs.exists(myPath, function(exists) {
  			if (exists) {
				fs.readFile(myPath, "utf8", function(error, data) {
					if(!!error || !data) {
						return callback();
					}

					var myData = JSON.parse(data);

					if(!!myData.main) {
						var myMain = [].concat(myData.main),
							mySourcePath = util.format("%s/%s", file.path, myMain[0]);

						myInfo.push(myData);
						mySources[myData.name] = mySourcePath;

						callback();
					}
					else {
						console.log(util.format("Skipping library @ %s. Bower.js is missing 'main' property.", file.path));
						callback();
					}
				});
  			} else {
    			console.log(util.format("Skipping library @ %s. Couldn't find %s", file.path, myPath));
    			callback();
  			}
		});
	};

	var endStream = function() {
		var mySort = new toposort();

		myInfo.forEach(function(data) {
			var myDependencies = [];
			if(!!data.dependencies) {
				myDependencies = Object.keys(data.dependencies);
			}

			mySort.add(data.name, myDependencies);
		});

		myLibs.push.apply(myLibs, mySort.sort().reverse().map(function(name) {
			return mySources[name];
		}));

		myLibs = myLibs.concat(myFiles);

		gulp.src(myLibs)
			.pipe(concat(filename))
			.on("data", function(data) {
				this.push(data);
				this.emit("end");
			}.bind(this));
	}

	return through2.obj(bufferContents, endStream);
};
<commit_msg>Checks main prop extname for JS filetype, else skip package.<commit_after>"use strict";

var gulp = require("gulp"),
        path = require("path"),
	gutil = require("gulp-util"),
	through2 = require("through2"),
	util = require("util"),
	fs = require("fs"),
	toposort = require("toposort-class"),
	concat = require("gulp-concat");

module.exports = function(filename, sources) {
	if (!filename) {
		throw new gutil.PluginError("gulp-concat-vendor", "Required parameter filename is missing");
	}

	var mySources = {},
		myLibs = [],
		myFiles = [],
		myInfo = [];

	var bufferContents = function(file, enc, callback) {
		if(file.isStream()) {
			this.emit("error", new gutil.PluginError("gulp-concat-vendor", "Streaming not supported"));
			return callback();
		}

		if(!file.isNull()) {
			myFiles.push(file.path);
			return callback();
		}

		var myPath = util.format("%s/.bower.json", file.path);
		fs.exists(myPath, function(exists) {
  			if (exists) {
				fs.readFile(myPath, "utf8", function(error, data) {
					if(!!error || !data) {
						return callback();
					}

					var myData = JSON.parse(data);

					if(!!myData.main) {
                                                if( path.extname( myData.main ) != '.js' ) return;
						var myMain = [].concat(myData.main),
							mySourcePath = util.format("%s/%s", file.path, myMain[0]);

						myInfo.push(myData);
						mySources[myData.name] = mySourcePath;

						callback();
					}
					else {
						console.log(util.format("Skipping library @ %s. Bower.js is missing 'main' property.", file.path));
						callback();
					}
				});
  			} else {
    			console.log(util.format("Skipping library @ %s. Couldn't find %s", file.path, myPath));
    			callback();
  			}
		});
	};

	var endStream = function() {
		var mySort = new toposort();

		myInfo.forEach(function(data) {
			var myDependencies = [];
			if(!!data.dependencies) {
				myDependencies = Object.keys(data.dependencies);
			}

			mySort.add(data.name, myDependencies);
		});

		myLibs.push.apply(myLibs, mySort.sort().reverse().map(function(name) {
			return mySources[name];
		}));

		myLibs = myLibs.concat(myFiles);

		gulp.src(myLibs)
			.pipe(concat(filename))
			.on("data", function(data) {
				this.push(data);
				this.emit("end");
			}.bind(this));
	}

	return through2.obj(bufferContents, endStream);
};
<|endoftext|>


<commit_before>module.exports = {
  extends: ['airbnb', 'prettier', 'prettier/react'],
  plugins: ['prettier'],
  parser: 'babel-eslint',
  env: {
    // allow browser globals
    browser: true,
  },
  rules: {
    // allow require() calls
    'global-require': 0,

    // ensure that default, named, and namespaced imports have been exported by the target file
    'import/default': 2,
    'import/named': 2,
    'import/namespace': [2, {allowComputed: true}],

    // require all module imports to be declared as (dev-)dependencies in package.json
    'import/no-extraneous-dependencies': [2, {devDependencies: true}],

    // require import groups to be ordered by specificity and separated by linebreaks
    'import/order': [2, {'newlines-between': 'always'}],

    // enforce conciseness in import paths
    'import/no-useless-path-segments': 2,

    // allow non-ID-linked <label>s to accomodate those containing linked <input>s
    'jsx-a11y/label-has-for': 0,

    // allow supposedly-confusing arrows
    'no-confusing-arrow': 0,

    // disallow confusing global browser variables
    'no-restricted-globals': ['error', 'event', 'find'],

    // allow event listeners on static elements (e.g. onClick on divs)
    'jsx-a11y/no-static-element-interactions': 0,

    // allow react-router's <Link to> as a valid href
    // TODO: remove when https://github.com/airbnb/javascript/pull/1648 is released
    'jsx-a11y/anchor-is-valid': [2, {
      components: ['Link'],
      specialLink: ['to'],
      aspects: ['noHref', 'invalidHref', 'preferButton'],
    }],

    'prettier/prettier': [2, {
      printWidth: 100,
      semi: false,
      singleQuote: true,
      trailingComma: 'es5',
      bracketSpacing: false,
    }],

    // disallow .jsx files for consistency
    'react/jsx-filename-extension': 0,

    // do not require default props for optional props
    'react/require-default-props': 0,

    'react/sort-comp': [2, {
      order: [
        'static-methods',
        'instance-variables',
        'lifecycle',
        '/^(on|handle).+$/',
        'getters',
        'setters',
        '/^(get|set).+$/',
        'instance-methods',
        'everything-else',
        'rendering',
      ],
      groups: {
        rendering: ['/^render.+$/', 'render']
      },
    }]
  },
  settings: {
    // do not attempt to parse npm modules or non-JS files for exports
    'import/ignore': ['node_modules', '.(png|svg|jpg|css|pdf)$'],
    'import/extensions': ['.js'],
    react: {version: '16.3.2'},
  },
}
<commit_msg>Disallow accessing `this.state` inside of `setState`<commit_after>module.exports = {
  extends: ['airbnb', 'prettier', 'prettier/react'],
  plugins: ['prettier'],
  parser: 'babel-eslint',
  env: {
    // allow browser globals
    browser: true,
  },
  rules: {
    // allow require() calls
    'global-require': 0,

    // ensure that default, named, and namespaced imports have been exported by the target file
    'import/default': 2,
    'import/named': 2,
    'import/namespace': [2, {allowComputed: true}],

    // require all module imports to be declared as (dev-)dependencies in package.json
    'import/no-extraneous-dependencies': [2, {devDependencies: true}],

    // require import groups to be ordered by specificity and separated by linebreaks
    'import/order': [2, {'newlines-between': 'always'}],

    // enforce conciseness in import paths
    'import/no-useless-path-segments': 2,

    // allow non-ID-linked <label>s to accomodate those containing linked <input>s
    'jsx-a11y/label-has-for': 0,

    // allow supposedly-confusing arrows
    'no-confusing-arrow': 0,

    // disallow confusing global browser variables
    'no-restricted-globals': ['error', 'event', 'find'],

    // allow event listeners on static elements (e.g. onClick on divs)
    'jsx-a11y/no-static-element-interactions': 0,

    // allow react-router's <Link to> as a valid href
    // TODO: remove when https://github.com/airbnb/javascript/pull/1648 is released
    'jsx-a11y/anchor-is-valid': [2, {
      components: ['Link'],
      specialLink: ['to'],
      aspects: ['noHref', 'invalidHref', 'preferButton'],
    }],

    'prettier/prettier': [2, {
      printWidth: 100,
      semi: false,
      singleQuote: true,
      trailingComma: 'es5',
      bracketSpacing: false,
    }],

    // disallow .jsx files for consistency
    'react/jsx-filename-extension': 0,

    // disallow accessing `this.state` inside of `setState`
    'react/no-access-state-in-setstate': 2,

    // do not require default props for optional props
    'react/require-default-props': 0,

    'react/sort-comp': [2, {
      order: [
        'static-methods',
        'instance-variables',
        'lifecycle',
        '/^(on|handle).+$/',
        'getters',
        'setters',
        '/^(get|set).+$/',
        'instance-methods',
        'everything-else',
        'rendering',
      ],
      groups: {
        rendering: ['/^render.+$/', 'render']
      },
    }]
  },
  settings: {
    // do not attempt to parse npm modules or non-JS files for exports
    'import/ignore': ['node_modules', '.(png|svg|jpg|css|pdf)$'],
    'import/extensions': ['.js'],
    react: {version: '16.3.2'},
  },
}
<|endoftext|>


<commit_before>/**
 * Module dependencies
 */

var Connection = require('./connection')
  , events = require('events')
  , util = require('util')
  , crypto = require('crypto')
  , net = require('net');

/**
 * Default options
 */

var defaultConnectOptions = {
  keepalive: 10000,
  clientId: 'mqttjs_' + crypto.randomBytes(16).toString('hex'),
  protocolId: 'MQIsdp',
  protocolVersion: 3
};

var defaultPort = 1883
  , defaultHost = 'localhost';

var nop = function(){};

/**
 * MqttClient constructor
 *
 * @param <Number> [port] - broker port
 * @param <String> [host] - broker hostname
 * @param <Object> [options] - connection options
 * (see Connection#connect)
 */
var MqttClient = module.exports.MqttClient =
function MqttClient(stream, options) {
  if (!this instanceof MqttClient) {
    return new MqttClient(stream, options);
  }

  this.stream = stream;
  this.options = options || {};

  // Defaults
  for(var k in defaultConnectOptions) {
    if ('undefined' === typeof this.options[k]) {
      this.options[k] = defaultConnectOptions[k];
    } else {
      this.options[k] = options[k];
    }
  }

  this.conn = new Connection(this.stream);

  this.nextId = 0;

  // Inflight messages
  this.inflight = {
    puback: {},
    pubrec: {},
    pubcomp: {},
    suback: {},
    unsuback: {}
  }

  // Incoming messages
  this.incoming = {
    pubrel: {}
  };

  // Send a connect packet on stream connect
  this.stream.on('connect',
      this.conn.connect.bind(this.conn, this.options));

  // Handle connack
  this.conn.on('connack', this._handleConnack.bind(this));

  // Handle incoming publish
  this.conn.on('publish', this._handlePublish.bind(this));

  // Handle incoming acks
  this.conn.on('puback', this._handleAck.bind(this));
  this.conn.on('pubrec', this._handleAck.bind(this));
  this.conn.on('pubcomp', this._handleAck.bind(this));
  this.conn.on('suback', this._handleAck.bind(this));
  this.conn.on('unsuback', this._handleAck.bind(this));

  // Handle outgoing acks
  this.conn.on('pubrel', this._handlePubrel.bind(this));

  // Echo errors
  this.conn.on('error', this.emit.bind(this));
  this.stream.on('error', this.emit.bind(this));

  // Setup ping timer
  this._setupPingTimer();

  events.EventEmitter.call(this);
};
util.inherits(MqttClient, events.EventEmitter);

/**
 * publish - publish <message> to <topic>
 *
 * @param <String> topic - topic to publish to
 * @param <String, Buffer> message - message to publish
 * @param <Object> [opts] - publish options, includes:
 *    <Number> qos - qos level to publish on
 *    <Boolean> retain - whether or not to retain the message
 * @param <Function> [callback] - function(err){}
 *    called when publish succeeds or fails
 * @api public
 */
MqttClient.prototype.publish =
function(topic, message, opts, callback) {
  var packet;

  // .publish(topic, payload, cb);
  if ('function' === typeof opts) {
    callback = opts;
    opts = null;
  }

  // Default opts
  if(!opts) opts = {qos: 0, retain: false};

  callback = callback || nop;

  packet = {
    topic: topic,
    payload: message,
    qos: opts.qos,
    retain: opts.retain,
    messageId: this.nextId
  }

  this.conn.publish(packet);

  switch (opts.qos) {
    case 0:
      // Immediately callback
      callback();
      break;
    case 1:
      // Add to puback callbacks
      this.inflight.puback[this.nextId++] = callback;
      break;
    case 2:
      // Add to pubrec callbacks
      this.inflight.pubrec[this.nextId++] = callback;
      break
    default:
      break;
  }
};

/**
 * subscribe - subscribe to <topic>
 *
 * @param <String, Array> topic - topic(s) to subscribe to
 * @param <Object> [opts] - subscription options, includes:
 *    <Number> qos - subscribe qos level
 * @param <Function> [callback] - function(err){} fires on suback
 * @api public
 */
MqttClient.prototype.subscribe =
function(topic, opts, callback) {
  var subs = [];

  // .subscribe('topic', callback)
  if ('function' === typeof opts) {
    callback = opts;
    opts = null;
  }

  // Defaults
  opts = opts || {qos: 0};
  callback = callback || nop;

  if ('string' === typeof topic) {
    subs.push({topic: topic, qos: opts.qos});
  } else if ('object' === typeof topic) {
    // TODO: harder array check
    for (var i = 0; i < topic.length; i += 1) {
      var t = topic[i];
      subs.push({topic: t, qos: opts.qos});
    }
  } else {
    // Error!
  }

  var packet = {
    subscriptions: subs,
    qos: 1,
    messageId: this.nextId,
    retain: false,
    dup: false
  };

  this.conn.subscribe(packet);
  this.inflight.suback[this.nextId++] = callback;
};

/**
 * unsubscribe - unsubscribe from topic(s)
 *
 * @param <String, Array> topic - topics to unsubscribe from
 * @param <Function> [callback] - callback fired on unsuback
 */
MqttClient.prototype.unsubscribe = function(topic, callback) {
  callback = callback || nop;
  var unsubs;

  if ('string' === typeof topic) {
    unsubs = [topic];
  } else if ('object' === typeof topic && topic.length) {
    unsubs = topic;
  }

  this.conn.unsubscribe({
    unsubscriptions: unsubs,
    messageId: this.nextId
  });

  this.inflight.unsuback[this.nextId++] = callback;
};

/**
 * _setupPingTimer
 *
 * @api private
 */

MqttClient.prototype._setupPingTimer = function() {
  this.pingTimer = setTimeout(function () {
    this.conn.pingreq();
  }.bind(this), this.options.keepalive / 2);
};

/**
 * _handleConnack
 *
 * @param <Object> packet
 * @api private
 */

MqttClient.prototype._handleConnack = function(packet) {
  var rc = packet.returnCode;

  // TODO: move to protocol
  var errors = [
    '',
    'Unacceptable protocol version',
    'Identifier rejected',
    'Server unavailable',
    'Bad username or password',
    'Not authorized'
  ];

  if (rc === 0) {
    this.emit('connect');
  } else if (rc > 0) {
    this.emit('error',
        new Error('Connection refused: ' + errors[rc]));
  }
};

/**
 * _handlePublish
 *
 * @param <Object> packet
 * @api private
 */

MqttClient.prototype._handlePublish = function(packet) {
  var topic = packet.topic
    , message = packet.payload
    , qos = packet.qos
    , mid = packet.messageId;

  switch (qos) {
    case 0:
      this.emit('message', topic, message);
      break;
    case 1:
      this.conn.puback({messageId: mid});
      this.emit('message', topic, message);
      break;
    case 2:
      this.conn.pubrec({messageId: mid});
      this.incoming.pubrel[mid] = {topic: topic, message: message};
      break;
    default:
      break;
  }
};

/**
 * _handleAck
 *
 * @param <Object> packet
 * @api private
 */

MqttClient.prototype._handleAck = function(packet) {
  var mid = packet.messageId
    , type = packet.cmd
    , cb = this.inflight[type][mid];

  // Check if callback exists
  if(!cb) this.emit('error', new Error('Unknown message id'));

  // Process
  switch (type) {
    case 'puback':
      // Callback - we're done
      cb();
      break;
    case 'pubrec':
      // Pubrel and add to pubcomp list
      this.conn.pubrel(packet);
      this.inflight.pubcomp[mid] = cb;
      break;
    case 'pubcomp':
      // Callback - we're done
      cb();
      break;
    case 'suback':
      cb();
      break;
    case 'unsuback':
      cb();
      break;
    default:
      // code
  }

  // Remove from queue
  delete this.inflight[type][mid];
};

/**
 * _handlePubrel
 *
 * @param <Object> packet
 * @api private
 */

MqttClient.prototype._handlePubrel = function(packet) {
  var mid = packet.messageId
    , data = this.incoming.pubrel[mid];

  if (!data) this.emit('error', new Error('Unknown message id'));
  this.conn.pubcomp({messageId: mid});
  this.emit('message', data.topic, data.message);
};

/**
 * createClient -
 *
 * @param <Number> [port]
 * @param <String> [host]
 * @param <Object> [opts]
 */

module.exports.createClient = function(port, host, opts) {
  var net_client, mqtt_client;

  if ('object' === typeof port) {
    // createClient({})
    opts = port;
    port = defaultPort;
    host = defaultHost;
  } else if ('object' === typeof host) {
    // createClient(1883, {})
    opts = host;
    host = defaultHost;
  }

  net_client = net.createConnection(port, host);
  mqtt_client = new MqttClient(net_client, opts);

  return mqtt_client;
};
<commit_msg>Ping every <keepalive>ms<commit_after>/**
 * Module dependencies
 */

var Connection = require('./connection')
  , events = require('events')
  , util = require('util')
  , crypto = require('crypto')
  , net = require('net');

/**
 * Default options
 */

var defaultConnectOptions = {
  keepalive: 10000,
  clientId: 'mqttjs_' + crypto.randomBytes(16).toString('hex'),
  protocolId: 'MQIsdp',
  protocolVersion: 3
};

var defaultPort = 1883
  , defaultHost = 'localhost';

var nop = function(){};

/**
 * MqttClient constructor
 *
 * @param <Number> [port] - broker port
 * @param <String> [host] - broker hostname
 * @param <Object> [options] - connection options
 * (see Connection#connect)
 */
var MqttClient = module.exports.MqttClient =
function MqttClient(stream, options) {
  if (!this instanceof MqttClient) {
    return new MqttClient(stream, options);
  }

  this.stream = stream;
  this.options = options || {};

  // Defaults
  for(var k in defaultConnectOptions) {
    if ('undefined' === typeof this.options[k]) {
      this.options[k] = defaultConnectOptions[k];
    } else {
      this.options[k] = options[k];
    }
  }

  this.conn = new Connection(this.stream);

  this.nextId = 0;

  // Inflight messages
  this.inflight = {
    puback: {},
    pubrec: {},
    pubcomp: {},
    suback: {},
    unsuback: {}
  }

  // Incoming messages
  this.incoming = {
    pubrel: {}
  };

  // Send a connect packet on stream connect
  this.stream.on('connect',
      this.conn.connect.bind(this.conn, this.options));

  // Handle connack
  this.conn.on('connack', this._handleConnack.bind(this));

  // Handle incoming publish
  this.conn.on('publish', this._handlePublish.bind(this));

  // Handle incoming acks
  this.conn.on('puback', this._handleAck.bind(this));
  this.conn.on('pubrec', this._handleAck.bind(this));
  this.conn.on('pubcomp', this._handleAck.bind(this));
  this.conn.on('suback', this._handleAck.bind(this));
  this.conn.on('unsuback', this._handleAck.bind(this));

  // Handle outgoing acks
  this.conn.on('pubrel', this._handlePubrel.bind(this));

  // Echo errors
  this.conn.on('error', this.emit.bind(this));
  this.stream.on('error', this.emit.bind(this));

  // Setup ping timer
  this._setupPingTimer();

  events.EventEmitter.call(this);
};
util.inherits(MqttClient, events.EventEmitter);

/**
 * publish - publish <message> to <topic>
 *
 * @param <String> topic - topic to publish to
 * @param <String, Buffer> message - message to publish
 * @param <Object> [opts] - publish options, includes:
 *    <Number> qos - qos level to publish on
 *    <Boolean> retain - whether or not to retain the message
 * @param <Function> [callback] - function(err){}
 *    called when publish succeeds or fails
 * @api public
 */
MqttClient.prototype.publish =
function(topic, message, opts, callback) {
  var packet;

  // .publish(topic, payload, cb);
  if ('function' === typeof opts) {
    callback = opts;
    opts = null;
  }

  // Default opts
  if(!opts) opts = {qos: 0, retain: false};

  callback = callback || nop;

  packet = {
    topic: topic,
    payload: message,
    qos: opts.qos,
    retain: opts.retain,
    messageId: this.nextId
  }

  this.conn.publish(packet);

  switch (opts.qos) {
    case 0:
      // Immediately callback
      callback();
      break;
    case 1:
      // Add to puback callbacks
      this.inflight.puback[this.nextId++] = callback;
      break;
    case 2:
      // Add to pubrec callbacks
      this.inflight.pubrec[this.nextId++] = callback;
      break
    default:
      break;
  }
};

/**
 * subscribe - subscribe to <topic>
 *
 * @param <String, Array> topic - topic(s) to subscribe to
 * @param <Object> [opts] - subscription options, includes:
 *    <Number> qos - subscribe qos level
 * @param <Function> [callback] - function(err){} fires on suback
 * @api public
 */
MqttClient.prototype.subscribe =
function(topic, opts, callback) {
  var subs = [];

  // .subscribe('topic', callback)
  if ('function' === typeof opts) {
    callback = opts;
    opts = null;
  }

  // Defaults
  opts = opts || {qos: 0};
  callback = callback || nop;

  if ('string' === typeof topic) {
    subs.push({topic: topic, qos: opts.qos});
  } else if ('object' === typeof topic) {
    // TODO: harder array check
    for (var i = 0; i < topic.length; i += 1) {
      var t = topic[i];
      subs.push({topic: t, qos: opts.qos});
    }
  } else {
    // Error!
  }

  var packet = {
    subscriptions: subs,
    qos: 1,
    messageId: this.nextId,
    retain: false,
    dup: false
  };

  this.conn.subscribe(packet);
  this.inflight.suback[this.nextId++] = callback;
};

/**
 * unsubscribe - unsubscribe from topic(s)
 *
 * @param <String, Array> topic - topics to unsubscribe from
 * @param <Function> [callback] - callback fired on unsuback
 */
MqttClient.prototype.unsubscribe = function(topic, callback) {
  callback = callback || nop;
  var unsubs;

  if ('string' === typeof topic) {
    unsubs = [topic];
  } else if ('object' === typeof topic && topic.length) {
    unsubs = topic;
  }

  this.conn.unsubscribe({
    unsubscriptions: unsubs,
    messageId: this.nextId
  });

  this.inflight.unsuback[this.nextId++] = callback;
};

/**
 * _setupPingTimer
 *
 * @api private
 */

MqttClient.prototype._setupPingTimer = function() {
  this.pingTimer = setTimeout(function () {
    this.conn.pingreq();
  }.bind(this), this.options.keepalive);
};

/**
 * _handleConnack
 *
 * @param <Object> packet
 * @api private
 */

MqttClient.prototype._handleConnack = function(packet) {
  var rc = packet.returnCode;

  // TODO: move to protocol
  var errors = [
    '',
    'Unacceptable protocol version',
    'Identifier rejected',
    'Server unavailable',
    'Bad username or password',
    'Not authorized'
  ];

  if (rc === 0) {
    this.emit('connect');
  } else if (rc > 0) {
    this.emit('error',
        new Error('Connection refused: ' + errors[rc]));
  }
};

/**
 * _handlePublish
 *
 * @param <Object> packet
 * @api private
 */

MqttClient.prototype._handlePublish = function(packet) {
  var topic = packet.topic
    , message = packet.payload
    , qos = packet.qos
    , mid = packet.messageId;

  switch (qos) {
    case 0:
      this.emit('message', topic, message);
      break;
    case 1:
      this.conn.puback({messageId: mid});
      this.emit('message', topic, message);
      break;
    case 2:
      this.conn.pubrec({messageId: mid});
      this.incoming.pubrel[mid] = {topic: topic, message: message};
      break;
    default:
      break;
  }
};

/**
 * _handleAck
 *
 * @param <Object> packet
 * @api private
 */

MqttClient.prototype._handleAck = function(packet) {
  var mid = packet.messageId
    , type = packet.cmd
    , cb = this.inflight[type][mid];

  // Check if callback exists
  if(!cb) this.emit('error', new Error('Unknown message id'));

  // Process
  switch (type) {
    case 'puback':
      // Callback - we're done
      cb();
      break;
    case 'pubrec':
      // Pubrel and add to pubcomp list
      this.conn.pubrel(packet);
      this.inflight.pubcomp[mid] = cb;
      break;
    case 'pubcomp':
      // Callback - we're done
      cb();
      break;
    case 'suback':
      cb();
      break;
    case 'unsuback':
      cb();
      break;
    default:
      // code
  }

  // Remove from queue
  delete this.inflight[type][mid];
};

/**
 * _handlePubrel
 *
 * @param <Object> packet
 * @api private
 */

MqttClient.prototype._handlePubrel = function(packet) {
  var mid = packet.messageId
    , data = this.incoming.pubrel[mid];

  if (!data) this.emit('error', new Error('Unknown message id'));
  this.conn.pubcomp({messageId: mid});
  this.emit('message', data.topic, data.message);
};

/**
 * createClient -
 *
 * @param <Number> [port]
 * @param <String> [host]
 * @param <Object> [opts]
 */

module.exports.createClient = function(port, host, opts) {
  var net_client, mqtt_client;

  if ('object' === typeof port) {
    // createClient({})
    opts = port;
    port = defaultPort;
    host = defaultHost;
  } else if ('object' === typeof host) {
    // createClient(1883, {})
    opts = host;
    host = defaultHost;
  }

  net_client = net.createConnection(port, host);
  mqtt_client = new MqttClient(net_client, opts);

  return mqtt_client;
};
<|endoftext|>


<commit_before>var pull    = require('pull-stream')
var paramap = require('pull-paramap')
var path    = require('path')
var unpack  = require('npmd-unpack').unpack
var mkdirp  = require('mkdirp')
var fs      = require('fs')
var leaves  = require('npmd-leaves')
var merge   = require('pull-merge')
var deps    = require('get-deps')
var pushable  = require('pull-pushable')

function linkable(pkg, opts) {
  var linkRoot = (opts && opts.linkRoot)
    || path.join(process.env.HOME, '.npmd', 'linkable')
  return path.join(linkRoot, 'string' === typeof pkg ? pkg : pkg.hash)
}

//install a module with a symlink.
//adds $moduleDir/node_modules/$name -> $hash

function linkModule(moduleDir, name, hash, opts, cb) {
  if(!cb)
    cb = opts, opts = {}
  name = name.name || name
  var source = path.join(moduleDir, 'node_modules', name)
  var target = path.join(linkable(hash, opts), 'package')

  fs.readlink (source, function (err, found) {
    console.log(source, target, found)
    if(found === target)
      done()
    else if(err)
      fs.symlink(target, source, done)
    else
      fs.unlink(source, function (err) {
        if(err) return cb(err)
        fs.symlink(target, source, done)
      })
  })

  function done (err) {
    if(err) {
      err.source = source
      err.target = target
    }
    cb(err)
  }
}

//var spawn = require('child_process').spawn
//
//function compile(opts, cb) {
//  var cp = spawn('node-gyp', ['rebuild'], {
//    cwd: opts.target
//  })
//  cp.stdout.pipe(process.stdout)
//  cp.stderr.pipe(process.stderr)
//  cp.on('exit', function (code) {
//    cb(code === 0 ? null : new Error('exit status:'+code))
//  })
//}

function once(fun) {
  return function () {
    var args = [].slice.call(arguments)
    var cb = args.pop()
    var err = new Error('twice!')
    var i = 0
    args.push(function (err, val) {
      if(i++) throw err
      cb(err, val)
    })
    fun.apply(this, args)
  }
}

var link =
module.exports = function (ltree, opts, cb) {
  if(!cb)
    cb = opts, opts = {}
  var dirs = {}
  var linked = {}
  var queue = pushable()

  pull(
    pull.values(ltree),
    paramap(function (pkg, cb) {
      var dir = linkable(pkg, opts)
      if(dirs[dir]) return cb(null, pkg)
      fs.stat(dir, function (err) {

        if(dirs[dir]) return cb(null, pkg)
        dirs[dir] = true
        if(!err) return cb(null, pkg)

        unpack(pkg, {
          cache: opts.cache,
          target: dir
        }, function (err) {
          console.log('unpacked', pkg.name, pkg.version)
          if(err) return cb(err)
          cb(null, pkg)
        })
      })
    }),
    pull.asyncMap(function (pkg, cb) {
      //unpack to
      //.npmd/linkable/HASH
      //then symlink to the deps

      var moduleDir = path.join(linkable(pkg), 'package')

      if(linked[pkg.hash]) return cb(null, pkg)
      linked[pkg.hash] = true
      mkdirp(path.join(moduleDir, 'node_modules'), function () {
        var n = 0

        for(var name in pkg.dependencies) {
          n ++
          linkModule(moduleDir, name, pkg.dependencies[name], next)
        }
        if(!n) cb()

        function next (err) {
          if(--n) return
          cb()
        }
      })
    }),
    pull.drain(null, function (err) {
      cb(err, ltree)
    })
  )
}

module.exports.db = function (db, config) {
  db.methods.lResolve = {type: 'async'}
  db.lResolve = function (module, opts, cb) {
    if(!cb)
      cb = opts, opts = {}

    opts.hash = true
    opts.check = false

    db.resolve(module, opts, function (err, tree) {
      if(err) cb(err)
      cb(err, leaves(tree), tree)
    })
  }
}

var all = module.exports.all = function (tree, opts, cb) {
  var roots = leaves.roots(tree), n = 0
  opts = opts || {}
  opts.dir = opts.dir || process.cwd()

  var i = 0
  link(tree, function (err) {
    if(err) throw err
    if(i++) throw new Error('finished twice!')

    for(var k in roots) {
      n ++
      ;(function (root) {
        mkdirp(path.join(opts.dir, 'node_modules'), function () {
        console.log(root.name, root.version, root.hash)
          linkModule(opts.dir, root.name, root.hash, opts, next)
        })
      })(roots[k])
    }
  })

  function next (err) {
    if(err) return cb(err, n = null)
    if(--n) return
    cb()
  }

}

module.exports.commands = function (db) {
  var start = Date.now()
  db.commands.push(function (db, config, cb) {
    var args = config._.slice()
    var cmd = args.shift()
    if(!args.length)
      args = deps(process.cwd(), config)

    if('link' === cmd) {
      db.lResolve(args, config, function (err, tree) {
        if(err) cb(err)
        else all(tree, config, cb)
      })
    } else if('lresolve' === cmd) {
      db.lResolve(args, config, function (err, tree, root) {
        if(err) return cb(err)
        console.log(JSON.stringify(tree, null, 2))
        cb(null, tree)
      })
    }
    else
      return

    return true
  })
}

module.exports.linkModule = linkModule
<commit_msg>not using this stuff yet<commit_after>var pull    = require('pull-stream')
var paramap = require('pull-paramap')
var path    = require('path')
var unpack  = require('npmd-unpack').unpack
var mkdirp  = require('mkdirp')
var fs      = require('fs')
var leaves  = require('npmd-leaves')
//var merge   = require('pull-merge')
var deps    = require('get-deps')
//var pushable  = require('pull-pushable')

function linkable(pkg, opts) {
  var linkRoot = (opts && opts.linkRoot)
    || path.join(process.env.HOME, '.npmd', 'linkable')
  return path.join(linkRoot, 'string' === typeof pkg ? pkg : pkg.hash)
}

//install a module with a symlink.
//adds $moduleDir/node_modules/$name -> $hash

function linkModule(moduleDir, name, hash, opts, cb) {
  if(!cb)
    cb = opts, opts = {}
  name = name.name || name
  var source = path.join(moduleDir, 'node_modules', name)
  var target = path.join(linkable(hash, opts), 'package')

  fs.readlink (source, function (err, found) {
    console.log(source, target, found)
    if(found === target)
      done()
    else if(err)
      fs.symlink(target, source, done)
    else
      fs.unlink(source, function (err) {
        if(err) return cb(err)
        fs.symlink(target, source, done)
      })
  })

  function done (err) {
    if(err) {
      err.source = source
      err.target = target
    }
    cb(err)
  }
}

//var spawn = require('child_process').spawn
//
//function compile(opts, cb) {
//  var cp = spawn('node-gyp', ['rebuild'], {
//    cwd: opts.target
//  })
//  cp.stdout.pipe(process.stdout)
//  cp.stderr.pipe(process.stderr)
//  cp.on('exit', function (code) {
//    cb(code === 0 ? null : new Error('exit status:'+code))
//  })
//}

function once(fun) {
  return function () {
    var args = [].slice.call(arguments)
    var cb = args.pop()
    var err = new Error('twice!')
    var i = 0
    args.push(function (err, val) {
      if(i++) throw err
      cb(err, val)
    })
    fun.apply(this, args)
  }
}

var link =
module.exports = function (ltree, opts, cb) {
  if(!cb)
    cb = opts, opts = {}
  var dirs = {}
  var linked = {}
  var queue = pushable()

  pull(
    pull.values(ltree),
    paramap(function (pkg, cb) {
      var dir = linkable(pkg, opts)
      if(dirs[dir]) return cb(null, pkg)
      fs.stat(dir, function (err) {

        if(dirs[dir]) return cb(null, pkg)
        dirs[dir] = true
        if(!err) return cb(null, pkg)

        unpack(pkg, {
          cache: opts.cache,
          target: dir
        }, function (err) {
          console.log('unpacked', pkg.name, pkg.version)
          if(err) return cb(err)
          cb(null, pkg)
        })
      })
    }),
    pull.asyncMap(function (pkg, cb) {
      //unpack to
      //.npmd/linkable/HASH
      //then symlink to the deps

      var moduleDir = path.join(linkable(pkg), 'package')

      if(linked[pkg.hash]) return cb(null, pkg)
      linked[pkg.hash] = true
      mkdirp(path.join(moduleDir, 'node_modules'), function () {
        var n = 0

        for(var name in pkg.dependencies) {
          n ++
          linkModule(moduleDir, name, pkg.dependencies[name], next)
        }
        if(!n) cb()

        function next (err) {
          if(--n) return
          cb()
        }
      })
    }),
    pull.drain(null, function (err) {
      cb(err, ltree)
    })
  )
}

module.exports.db = function (db, config) {
  db.methods.lResolve = {type: 'async'}
  db.lResolve = function (module, opts, cb) {
    if(!cb)
      cb = opts, opts = {}

    opts.hash = true
    opts.check = false

    db.resolve(module, opts, function (err, tree) {
      if(err) cb(err)
      cb(err, leaves(tree), tree)
    })
  }
}

var all = module.exports.all = function (tree, opts, cb) {
  var roots = leaves.roots(tree), n = 0
  opts = opts || {}
  opts.dir = opts.dir || process.cwd()

  var i = 0
  link(tree, function (err) {
    if(err) throw err
    if(i++) throw new Error('finished twice!')

    for(var k in roots) {
      n ++
      ;(function (root) {
        mkdirp(path.join(opts.dir, 'node_modules'), function () {
        console.log(root.name, root.version, root.hash)
          linkModule(opts.dir, root.name, root.hash, opts, next)
        })
      })(roots[k])
    }
  })

  function next (err) {
    if(err) return cb(err, n = null)
    if(--n) return
    cb()
  }

}

module.exports.commands = function (db) {
  var start = Date.now()
  db.commands.push(function (db, config, cb) {
    var args = config._.slice()
    var cmd = args.shift()
    if(!args.length)
      args = deps(process.cwd(), config)

    if('link' === cmd) {
      db.lResolve(args, config, function (err, tree) {
        if(err) cb(err)
        else all(tree, config, cb)
      })
    } else if('lresolve' === cmd) {
      db.lResolve(args, config, function (err, tree, root) {
        if(err) return cb(err)
        console.log(JSON.stringify(tree, null, 2))
        cb(null, tree)
      })
    }
    else
      return

    return true
  })
}

module.exports.linkModule = linkModule
<|endoftext|>