<commit_before>'use strict';

const config = require('../config');

module.exports = Trade;

function Trade() {
    this.prices = {};
    this.instances = [];

    this.getPrices((prices) => {
        this.prices = prices;
    });
    setInterval(() => {
        this.getPrices((prices) => {
            this.prices = prices;
        });
    }, 21600000);

    this.startBots(() => {
        this.addBotListeners();
        setInterval(() => this.reloadBotSessions(), 3600000);
    });
}

Trade.prototype.getPriceList = function() {
    return this.prices;
}

Trade.prototype.getPrice = function(name, rateType, itemType) {
    return this.prices[name] * config.rates[rateType][itemType] || 0;
}

Trade.prototype.getUserRates = function() {
    return config.rates.user;
}

Trade.prototype.getBotRates = function() {
    return config.rates.bot;
}

Trade.prototype.getTrashPrice = function() {
    return config.rates.trashPriceBelow;
}

Trade.prototype.getIgnorePrice = function() {
    return config.rates.ignoreItemsBelow;
}

Trade.prototype.validateOffer = function(obj, callback) {
    let self = this;

    let userValue = 0;
    let botValue = 0;
    let userCount = 0;
    let botCount = 0;

    if(obj.user.length) {
        self.getInventory(obj.steamID64, '730', '2', (err, data) => {
            if( ! err) {
                let userInventory = data;
                for(let i in userInventory) {
                    let item = userInventory[i];
                    if(obj.user.indexOf(item.assetid) !== -1) {
                        userCount = userCount + 1;
                        userValue += self.getPrice(item.data.market_hash_name, 'user', item.item_type);
                    }
                }

                if(obj.bot.length) {
                    if(typeof config.bots[obj.bot_id] === 'undefined') {
                        return callback('(╯°□°）╯︵ ┻━┻ STAPH NAOW!');
                    }
                    self.getInventory(config.bots[obj.bot_id].steamID64, '730', '2', (err, data) => {
                        if( ! err) {
                            let botInventory = data;
                            for(let i in botInventory) {
                                let item = botInventory[i];
                                if(obj.bot.indexOf(item.assetid) !== -1) {
                                    botCount = botCount + 1;
                                    botValue += self.getPrice(item.data.market_hash_name, 'bot', item.item_type);
                                    if(self.getPrice(item.data.market_hash_name, 'bot', item.item_type) === 0) {
                                        return callback('Could not get a price for item(s). Trade has been cancelled.');
                                    }
                                }
                            }
                            if(userCount !== obj.user.length) {
                                return callback('Some items were not found in users inventory!');
                            }
                            if(botCount !== obj.bot.length) {
                                return callback('Some items were not found in bots inventory!');
                            }
                            if(parseFloat(userValue.toFixed(2)) < parseFloat(botValue.toFixed(2))) {
                                return callback('You do not have enough value!');
                            }
                            return callback(null, true);
                        } else {
                            return callback('Could not verify inventory contents for the trade. Please try again later!');
                        }
                    });
                } else {
                    if(userCount !== obj.user.length) {
                        return callback('Some items were not found in users inventory!' + `${userCount}|${obj.user.length}`);
                    }
                    if(botCount !== obj.bot.length) {
                        return callback('Some items were not found in bots inventory!');
                    }
                    if(parseFloat(userValue.toFixed(2)) < parseFloat(botValue.toFixed(2))) {
                        return callback('You do not have enough value!');
                    }
                    return callback(null, true);
                }
            } else {
                return callback('Could not verify inventory contents for the trade. Please try again later!');
            }
        });
    } else {
        return callback('(╯°□°）╯︵ ┻━┻ STAPH!');
    }

};

require('./bots');
require('./inv');
require('./prices');
<commit_msg>prices fix<commit_after>'use strict';

const config = require('../config');

module.exports = Trade;

function Trade() {
    this.prices = {};
    this.instances = [];

    this.getPrices((prices) => {
        this.prices = prices;
    });
    setInterval(() => {
        this.getPrices((prices) => {
            this.prices = prices;
        });
    }, 21600000);

    this.startBots(() => {
        this.addBotListeners();
        setInterval(() => this.reloadBotSessions(), 3600000);
    });
}

Trade.prototype.getPriceList = function() {
    return this.prices;
}

Trade.prototype.getPrice = function(name, rateType, itemType) {
    return this.prices[name] * config.rates[rateType][itemType.name] || 0;
}

Trade.prototype.getUserRates = function() {
    return config.rates.user;
}

Trade.prototype.getBotRates = function() {
    return config.rates.bot;
}

Trade.prototype.getTrashPrice = function() {
    return config.rates.trashPriceBelow;
}

Trade.prototype.getIgnorePrice = function() {
    return config.rates.ignoreItemsBelow;
}

Trade.prototype.validateOffer = function(obj, callback) {
    let self = this;

    let userValue = 0;
    let botValue = 0;
    let userCount = 0;
    let botCount = 0;

    if(obj.user.length) {
        self.getInventory(obj.steamID64, '730', '2', (err, data) => {
            if( ! err) {
                let userInventory = data;
                for(let i in userInventory) {
                    let item = userInventory[i];
                    if(obj.user.indexOf(item.assetid) !== -1) {
                        userCount = userCount + 1;
                        userValue += self.getPrice(item.data.market_hash_name, 'user', item.item_type);
                    }
                }

                if(obj.bot.length) {
                    if(typeof config.bots[obj.bot_id] === 'undefined') {
                        return callback('(╯°□°）╯︵ ┻━┻ STAPH NAOW!');
                    }
                    self.getInventory(config.bots[obj.bot_id].steamID64, '730', '2', (err, data) => {
                        if( ! err) {
                            let botInventory = data;
                            for(let i in botInventory) {
                                let item = botInventory[i];
                                if(obj.bot.indexOf(item.assetid) !== -1) {
                                    botCount = botCount + 1;
                                    botValue += self.getPrice(item.data.market_hash_name, 'bot', item.item_type);
                                    if(self.getPrice(item.data.market_hash_name, 'bot', item.item_type) === 0) {
                                        return callback('Could not get a price for item(s). Trade has been cancelled.');
                                    }
                                }
                            }
                            if(userCount !== obj.user.length) {
                                return callback('Some items were not found in users inventory!');
                            }
                            if(botCount !== obj.bot.length) {
                                return callback('Some items were not found in bots inventory!');
                            }
                            if(parseFloat(userValue.toFixed(2)) < parseFloat(botValue.toFixed(2))) {
                                return callback('You do not have enough value!');
                            }
                            return callback(null, true);
                        } else {
                            return callback('Could not verify inventory contents for the trade. Please try again later!');
                        }
                    });
                } else {
                    if(userCount !== obj.user.length) {
                        return callback('Some items were not found in users inventory!' + `${userCount}|${obj.user.length}`);
                    }
                    if(botCount !== obj.bot.length) {
                        return callback('Some items were not found in bots inventory!');
                    }
                    if(parseFloat(userValue.toFixed(2)) < parseFloat(botValue.toFixed(2))) {
                        return callback('You do not have enough value!');
                    }
                    return callback(null, true);
                }
            } else {
                return callback('Could not verify inventory contents for the trade. Please try again later!');
            }
        });
    } else {
        return callback('(╯°□°）╯︵ ┻━┻ STAPH!');
    }

};

require('./bots');
require('./inv');
require('./prices');
<|endoftext|>


<commit_before>var EXP_TABLE = new Buffer(512)
var LOG_TABLE = new Buffer(256)

/**
 * Precompute the log and anti-log tables for faster computation later
 *
 * For each possible value in the galois field 2^8, we will pre-compute
 * the logarithm and anti-logarithm (exponential) of this value
 *
 * ref {@link https://en.wikiversity.org/wiki/Reed%E2%80%93Solomon_codes_for_coders#Introduction_to_mathematical_fields}
 */
(function initTables() {
  var x = 1
  for (var i = 0; i < 255; i++) {
    EXP_TABLE[i] = x
    LOG_TABLE[x] = i

    x <<= 1 // multiply by 2

    // The QR code specification says to use byte-wise modulo 100011101 arithmetic.
    // This means that when a number is 256 or larger, it should be XORed with 0x11D.
    if (x & 0x100) { // similar to x >= 256, but a lot faster (because 0x100 == 256)
      x ^= 0x11D
    }
  }

  // Optimization: double the size of the anti-log table so that we don't need to mod 255 to
  // stay inside the bounds (because we will mainly use this table for the multiplication of
  // two GF numbers, no more).
  // @see {@link mul}
  for (i = 255; i < 512; i++) {
    EXP_TABLE[i] = EXP_TABLE[i - 255]
  }
}())

/**
 * Returns log value of n inside Galois Field
 *
 * @param  {Number} n
 * @return {Number}
 */
exports.log = function log(n) {
  if (n < 1) throw new Error('log(' + n + ')')
  return LOG_TABLE[n]
}

/**
 * Returns anti-log value of n inside Galois Field
 *
 * @param  {Number} n
 * @return {Number}
 */
exports.exp = function exp(n) {
  return EXP_TABLE[n]
}

/**
 * Multiplies two number inside Galois Field
 *
 * @param  {Number} x
 * @param  {Number} y
 * @return {Number}
 */
exports.mul = function mul(x, y) {
  if (x === 0 || y === 0) return 0

  // should be EXP_TABLE[(LOG_TABLE[x] + LOG_TABLE[y]) % 255] if EXP_TABLE wasn't oversized
  // @see {@link initTables}
  return EXP_TABLE[LOG_TABLE[x] + LOG_TABLE[y]]
}<commit_msg>add immediate run function<commit_after>var EXP_TABLE = new Buffer(512)
var LOG_TABLE = new Buffer(256)

/**
 * Precompute the log and anti-log tables for faster computation later
 *
 * For each possible value in the galois field 2^8, we will pre-compute
 * the logarithm and anti-logarithm (exponential) of this value
 *
 * ref {@link https://en.wikiversity.org/wiki/Reed%E2%80%93Solomon_codes_for_coders#Introduction_to_mathematical_fields}
 */
;(function initTables() {
  var x = 1
  for (var i = 0; i < 255; i++) {
    EXP_TABLE[i] = x
    LOG_TABLE[x] = i

    x <<= 1 // multiply by 2

    // The QR code specification says to use byte-wise modulo 100011101 arithmetic.
    // This means that when a number is 256 or larger, it should be XORed with 0x11D.
    if (x & 0x100) { // similar to x >= 256, but a lot faster (because 0x100 == 256)
      x ^= 0x11D
    }
  }

  // Optimization: double the size of the anti-log table so that we don't need to mod 255 to
  // stay inside the bounds (because we will mainly use this table for the multiplication of
  // two GF numbers, no more).
  // @see {@link mul}
  for (i = 255; i < 512; i++) {
    EXP_TABLE[i] = EXP_TABLE[i - 255]
  }
}())

/**
 * Returns log value of n inside Galois Field
 *
 * @param  {Number} n
 * @return {Number}
 */
exports.log = function log(n) {
  if (n < 1) throw new Error('log(' + n + ')')
  return LOG_TABLE[n]
}

/**
 * Returns anti-log value of n inside Galois Field
 *
 * @param  {Number} n
 * @return {Number}
 */
exports.exp = function exp(n) {
  return EXP_TABLE[n]
}

/**
 * Multiplies two number inside Galois Field
 *
 * @param  {Number} x
 * @param  {Number} y
 * @return {Number}
 */
exports.mul = function mul(x, y) {
  if (x === 0 || y === 0) return 0

  // should be EXP_TABLE[(LOG_TABLE[x] + LOG_TABLE[y]) % 255] if EXP_TABLE wasn't oversized
  // @see {@link initTables}
  return EXP_TABLE[LOG_TABLE[x] + LOG_TABLE[y]]
}<|endoftext|>


<commit_before>// import toxi from 'toxiclibsjs'
// import Processing from 'processing-js'
//
// Inspired by http://haptic-data.com/toxiclibsjs/examples/attraction2d

window.requestAnimFrame = (function(){ return  window.requestAnimationFrame || window.webkitRequestAnimationFrame || window.mozRequestAnimationFrame || function( callback ){ window.setTimeout(callback, 1000 / 60); }; })();

 var  VerletPhysics2D = toxi.physics2d.VerletPhysics2D,
      VerletParticle2D = toxi.physics2d.VerletParticle2D,
      AttractionBehavior = toxi.physics2d.behaviors.AttractionBehavior,
      GravityBehavior = toxi.physics2d.behaviors.GravityBehavior,
      PerlinNoise = toxi.math.noise.PerlinNoise,
      Vec2D = toxi.geom.Vec2D,
      Rect = toxi.geom.Rect;
var NUM_PARTICLES = 150;
var physics;
var mouseAttractor;
var mousePos;
var maxDistance;
var zOffset = 0;
var perlin;
var bgcolor = 0xff1f1a20;

function sketchProc(p) {
  function addParticle() {
    var randLoc = Vec2D.randomVector().scale(5).addSelf(p.width / 2, 0);
    var ph = new VerletParticle2D(randLoc);
    perlin = new PerlinNoise();

    physics.addParticle(ph);
    // add a negative attraction force field around the new particle
    physics.addBehavior(new AttractionBehavior(ph, 30, -1.1, 0.02));
  }

  p.setup = function() {
//     p.frameRate(60);
    p.size(document.body.clientWidth, document.body.clientHeight);
    p.background(bgcolor);
    // setup physics with 10% drag
    physics = new VerletPhysics2D();
    physics.setDrag(0.03);
    physics.setWorldBounds(new Rect(0, 0, p.width, p.height));
    // the NEW way to add gravity to the simulation, using behaviors
    physics.addBehavior(new GravityBehavior(new Vec2D(0, 0.18)));
    p.noStroke();
    p.noSmooth();
//     p.angleMode(p.DEGREES);
    maxDistance = p.dist(0, 0, p.width, p.height);
//     p.rafDraw();
  }

  function getAngle(origin, range, x, y, z) {
    origin = origin || 0;
    range = range || 10;

    var n = p.noise(x, y, z);
    var angle = p.map(n, 0, 1, origin-range, origin+range);

    return angle;
  }
//   p.rafDraw = function() {
  p.draw = function() {
    p.background(bgcolor);

    if (physics.particles.length < NUM_PARTICLES) {
      addParticle();
    }
    physics.update();
    for ( i=0;i<physics.particles.length;i++) {
      var ph = physics.particles[i];
      var noise = 0.5* (perlin.noise( ph.x, ph.y ) - 0.5);
      p.fill(0x9abbff00);
      p.ellipse(ph.x, ph.y, 5, 5);
      p.fill(0x8a88ff00);
      p.ellipse(ph.x, ph.y, 15, 15);
      p.fill(0x4588ff00);
      p.ellipse(ph.x, ph.y, 5+(26*noise), 5+(26*noise));
      p.fill(0x1088ff00);
      p.ellipse(ph.x, ph.y, 45+(10*noise), 45+(10*noise));
      p.fill(0x0888ff00);
      p.ellipse(ph.x, ph.y, 65+(24*noise), 65+(24*noise));
    }

//     if (p.mouseButton == p.LEFT) {

    if (p.__mousePressed && p.mouseButton === p.LEFT) {

      for(var i = 0; i <= p.width; i += 50) {
        for(var j = 0; j <= p.height; j += 50) {
          var size = p.dist(p.mouseX, p.mouseY, i, j);
          size = size/maxDistance * 132;
          if (size > 6) {
            p.fill(0x20000000);
            p.ellipse(i, j, size*6, size*6);
            // p.fill(0xb0000000);
            // p.ellipse(i, j, size, size);
          }
        }
      }

      var xOffset = p.mouseX*0.01;
      var yOffset = p.mouseY*0.01;
      p.pushMatrix();
        p.rotate(getAngle(6, 12, xOffset, yOffset, zOffset)/100);

        p.fill(0x80000000);
        p.ellipse(p.mouseX-30, p.mouseY-20, 20, 10);
        p.ellipse(p.mouseX+30, p.mouseY-20, 20, 10);
        p.fill(0x80f0f0f0);
        p.ellipse(p.mouseX-28, p.mouseY-22, 5, 4);
        p.ellipse(p.mouseX+30, p.mouseY-22, 5, 4);

        p.fill(0x03e0ffe0);
        p.ellipse(p.mouseX, p.mouseY, 140, 160);
        zOffset += 0.01;
      p.popMatrix();
    }
//    window.requestAnimFrame(p.rafDraw);
  }

  p.mousePressed = function() {
    mousePos = new Vec2D(p.mouseX, p.mouseY);
    mouseAttractor = new AttractionBehavior(mousePos, 260, 0.59);
    physics.addBehavior(mouseAttractor);
  }

  p.mouseDragged = function() {
    mousePos.set(p.mouseX, p.mouseY);
  }

  p.mouseReleased = function() {
    physics.removeBehavior(mouseAttractor);
  }
}

var canvas = document.getElementById("canvas1");
var processingInstance = new Processing(canvas, sketchProc);
<commit_msg>tweaking blobs<commit_after>// import toxi from 'toxiclibsjs'
// import Processing from 'processing-js'
//
// Inspired by http://haptic-data.com/toxiclibsjs/examples/attraction2d

window.requestAnimFrame = (function(){ return  window.requestAnimationFrame || window.webkitRequestAnimationFrame || window.mozRequestAnimationFrame || function( callback ){ window.setTimeout(callback, 1000 / 60); }; })();

 var  VerletPhysics2D = toxi.physics2d.VerletPhysics2D,
      VerletParticle2D = toxi.physics2d.VerletParticle2D,
      AttractionBehavior = toxi.physics2d.behaviors.AttractionBehavior,
      GravityBehavior = toxi.physics2d.behaviors.GravityBehavior,
      PerlinNoise = toxi.math.noise.PerlinNoise,
      Vec2D = toxi.geom.Vec2D,
      Rect = toxi.geom.Rect;

var NUM_PARTICLES = 50;
var physics;
var mouseAttractor;
var mousePos;
var maxDistance;
var zOffset = 0;
var perlin;
var bgcolor = 0xff1f1a20;

function sketchProc(p) {
  function addParticle() {
    var randLoc = Vec2D.randomVector().scale(5).addSelf(p.width / 2, 0);
    var ph = new VerletParticle2D(randLoc);
    perlin = new PerlinNoise();

    physics.addParticle(ph);
    // add a negative attraction force field around the new particle
    physics.addBehavior(new AttractionBehavior(ph, 30, -1.1, 0.02));
  }

  p.setup = function() {
//     p.frameRate(60);
    p.size(600, 600);
    //p.size(document.body.clientWidth, document.body.clientHeight);
    p.background(bgcolor);
    // setup physics with 10% drag
    physics = new VerletPhysics2D();
    physics.setDrag(0.03);
    physics.setWorldBounds(new Rect(0, 0, p.width, p.height));
    // the NEW way to add gravity to the simulation, using behaviors
    physics.addBehavior(new GravityBehavior(new Vec2D(0, 0.18)));
    p.noStroke();
    p.noSmooth();
//     p.angleMode(p.DEGREES);
    maxDistance = p.dist(0, 0, p.width, p.height);
//     p.rafDraw();
  }

  function getAngle(origin, range, x, y, z) {
    origin = origin || 0;
    range = range || 10;

    var n = p.noise(x, y, z);
    var angle = p.map(n, 0, 1, origin-range, origin+range);

    return angle;
  }
//   p.rafDraw = function() {
  p.draw = function() {
    p.background(bgcolor);

    if (physics.particles.length < NUM_PARTICLES) {
      addParticle();
    }
    physics.update();
    for ( i=0;i<physics.particles.length;i++) {
      var ph = physics.particles[i];
      var noise = 0.5* (perlin.noise( ph.x, ph.y ) - 0.5);
      p.fill(0x9abbff00);
      p.ellipse(ph.x, ph.y, 5, 5);
      p.fill(0x8a88ff00);
      p.ellipse(ph.x, ph.y, 15, 15);
      p.fill(0x6588ff00);
      p.ellipse(ph.x, ph.y, 5+(26*noise), 5+(26*noise));
      p.fill(0x1088ff00);
      p.ellipse(ph.x, ph.y, 45+(10*noise), 45+(10*noise));
      p.fill(0x0888ff00);
      p.ellipse(ph.x, ph.y, 65+(24*noise), 65+(24*noise));
    }

//     if (p.mouseButton == p.LEFT) {

    if (p.__mousePressed && p.mouseButton === p.LEFT) {

      for(var i = 0; i <= p.width; i += 60) {
        for(var j = 0; j <= p.height; j += 60) {
          var size = p.dist(p.mouseX, p.mouseY, i, j);
          size = size/maxDistance * 132;
          if (size > 6) {
            p.fill(0x10000000);
            p.ellipse(i, j, size*5, size*5);
            p.fill(0x30000000);
            p.ellipse(i, j, size*2, size*2);
          }
        }
      }

      var xOffset = p.mouseX*0.01;
      var yOffset = p.mouseY*0.01;
      p.pushMatrix();
        p.rotate(getAngle(6, 12, xOffset, yOffset, zOffset)/100);

        p.fill(0x80000000);
        p.ellipse(p.mouseX-30, p.mouseY-20, 20, 10);
        p.ellipse(p.mouseX+30, p.mouseY-20, 20, 10);
        p.fill(0x80f0f0f0);
        p.ellipse(p.mouseX-28, p.mouseY-22, 5, 4);
        p.ellipse(p.mouseX+30, p.mouseY-22, 5, 4);

        p.fill(0x05e0ffe0);
        p.ellipse(p.mouseX, p.mouseY, 140, 160);
        zOffset += 0.01;
      p.popMatrix();
    }
//    window.requestAnimFrame(p.rafDraw);
  }

  p.mousePressed = function() {
    mousePos = new Vec2D(p.mouseX, p.mouseY);
    mouseAttractor = new AttractionBehavior(mousePos, 260, 0.59);
    physics.addBehavior(mouseAttractor);
  }

  p.mouseDragged = function() {
    mousePos.set(p.mouseX, p.mouseY);
  }

  p.mouseReleased = function() {
    physics.removeBehavior(mouseAttractor);
  }
}

var canvas = document.getElementById("canvas1");
var processingInstance = new Processing(canvas, sketchProc);
<|endoftext|>


<commit_before>function disableSubmitButton() {
    document.getElementById("spinner").style.display = '';
    var submitButton = document.getElementById('submitbtn');
    $('#submitbtn').css('background-color', '#F9BFBB');
    submitButton.disabled = true;
}

function doSubmit() {
    disableSubmitButton();
    var email = $("#email").val();
    jagg.post("/site/blocks/password-reset/initiate/ajax/initiate.jag", {
            action: "initiatePasswordReset",
            email: email
        },
        function (result) {
            $('#userForm').hide();
            $('#helper_text').hide();
            var response = JSON.parse(result);
            if (!response.error) {
                jagg.message({
                    content: 'Password recovery instructions have been sent to ' + email + '. Please check your email.',
                    type: 'success',
                    cbk: function () {
                        window.location.href = "index.jag";
                    }
                });
            } else if (response.message.indexOf("Error while validating captcha") != -1) {
                jagg.message({
                    content: 'Error occurred while validating captcha. Please disable captcha and try again.',
                    type: 'error',
                    cbk: function () {
                        window.location.href = "initiate.jag";
                    }
                });
            } else if (response.message.indexOf("User does not exist") != -1) {
                jagg.message({
                    content: 'No account found with the given email. Please try again with a correct email.',
                    type: 'error',
                    cbk: function () {
                        window.location.href = "initiate.jag";
                    }
                });
            } else {
                jagg.message({
                    content: 'Error occurred while resetting your password. Please try again after few minutes.',
                    type: 'error',
                    cbk: function () {
                        window.location.href = "index.jag";
                    }
                });
            }
        });
}

$(document).ready(function ($) {
    jQuery.validator.setDefaults({
        errorElement: 'span'
    });
    $('#userForm').validate({
        rules: {
            email: {
                required: true
            }
        },
        submitHandler: function (form) {
            doSubmit();
        }
    });
});
<commit_msg>Fixing #2262<commit_after>function disableSubmitButton() {
    document.getElementById("spinner").style.display = '';
    var submitButton = document.getElementById('submitbtn');
    $('#submitbtn').css('background-color', '#F9BFBB');
    submitButton.disabled = true;
}

function doSubmit() {
    disableSubmitButton();
    var email = $("#email").val();
    jagg.post("/site/blocks/password-reset/initiate/ajax/initiate.jag", {
            action: "initiatePasswordReset",
            email: email
        },
        function (result) {
            $('#userForm').hide();
            $('#helper_text').hide();
            var response = JSON.parse(result);
            if (!response.error) {
                jagg.message({
                    content: 'Password recovery instructions have been sent to ' + email + '. Please check your email.',
                    type: 'success',
                    cbk: function () {
                        window.location.href = "index.jag";
                    }
                });
            } else if (response.message.indexOf("Error while validating captcha") != -1) {
                jagg.message({
                    content: 'Error occurred while validating captcha. Please disable captcha and try again.',
                    type: 'error',
                    cbk: function () {
                        window.location.href = "initiate.jag";
                    }
                });
            } else if (response.message.indexOf("User does not exist") != -1) {
                jagg.message({
                    content: 'No account found with the given email. Please try again with a correct email.',
                    type: 'error',
                    cbk: function () {
                        window.location.href = "initiate.jag";
                    }
                });
            } else {
                jagg.message({
                    content: 'Error occurred while resetting your password. Please try again after few minutes.',
                    type: 'error',
                    cbk: function () {
                        window.location.href = "index.jag";
                    }
                });
            }
        });
}

$(document).ready(function ($) {
    jQuery.validator.setDefaults({
        errorElement: 'span'
    });
    $('#userForm').validate({
        rules: {
            email: {
                required: true
            }
        },
        messages: {
            email: "Please enter your username"
        },
        submitHandler: function (form) {
            doSubmit();
        }
    });
});
<|endoftext|>


<commit_before>/* jshint -W117 */
'use strict';

var JSM = require('jingle');
var RTC = require('webrtc-adapter-test');
var GUM = require('getusermedia');
var GSM = require('getscreenmedia');

var jxt = require('jxt').createRegistry();
jxt.use(require('jxt-xmpp-types'));
jxt.use(require('jxt-xmpp'));

var IqStanza = jxt.getDefinition('iq', 'jabber:client');

(function($) {
   Strophe.addConnectionPlugin('jingle', {
      connection: null,
      peer_constraints: {},
      AUTOACCEPT: false,
      localStream: null,
      manager: null,
      RTC: null,
      getUserMedia: null,
      getScreenMedia: null,

      init: function(conn) {
         var self = this;

         self.RTC = RTC;
         self.getUserMedia = GUM;
         self.getScreenMedia = GSM;

         self.connection = conn;

         if ((RTC.webrtcDetectedVersion < 33 && RTC.webrtcDetectedBrowser === 'firefox') || RTC.webrtcDetectedBrowser === 'chrome') {
            self.peer_constraints = {
               mandatory: {
                  'OfferToReceiveAudio': true,
                  'OfferToReceiveVideo': true
               }
            };

            if (RTC.webrtcDetectedBrowser === 'firefox') {
               self.peer_constraints.mandatory.MozDontOfferDataChannel = true;
            }
         } else {
            self.peer_constraints = {
               'offerToReceiveAudio': true,
               'offerToReceiveVideo': true
            };

            if (RTC.webrtcDetectedBrowser === 'firefox') {
               self.peer_constraints.mozDontOfferDataChannel = true;
            }
         }

         self.manager = new JSM({
            peerConnectionConstraints: self.peer_constraints,
            jid: self.connection.jid,
            selfID: self.connection.jid
         });

         var events = {
            'incoming': 'callincoming.jingle',
            'terminated': 'callterminated.jingle',
            'peerStreamAdded': 'remotestreamadded.jingle',
            'peerStreamRemoved': 'remotestreamremoved.jingle',
            'ringing': 'ringing.jingle',
            'log:error': 'error.jingle'
         };

         $.each(events, function(key, val) {
            self.manager.on(key, function() {
               $(document).trigger(val, arguments);
            });
         });

         self.manager.on('incoming', function(session) {
            session.on('change:connectionState', function(session, state) {
               $(document).trigger('iceconnectionstatechange.jingle', [session.sid, session, state]);
            });
         });

         if (this.connection.disco) {
            var i;
            for (i = 0; i < self.manager.capabilities.length; i++) {
               self.connection.disco.addFeature(self.manager.capabilities[i]);
            }
         }
         this.connection.addHandler(this.onJingle.bind(this), 'urn:xmpp:jingle:1', 'iq', 'set', null, null);

         this.manager.on('send', function(data) {

            var iq = new IqStanza(data);

            self.connection.send($.parseXML(iq.toString()).getElementsByTagName('iq')[0]);
         });

         //@TODO add on client unavilable (this.manager.endPeerSessions(peer_jid_full, true))
      },
      onJingle: function(iq) {
         var req = jxt.parse(iq.outerHTML);

         this.manager.process(req.toJSON());

         return true;
      },
      initiate: function(peerjid, stream, offerOptions) { // initiate a new jinglesession to peerjid
         var session = this.manager.createMediaSession(peerjid);

         session.on('change:connectionState', function(session, state) {
            $(document).trigger('iceconnectionstatechange.jingle', [session.sid, session, state]);
         });

         if (stream) {
            this.localStream = stream;
         }

         // configure session
         if (this.localStream) {
            session.addStream(this.localStream);
            session.start(offerOptions);

            return session;
         }

         console.error('No local stream defined');
      },
      terminate: function(jid, reason, silent) { // terminate by sessionid (or all sessions)
         if (typeof jid === 'undefined' || jid === null) {
            this.manager.endAllSessions(reason, silent);
         } else {
            this.manager.endPeerSessions(jid, reason, silent);
         }
      },
      terminateByJid: function(jid) {
         this.manager.endPeerSessions(jid);
      },
      addICEServer: function(server) {
         this.manager.addICEServer(server);
      },
      setICEServers: function(servers) {
         this.manager.iceServers = servers;
      },
      setPeerConstraints: function(constraints) {
         this.manager.config.peerConnectionConstraints = constraints;
      }
   });
}(jQuery));
<commit_msg>use updated lib<commit_after>/* jshint -W117 */
'use strict';

var JSM = require('jingle');
var RTC = require('webrtc-adapter');
var GUM = require('getusermedia');
var GSM = require('getscreenmedia');

var jxt = require('jxt').createRegistry();
jxt.use(require('jxt-xmpp-types'));
jxt.use(require('jxt-xmpp'));

var IqStanza = jxt.getDefinition('iq', 'jabber:client');

(function($) {
   Strophe.addConnectionPlugin('jingle', {
      connection: null,
      peer_constraints: {},
      AUTOACCEPT: false,
      localStream: null,
      manager: null,
      RTC: null,
      getUserMedia: null,
      getScreenMedia: null,

      init: function(conn) {
         var self = this;

         self.RTC = RTC;
         self.getUserMedia = GUM;
         self.getScreenMedia = GSM;

         self.connection = conn;

         var browserDetails = self.RTC.browserDetails;

         if ((browserDetails.version < 33 && browserDetails.browser === 'firefox') || browserDetails.browser === 'chrome') {
            self.peer_constraints = {
               mandatory: {
                  'OfferToReceiveAudio': true,
                  'OfferToReceiveVideo': true
               }
            };

            if (browserDetails.browser === 'firefox') {
               self.peer_constraints.mandatory.MozDontOfferDataChannel = true;
            }
         } else {
            self.peer_constraints = {
               'offerToReceiveAudio': true,
               'offerToReceiveVideo': true
            };

            if (browserDetails.browser === 'firefox') {
               self.peer_constraints.mozDontOfferDataChannel = true;
            }
         }

         self.manager = new JSM({
            peerConnectionConstraints: self.peer_constraints,
            jid: self.connection.jid,
            selfID: self.connection.jid
         });

         var events = {
            'incoming': 'callincoming.jingle',
            'terminated': 'callterminated.jingle',
            'peerStreamAdded': 'remotestreamadded.jingle',
            'peerStreamRemoved': 'remotestreamremoved.jingle',
            'ringing': 'ringing.jingle',
            'log:error': 'error.jingle'
         };

         $.each(events, function(key, val) {
            self.manager.on(key, function() {
               $(document).trigger(val, arguments);
            });
         });

         self.manager.on('incoming', function(session) {
            session.on('change:connectionState', function(session, state) {
               $(document).trigger('iceconnectionstatechange.jingle', [session.sid, session, state]);
            });
         });

         if (this.connection.disco) {
            var i;
            for (i = 0; i < self.manager.capabilities.length; i++) {
               self.connection.disco.addFeature(self.manager.capabilities[i]);
            }
         }
         this.connection.addHandler(this.onJingle.bind(this), 'urn:xmpp:jingle:1', 'iq', 'set', null, null);

         this.manager.on('send', function(data) {

            var iq = new IqStanza(data);

            self.connection.send($.parseXML(iq.toString()).getElementsByTagName('iq')[0]);
         });

         //@TODO add on client unavilable (this.manager.endPeerSessions(peer_jid_full, true))
      },
      onJingle: function(iq) {
         var req = jxt.parse(iq.outerHTML);

         this.manager.process(req.toJSON());

         return true;
      },
      initiate: function(peerjid, stream, offerOptions) { // initiate a new jinglesession to peerjid
         var session = this.manager.createMediaSession(peerjid);

         session.on('change:connectionState', function(session, state) {
            $(document).trigger('iceconnectionstatechange.jingle', [session.sid, session, state]);
         });

         if (stream) {
            this.localStream = stream;
         }

         // configure session
         if (this.localStream) {
            session.addStream(this.localStream);
            session.start(offerOptions);

            return session;
         }

         console.error('No local stream defined');
      },
      terminate: function(jid, reason, silent) { // terminate by sessionid (or all sessions)
         if (typeof jid === 'undefined' || jid === null) {
            this.manager.endAllSessions(reason, silent);
         } else {
            this.manager.endPeerSessions(jid, reason, silent);
         }
      },
      terminateByJid: function(jid) {
         this.manager.endPeerSessions(jid);
      },
      addICEServer: function(server) {
         this.manager.addICEServer(server);
      },
      setICEServers: function(servers) {
         this.manager.iceServers = servers;
      },
      setPeerConstraints: function(constraints) {
         this.manager.config.peerConnectionConstraints = constraints;
      }
   });
}(jQuery));
<|endoftext|>


<commit_before>/**
 * Sails.js Context Loader module
 *
 * this module load context data for use in ACL and controllers
 *
 * @todo change to be a sails.js npm hook in sails 0.11.x
 */

var actionUtil = require('we-helpers').actionUtil;
var _ = require('lodash');
var context = {};

context.sails = {};

/**
 * Sails.js context police
 */
context.sails.police = function sailsContextLoader(req, res, next) {
  // sails-context requires req.options.action
  if ( !req.options || !req.options.action ) {
    return next();
  }

  // set context object in request
  req.context = {};
  // point view context var to req.context
  res.locals.context = req.context;

  if (req.options.model) {
    req.context.Model = actionUtil.parseModel(req);
  }

  switch (req.options.action) {
    case 'find':
      return context.loadContextForRecords(req, res, next);
    case 'findOne':
    case 'update':
    case 'destroy':
      return context.loadContextForRecord(req, res, next);
    default:
      return next();
  }
};

/**
 * Load context for single record requests
 */
context.loadContextForRecord = function(req, res, next) {
  req.context.pk = actionUtil.requirePk(req);

  if( !_.isNumber(req.context.pk) )
    req.context.pk = null;

  req.context.isList = false;
  context.loadContextRecord(req, function(err) {
    if (err) {
      return res.serverError(err);
    }

    return next();
  })
}

/**
 * Load context for list requests
 */
context.loadContextForRecords = function(req, res, next) {
  req.context.where = actionUtil.parseCriteria(req);
  req.context.isList = true;
  context.loadListCount(req, function (err) {
    if (err) {
      sails.log.verbose(err);
      return next();
    }
    return next();
  })
}

/**
 * Preload current record for findOne, update and destroy
 */
context.loadContextRecord = function(req, cb) {
  if (!req.context.Model || !req.context.pk) {
    req._sails.log.verbose('sails-context: Model not found in context.loadContextRecord', req.options);
    req.context.record = null;
    return cb();
  }

  req.context.Model.findOneById(req.context.pk)
  .exec(function(err, record) {
    if (err) {
      req._sails.log.verbose('sails-context: Error on loadContextRecord', err);
      return cb();
    }

    if (_.isEmpty(record) ) {
      req.context.notFound = true;
    }

    req.context.record = record;

    return cb();
  });
}

/**
 * Load count for list requests
 */
context.loadListCount = function loadListCount(req, cb) {
  if (!req.context.Model) {
    req.context.records = null;
    return cb();
  }

  return req.context.Model.count(req.context.where)
  .exec(function afterGetModelCount(err, count) {
    if (err) {
      req._sails.log.verbose('sails-context: Error on loadListCount',err);
      return cb();
    }

    req.context.count = count;

    return cb();
  });
}

module.exports = context;
<commit_msg>Fixed - String integer from REST should be parsed to pure Integer<commit_after>/**
 * Sails.js Context Loader module
 *
 * this module load context data for use in ACL and controllers
 *
 * @todo change to be a sails.js npm hook in sails 0.11.x
 */

var actionUtil = require('we-helpers').actionUtil;
var _ = require('lodash');
var context = {};

context.sails = {};

/**
 * Sails.js context police
 */
context.sails.police = function sailsContextLoader(req, res, next) {
  // sails-context requires req.options.action
  if ( !req.options || !req.options.action ) {
    return next();
  }

  // set context object in request
  req.context = {};
  // point view context var to req.context
  res.locals.context = req.context;

  if (req.options.model) {
    req.context.Model = actionUtil.parseModel(req);
  }

  switch (req.options.action) {
    case 'find':
      return context.loadContextForRecords(req, res, next);
    case 'findOne':
    case 'update':
    case 'destroy':
      return context.loadContextForRecord(req, res, next);
    default:
      return next();
  }
};

/**
 * Load context for single record requests
 */
context.loadContextForRecord = function(req, res, next) {
  req.context.pk = actionUtil.requirePk(req);

  if( !_.isNumber(_.parseInt(req.context.pk)) )
    req.context.pk = null;

  req.context.isList = false;
  context.loadContextRecord(req, function(err) {
    if (err) {
      return res.serverError(err);
    }

    return next();
  })
}

/**
 * Load context for list requests
 */
context.loadContextForRecords = function(req, res, next) {
  req.context.where = actionUtil.parseCriteria(req);
  req.context.isList = true;
  context.loadListCount(req, function (err) {
    if (err) {
      sails.log.verbose(err);
      return next();
    }
    return next();
  })
}

/**
 * Preload current record for findOne, update and destroy
 */
context.loadContextRecord = function(req, cb) {
  if (!req.context.Model || !req.context.pk) {
    req._sails.log.verbose('sails-context: Model not found in context.loadContextRecord', req.options);
    req.context.record = null;
    return cb();
  }

  req.context.Model.findOneById(req.context.pk)
  .exec(function(err, record) {
    if (err) {
      req._sails.log.verbose('sails-context: Error on loadContextRecord', err);
      return cb();
    }

    if (_.isEmpty(record) ) {
      req.context.notFound = true;
    }

    req.context.record = record;

    return cb();
  });
}

/**
 * Load count for list requests
 */
context.loadListCount = function loadListCount(req, cb) {
  if (!req.context.Model) {
    req.context.records = null;
    return cb();
  }

  return req.context.Model.count(req.context.where)
  .exec(function afterGetModelCount(err, count) {
    if (err) {
      req._sails.log.verbose('sails-context: Error on loadListCount',err);
      return cb();
    }

    req.context.count = count;

    return cb();
  });
}

module.exports = context;
<|endoftext|>


<commit_before>
var koratDragonDen = koratDragonDen || {};
koratDragonDen.debtCalculatorSample = koratDragonDen.debtCalculatorSample || {};

koratDragonDen.debtCalculatorSample.model = (function model(){
  'use strict';

  var allDebts = {};
  var subscribers = [];

  // TODO - Add support for this
  // var customPriority = [];

  var allocationMethod = 0;
  var prioritizationMethod = 0;
  var monthlyPayments = 0.0;

  var Debt = function Debt(uid) {
    this.uid = uid;
  };
  Debt.prototype.apr = 0.0;
  Debt.prototype.amountOwed = 0.0;
  Debt.prototype.minimumMonthlyPayment = 0.0;

  var publishDebtUpdates = function publishDebtUpdates(uid, updateType) {

    var debtObject;

    if (updateType === 'delete') {
      debtObject = undefined;
    } else {
      debtObject = allDebts[uid];
    }

    var data = {
      'debtObject' : debtObject,
      'type' : updateType
    };

    for (var i = 0; i < subscribers.length; i++) {
      subscribers[i](data);
    }
  };

  var getDebtsSortedByHighestApr = function getDebtsSortedByHighestApr() {
    // TODO

    var unorderedDebts = [];
    var orderedDebts = [];

    for (var debt in allDebts) {
      if (allDebts.hasOwnProperty(debt)) {
        unorderedDebts.push(allDebts[debt].uid);
      }
    }

    var highestAprDebt = 0;
    while (unorderedDebts.length > 0) {

      highestAprDebt = 0;

      for (var i = 1, l = unorderedDebts.length; i < l; i++) {
        if (allDebts[unorderedDebts[i]].apr > allDebts[unorderedDebts[highestAprDebt]].apr) {
          highestAprDebt = i;
        }
      }

      orderedDebts.push({
        debtObject : allDebts[unorderedDebts[highestAprDebt]],
        remainingOwed : allDebts[unorderedDebts[highestAprDebt]].amountOwed
      });

      unorderedDebts.splice(highestAprDebt, 1);
    }

    return orderedDebts;

  };

  var getDebtsSortedByLowestOwed = function getDebtsSortedByLowestOwed() {
    // TODO

    var unorderedDebts = [];
    var orderedDebts = [];

    for (var debt in allDebts) {
      if (allDebts.hasOwnProperty(debt)) {
        unorderedDebts.push(allDebts[debt].uid);
      }
    }

    var lowestOwedDebt;
    while (unorderedDebts.length > 0) {

      lowestOwedDebt = 0;

      for (var i = 1, l = unorderedDebts.length; i < l; i++) {
        if (allDebts[unorderedDebts[i]].amountOwed < allDebts[unorderedDebts[lowestOwedDebt]].amountOwed) {
          lowestOwedDebt = i;
        }
      }

      orderedDebts.push({
        debtObject : allDebts[unorderedDebts[lowestOwedDebt]],
        remainingOwed : allDebts[unorderedDebts[lowestOwedDebt]].amountOwed
      });

      unorderedDebts.splice(lowestOwedDebt, 1);
    }

    return orderedDebts;
  };

  var getMonthlyMinimumForPayoffTime = function getMonthlyMinimumForPayoffTime(orderedDebtsObject) {

    var currentMonthlyMinimum = 0.0;
    for (var i = 0; i < orderedDebtsObject.length; i++) {
      currentMonthlyMinimum += orderedDebtsObject[i].debtObject.minimumMonthlyPayment;
    }

    return currentMonthlyMinimum;
  };

  // TODO - This whole thing is a brainstormy mess. Fix it.
  var calculatePayoffTime = function calculatePayoffTime() {

    var debt, i;
    var orderedDebts = [];

    // TODO - Change these to enums
    switch (allocationMethod) {

      case 'highestApr':
        orderedDebts = getDebtsSortedByHighestApr();
        break;

      case 'lowestOwed':
        orderedDebts = getDebtsSortedByLowestOwed();
        break;

      case 'custom':
        // TODO - If custom priority, use customPriority
        break;

      default:
        // TODO - How do we want to handle this?
    }

    var months = 0;
    // TODO - Add stop for amounts that are just absurdly long
    while (orderedDebts.length > 0) {
      // Calculate interest first, then remove amount

      months++;

      var orderedDebtsLength = orderedDebts.length;

      // Calculate interest
      for (i = 0; i < orderedDebtsLength; i++) {
        // TODO - Cache monthly interest rate
        orderedDebts[i].remainingOwed *= ( 1.0 + (orderedDebts[i].debtObject.apr / 1200.0) );
      }

      // Determine amount over monthly minimum, if any
      var currentMonthlyMinimum = getMonthlyMinimumForPayoffTime(orderedDebts);
      var amountOverMonthlyMinimum = Math.max(monthlyPayments - currentMonthlyMinimum, 0.0);

      // TODO - Change these to enums
      switch (prioritizationMethod) {

        case 'evenSplit':
          // TODO - Factor in when this is reset mid-calculation because of a debt(s) being paid off
          var evenSplitExtra = amountOverMonthlyMinimum / orderedDebtsLength;

          for (i = 0; i < orderedDebtsLength; i++) {
            // TODO - Check if this subtracts more than owed
            orderedDebts[i].remainingOwed -= (evenSplitExtra + orderedDebts[i].debtObject.minimumMonthlyPayment);
          }
          break;

        case 'priorityFirst':
          var remainingAmountOverMonthlyMinimum = amountOverMonthlyMinimum;
          for (i = 0; i < orderedDebtsLength; i++) {
            // TODO - Check if this subtracts more than owed
            orderedDebts[i].remainingOwed -= (remainingAmountOverMonthlyMinimum + orderedDebts[i].debtObject.minimumMonthlyPayment);
            remainingAmountOverMonthlyMinimum -= remainingAmountOverMonthlyMinimum;
          }
          break;

        case 'proportionalSplit':
          // If proportional split
          var totalAmountRemaining = 0.0;
          // TODO - This is an array
          for (i = 0; i < orderedDebtsLength; i++) {
            totalAmountRemaining += orderedDebts[i].remainingOwed;
          }

          evenSplitExtra = amountOverMonthlyMinimum / orderedDebtsLength;
          // TODO - Factor in when this is reset mid-calculation because of a debt(s) being paid off

          for (i = 0; i < orderedDebtsLength; i++) {
            // TODO - Check if this subtracts more than owed
            orderedDebts[i].remainingOwed -= ((amountOverMonthlyMinimum * (orderedDebts[i].remainingOwed/totalAmountRemaining)) + orderedDebts[i].debtObject.minimumMonthlyPayment);
          }
          break;

        default:
          // TODO - How do we want to handle this?
      }
    }
  };

  function getNewUid() {

    return Math.random().toString(36).substr(2,9);
  }

  return {
    'subscribeToDebtUpdates' : function subscribeToDebtUpdates(callback) {

      // Sanity check. Don't let the same callback subscribe twice.
      for (var i = 0; i < subscribers.length; i++) {
        if (subscribers[i] === callback) {
          return;
        }
      }

      subscribers.push(callback);
    },

    'unsubscribeFromDebtUpdates' :
        function unsubscribeFromDebtUpdates(callback) {

      for (var i = 0; i < subscribers.length; i++) {
        if (subscribers[i] === callback) {
          subscribers.pop(i);
          return;
        }
      }
    },

    'newDebt' : function newDebt(debtData) {

      var uid = getNewUid();
      var debt = new Debt(uid);

      if (debtData !== undefined) {
        if (debtData.apr !== undefined){
          debt.apr = debtData.apr;
        }
        if (debtData.amountOwed !== undefined){
          debt.amountOwed = debtData.amountOwed;
        }
        if (debtData.minimumMonthlyPayment !== undefined){
          debt.minimumMonthlyPayment = debtData.minimumMonthlyPayment;
        }
      }

      allDebts[uid] = new Debt(uid);

      publishDebtUpdates(uid, 'add');
    },

    'updateDebtInfo' : function updateDebtInfo(uid, property, amount) {

      if (allDebts[uid]) {
        allDebts[uid][property] = amount;
      }

      publishDebtUpdates(uid, 'update');
    },

    'deleteDebt' : function deleteDebt(uid, test) {

      if (allDebts[uid]) {
        delete allDebts[uid];
      }

      publishDebtUpdates(uid, 'delete');
    },

    'getTotalAmountOwed' : function getTotalAmountOwed() {

      var totalAmountOwed = 0.0;

      for (var debt in allDebts) {
        if (allDebts.hasOwnProperty(debt)) {
          totalAmountOwed += allDebts[debt].amountOwed;
        }
      }

      return totalAmountOwed;
    },

    'getTotalMinimumMonthlyPayment' : function getTotalMinimumMonthlyPayment() {

      var totalMinimumMonthlyPayment = 0.0;

      for (var debt in allDebts) {
        if (allDebts.hasOwnProperty(debt)) {
          totalMinimumMonthlyPayment += allDebts[debt].minimumMonthlyPayment;
        }
      }

      return totalMinimumMonthlyPayment;
    }
  };

}());

<commit_msg>Using array.sort like I should have been doing all along<commit_after>
var koratDragonDen = koratDragonDen || {};
koratDragonDen.debtCalculatorSample = koratDragonDen.debtCalculatorSample || {};

koratDragonDen.debtCalculatorSample.model = (function model(){
  'use strict';

  var allDebts = {};
  var allocationMethod = 0;
  var prioritizationMethod = 0;
  var monthlyPayments = 0.0;
  var subscribers = [];

  var Debt = function Debt(uid) {
    this.uid = uid;
  };
  Debt.prototype.apr = 0.0;
  Debt.prototype.amountOwed = 0.0;
  Debt.prototype.minimumMonthlyPayment = 0.0;

  var publishDebtUpdates = function publishDebtUpdates(uid, updateType) {

    var debtObject;

    if (updateType === 'delete') {
      debtObject = undefined;
    } else {
      debtObject = allDebts[uid];
    }

    var data = {
      'debtObject' : debtObject,
      'type' : updateType
    };

    for (var i = 0; i < subscribers.length; i++) {
      subscribers[i](data);
    }
  };

  var getDebtsSortedByHighestApr = function getDebtsSortedByHighestApr() {

    var orderedDebts = [];

    for (var debt in allDebts) {
      if (allDebts.hasOwnProperty(debt)) {
        orderedDebts.push({
          debtObject : allDebts[debt],
          remainingOwed : allDebts[debt].amountOwed
        });
      }
    }

    orderedDebts.sort(function(a, b) {
      return a.debtObject.apr - b.debtObject.apr;
    });

    return orderedDebts;
  };

  var getDebtsSortedByLowestOwed = function getDebtsSortedByLowestOwed() {
    // TODO

    var unorderedDebts = [];
    var orderedDebts = [];

    for (var debt in allDebts) {
      if (allDebts.hasOwnProperty(debt)) {
        unorderedDebts.push(allDebts[debt].uid);
      }
    }

    var lowestOwedDebt;
    while (unorderedDebts.length > 0) {

      lowestOwedDebt = 0;

      for (var i = 1, l = unorderedDebts.length; i < l; i++) {
        if (allDebts[unorderedDebts[i]].amountOwed < allDebts[unorderedDebts[lowestOwedDebt]].amountOwed) {
          lowestOwedDebt = i;
        }
      }

      orderedDebts.push({
        debtObject : allDebts[unorderedDebts[lowestOwedDebt]],
        remainingOwed : allDebts[unorderedDebts[lowestOwedDebt]].amountOwed
      });

      unorderedDebts.splice(lowestOwedDebt, 1);
    }

    return orderedDebts;
  };

  var getMonthlyMinimumForPayoffTime = function getMonthlyMinimumForPayoffTime(orderedDebtsObject) {

    var currentMonthlyMinimum = 0.0;
    for (var i = 0; i < orderedDebtsObject.length; i++) {
      currentMonthlyMinimum += orderedDebtsObject[i].debtObject.minimumMonthlyPayment;
    }

    return currentMonthlyMinimum;
  };

  // TODO - This whole thing is a brainstormy mess. Fix it.
  var calculatePayoffTime = function calculatePayoffTime() {

    var debt, i;
    var orderedDebts = [];

    // TODO - Change these to enums
    switch (allocationMethod) {

      case 'highestApr':
        orderedDebts = getDebtsSortedByHighestApr();
        break;

      case 'lowestOwed':
        orderedDebts = getDebtsSortedByLowestOwed();
        break;

      case 'custom':
        // TODO - If custom priority, use customPriority
        break;

      default:
        // TODO - How do we want to handle this?
    }

    var months = 0;
    // TODO - Add stop for amounts that are just absurdly long
    while (orderedDebts.length > 0) {
      // Calculate interest first, then remove amount

      months++;

      var orderedDebtsLength = orderedDebts.length;

      // Calculate interest
      for (i = 0; i < orderedDebtsLength; i++) {
        // TODO - Cache monthly interest rate
        orderedDebts[i].remainingOwed *= ( 1.0 + (orderedDebts[i].debtObject.apr / 1200.0) );
      }

      // Determine amount over monthly minimum, if any
      var currentMonthlyMinimum = getMonthlyMinimumForPayoffTime(orderedDebts);
      var amountOverMonthlyMinimum = Math.max(monthlyPayments - currentMonthlyMinimum, 0.0);

      // TODO - Change these to enums
      switch (prioritizationMethod) {

        case 'evenSplit':
          // TODO - Factor in when this is reset mid-calculation because of a debt(s) being paid off
          var evenSplitExtra = amountOverMonthlyMinimum / orderedDebtsLength;

          for (i = 0; i < orderedDebtsLength; i++) {
            // TODO - Check if this subtracts more than owed
            orderedDebts[i].remainingOwed -= (evenSplitExtra + orderedDebts[i].debtObject.minimumMonthlyPayment);
          }
          break;

        case 'priorityFirst':
          var remainingAmountOverMonthlyMinimum = amountOverMonthlyMinimum;
          for (i = 0; i < orderedDebtsLength; i++) {
            // TODO - Check if this subtracts more than owed
            orderedDebts[i].remainingOwed -= (remainingAmountOverMonthlyMinimum + orderedDebts[i].debtObject.minimumMonthlyPayment);
            remainingAmountOverMonthlyMinimum -= remainingAmountOverMonthlyMinimum;
          }
          break;

        case 'proportionalSplit':
          // If proportional split
          var totalAmountRemaining = 0.0;
          // TODO - This is an array
          for (i = 0; i < orderedDebtsLength; i++) {
            totalAmountRemaining += orderedDebts[i].remainingOwed;
          }

          evenSplitExtra = amountOverMonthlyMinimum / orderedDebtsLength;
          // TODO - Factor in when this is reset mid-calculation because of a debt(s) being paid off

          for (i = 0; i < orderedDebtsLength; i++) {
            // TODO - Check if this subtracts more than owed
            orderedDebts[i].remainingOwed -= ((amountOverMonthlyMinimum * (orderedDebts[i].remainingOwed/totalAmountRemaining)) + orderedDebts[i].debtObject.minimumMonthlyPayment);
          }
          break;

        default:
          // TODO - How do we want to handle this?
      }
    }
  };

  function getNewUid() {

    return Math.random().toString(36).substr(2,9);
  }

  return {
    'subscribeToDebtUpdates' : function subscribeToDebtUpdates(callback) {

      // Sanity check. Don't let the same callback subscribe twice.
      for (var i = 0; i < subscribers.length; i++) {
        if (subscribers[i] === callback) {
          return;
        }
      }

      subscribers.push(callback);
    },

    'unsubscribeFromDebtUpdates' :
        function unsubscribeFromDebtUpdates(callback) {

      for (var i = 0; i < subscribers.length; i++) {
        if (subscribers[i] === callback) {
          subscribers.pop(i);
          return;
        }
      }
    },

    'newDebt' : function newDebt(debtData) {

      var uid = getNewUid();
      var debt = new Debt(uid);

      if (debtData !== undefined) {
        if (debtData.apr !== undefined){
          debt.apr = debtData.apr;
        }
        if (debtData.amountOwed !== undefined){
          debt.amountOwed = debtData.amountOwed;
        }
        if (debtData.minimumMonthlyPayment !== undefined){
          debt.minimumMonthlyPayment = debtData.minimumMonthlyPayment;
        }
      }

      allDebts[uid] = new Debt(uid);

      publishDebtUpdates(uid, 'add');
    },

    'updateDebtInfo' : function updateDebtInfo(uid, property, amount) {

      if (allDebts[uid]) {
        allDebts[uid][property] = amount;
      }

      publishDebtUpdates(uid, 'update');
    },

    'deleteDebt' : function deleteDebt(uid, test) {

      if (allDebts[uid]) {
        delete allDebts[uid];
      }

      publishDebtUpdates(uid, 'delete');
    },

    'getTotalAmountOwed' : function getTotalAmountOwed() {

      var totalAmountOwed = 0.0;

      for (var debt in allDebts) {
        if (allDebts.hasOwnProperty(debt)) {
          totalAmountOwed += allDebts[debt].amountOwed;
        }
      }

      return totalAmountOwed;
    },

    'getTotalMinimumMonthlyPayment' : function getTotalMinimumMonthlyPayment() {

      var totalMinimumMonthlyPayment = 0.0;

      for (var debt in allDebts) {
        if (allDebts.hasOwnProperty(debt)) {
          totalMinimumMonthlyPayment += allDebts[debt].minimumMonthlyPayment;
        }
      }

      return totalMinimumMonthlyPayment;
    }
  };

}());

<|endoftext|>


<commit_before>'use strict';

/**
 *
 * Node Each
 * Description: Asynchronous for each that avoids blocking Node Event Loop using setImmediate.
 *              Event Loop jump can be triggered by iteration number or iteration process time.
 *
 * */

/** Requires */
var Promise = require('bluebird');

/** Global Stats */
var stats = {
    executing: 0
};

/**
 * Async For Each Factory
 * @param {Array} collection - Array for iteration
 * @param {(Function|Promise)} callback - Callback function or promise with collection element parameter
 * @param {Object} [options] - Callback function or promise with collection element parameter
 * @param {Boolean} [options.debug] - Debug iterator
 * @param {String} [options.on] - Pause iterator on iteration or time
 * @param {Number} [options.when] - Iteration or time interval to trigger setImmediate
 * @returns {Promise} - Resolve when loop is finished
 * */
function each(collection, callback, options) {

    /** Collection array Type validation */
    if (!Array.isArray(collection)) {
        throw new TypeError('each first argument must be the collection array for iteration');
    }

    /** Callback function Type validation */
    if (typeof callback !== 'function') {
        throw new TypeError('each second argument must be the iteration callback function');
    }

    /** Options object Type validation */
    if (typeof options !== 'undefined' && typeof options !== 'object') {
        throw new TypeError('each third argument must be the options object');
    }

    /** Time in nanoseconds */
    var ns = 0;

    /** Default options */
    if (!(options && options.when > 0 && (options.on === 'iteration' || options.on === 'time'))) {
        options = {
            debug: (options && options.debug) || false,
            on: 'iteration',
            when: 1
        };
    } else if (options.on === 'time') {
        /** Convert time milliseconds to nanoseconds */
        ns = options.when * 1000000;
    }

    /** Iteration array, iteration start number, promise resolve reference and process times */
    var iterationArray = collection.slice(0),
        iteration = 0,
        loops = 1,
        promiseResolve,
        start = process.hrtime(),
        time = start;

    /**
     * Recursive Iterator function
     * */
    function iterator() {
        /** Take iteration element and remove it from iteration array */
        var el = iterationArray.splice(0, 1)[0];

        /** Resolve callback promise */
        Promise.resolve(callback(el, iteration)).then(function next() {

            /** Iteration array not empty, we still need to iterate */
            if (iterationArray.length > 0) {

                /** Increment iteration */
                ++iteration;

                /** Options pause on iteration */
                if (options.on === 'iteration') {

                    /** Remainder of iteration is 0 call setImmediate */
                    if (iteration % options.when === 0) {
                        /** Debug is true, increment loops */
                        if (options.debug === true) {
                            ++loops;
                        }
                        setImmediate(iterator);
                    } else {
                        /** Run next iteration */
                        iterator();
                    }

                } else {

                    /** Options pause on time */
                    /** Process time difference */
                    var timeDif = process.hrtime(time);

                    /** Time difference is greater than or equal to when call setImmediate */
                    if ((timeDif[0] * 1e9) + timeDif[1] >= ns) {
                        /** Debug is true, increment loops */
                        if (options.debug === true) {
                            ++loops;
                        }
                        /** Reset process time */
                        time = process.hrtime();
                        setImmediate(iterator);
                    } else {
                        /** Run next iteration */
                        iterator();
                    }

                }
            } else {
                /** Iteration array is empty, resolve loop promise */
                /** Resolve with debug object */
                if (options.debug === true) {
                    /** Increment last iteration */
                    if (collection.length) {
                        ++iteration;
                    }
                    var end = process.hrtime(start),
                        duration = (end[0] * 1000) + (end[1] / 1000000),
                        debugObj = {
                            average: collection.length ? duration / iteration : duration,
                            duration: duration,
                            iterations: iteration,
                            loops: loops,
                            on: options.on,
                            when: options.when
                        };
                    promiseResolve(debugObj);
                } else {
                    /** Resolve */
                    promiseResolve();
                }

                /** Decrement loops executing */
                --stats.executing;
            }

        });
    }

    /**
     * Iterator Promise that resolves when all iterations are finished
     * @param {Function} resolve - Promise resolve method
     * */
    function iteratorPromise(resolve) {

        /** Increment loops executing */
        ++stats.executing;

        /** Promise resolve method reference */
        promiseResolve = resolve;

        /** Start recursive iteration */
        iterator();

    }

    /** Return Iterator Promise */
    return new Promise(iteratorPromise);
}

/** Export each function and stats object */
module.exports = {
    each: each,
    stats: stats
};<commit_msg>refactor(debug): Change loops property to cycles<commit_after>'use strict';

/**
 *
 * Node Each
 * Description: Asynchronous for each that avoids blocking Node Event Loop using setImmediate.
 *              Event Loop jump can be triggered by iteration number or iteration process time.
 *
 * */

/** Requires */
var Promise = require('bluebird');

/** Global Stats */
var stats = {
    executing: 0
};

/**
 * Async For Each Factory
 * @param {Array} collection - Array for iteration
 * @param {(Function|Promise)} callback - Callback function or promise with collection element parameter
 * @param {Object} [options] - Callback function or promise with collection element parameter
 * @param {Boolean} [options.debug] - Debug iterator
 * @param {String} [options.on] - Pause iterator on iteration or time
 * @param {Number} [options.when] - Iteration or time interval to trigger setImmediate
 * @returns {Promise} - Resolve when loop is finished
 * */
function each(collection, callback, options) {

    /** Collection array Type validation */
    if (!Array.isArray(collection)) {
        throw new TypeError('each first argument must be the collection array for iteration');
    }

    /** Callback function Type validation */
    if (typeof callback !== 'function') {
        throw new TypeError('each second argument must be the iteration callback function');
    }

    /** Options object Type validation */
    if (typeof options !== 'undefined' && typeof options !== 'object') {
        throw new TypeError('each third argument must be the options object');
    }

    /** Time in nanoseconds */
    var ns = 0;

    /** Default options */
    if (!(options && options.when > 0 && (options.on === 'iteration' || options.on === 'time'))) {
        options = {
            debug: (options && options.debug) || false,
            on: 'iteration',
            when: 1
        };
    } else if (options.on === 'time') {
        /** Convert time milliseconds to nanoseconds */
        ns = options.when * 1000000;
    }

    /** Iteration array, iteration start number, promise resolve reference and process times */
    var cycles = 1,
        iterationArray = collection.slice(0),
        iteration = 0,
        promiseResolve,
        start = process.hrtime(),
        time = start;

    /**
     * Recursive Iterator function
     * */
    function iterator() {
        /** Take iteration element and remove it from iteration array */
        var el = iterationArray.splice(0, 1)[0];

        /** Resolve callback promise */
        Promise.resolve(callback(el, iteration)).then(function next() {

            /** Iteration array not empty, we still need to iterate */
            if (iterationArray.length > 0) {

                /** Increment iteration */
                ++iteration;

                /** Options pause on iteration */
                if (options.on === 'iteration') {

                    /** Remainder of iteration is 0 call setImmediate */
                    if (iteration % options.when === 0) {
                        /** Debug is true, increment cycles */
                        if (options.debug === true) {
                            ++cycles;
                        }
                        setImmediate(iterator);
                    } else {
                        /** Run next iteration */
                        iterator();
                    }

                } else {

                    /** Options pause on time */
                    /** Process time difference */
                    var timeDif = process.hrtime(time);

                    /** Time difference is greater than or equal to when call setImmediate */
                    if ((timeDif[0] * 1e9) + timeDif[1] >= ns) {
                        /** Debug is true, increment cycles */
                        if (options.debug === true) {
                            ++cycles;
                        }
                        /** Reset process time */
                        time = process.hrtime();
                        setImmediate(iterator);
                    } else {
                        /** Run next iteration */
                        iterator();
                    }

                }
            } else {
                /** Iteration array is empty, resolve loop promise */
                /** Resolve with debug object */
                if (options.debug === true) {
                    /** Increment last iteration */
                    if (collection.length) {
                        ++iteration;
                    }
                    var end = process.hrtime(start),
                        duration = (end[0] * 1000) + (end[1] / 1000000),
                        debugObj = {
                            average: collection.length ? duration / iteration : duration,
                            cycles: cycles,
                            duration: duration,
                            iterations: iteration,
                            on: options.on,
                            when: options.when
                        };
                    promiseResolve(debugObj);
                } else {
                    /** Resolve */
                    promiseResolve();
                }

                /** Decrement loops executing */
                --stats.executing;
            }

        });
    }

    /**
     * Iterator Promise that resolves when all iterations are finished
     * @param {Function} resolve - Promise resolve method
     * */
    function iteratorPromise(resolve) {

        /** Increment loops executing */
        ++stats.executing;

        /** Promise resolve method reference */
        promiseResolve = resolve;

        /** Start recursive iteration */
        iterator();

    }

    /** Return Iterator Promise */
    return new Promise(iteratorPromise);
}

/** Export each function and stats object */
module.exports = {
    each: each,
    stats: stats
};<|endoftext|>


<commit_before>
var request = require('request'),
  entities = require('./lib/entities'),
  fs = require('fs'),
  exec = require('child_process').exec;

function printHelp(replyTo){
  irc.privmsg(replyTo, '~power of NURDspace');
}

var tr = require('tor-request');

listen(regexFactory.startsWith(["power"]), function (match, data, replyTo, from) {

  var url = 'https://public.nurd.space/~zarya/power/api.php';
  var requestObject = {
    uri: url,
    strictSSL: false,
    timeout: 2000,
    encoding: null,
    headers: {
      'User-Agent': 'Mozilla/5.0 (Windows NT 6.2; WOW64) AppleWebKit/537.31 (KHTML, like Gecko) Chrome/26.0.1410.43 Safari/537.31 Nodebot'
    }
  };

  request(requestObject, function(error, response, body) {
    if(response.statusCode == 200) {
      var power = JSON.parse(body);
      if (power && power.watt && power.kwh){
        var price = power.kwh * 0.22
        irc.privmsg(replyTo, "[ " + power.watt + " W ~ " + parseInt(power.kwh) + " kWh ~ " + price.toFixed(2) + " euro ]" );
      } else if (power) {
        irc.privmsg(replyTo,JSON.stringify(power));
      } else {
        irc.privmsg(replyTo,"meh.");
      }
    }
  });

});
<commit_msg>clearer power output<commit_after>
var request = require('request'),
  entities = require('./lib/entities'),
  fs = require('fs'),
  exec = require('child_process').exec;

function printHelp(replyTo){
  irc.privmsg(replyTo, '~power of NURDspace');
}

var tr = require('tor-request');

listen(regexFactory.startsWith(["power"]), function (match, data, replyTo, from) {

  var url = 'https://public.nurd.space/~zarya/power/api.php';
  var requestObject = {
    uri: url,
    strictSSL: false,
    timeout: 2000,
    encoding: null,
    headers: {
      'User-Agent': 'Mozilla/5.0 (Windows NT 6.2; WOW64) AppleWebKit/537.31 (KHTML, like Gecko) Chrome/26.0.1410.43 Safari/537.31 Nodebot'
    }
  };

  request(requestObject, function(error, response, body) {
    if(response.statusCode == 200) {
      var power = JSON.parse(body);
      if (power && power.watt && power.kwh){
        var price = power.kwh * 0.22
        irc.privmsg(replyTo, "[ " + power.watt + " W ][ Total: " + parseInt(power.kwh) + " kWh ~ " + price.toFixed(2) + " euro ]" );
      } else if (power) {
        irc.privmsg(replyTo,JSON.stringify(power));
      } else {
        irc.privmsg(replyTo,"meh.");
      }
    }
  });

});
<|endoftext|>


<commit_before>var _ = require('lodash');
var utils = require('./utils');
var traverse = require('traverse');

var defaults = {
  baseFolder: process.cwd()
};

var loaders = {
  'file': require('./loaders/file')
};

var cache = {};

function getRefSchema(refVal, refType, parent, options, state) {
  if (refType && loaders[refType]) {
    var newVal;

    var filePath = utils.getRefFilePath(refVal);

    var loaderValue;
    if (cache[filePath]) {
      loaderValue = cache[filePath];
    }

    if (!loaderValue) {
      loaderValue = loaders[refType](refVal, options);
      if (loaderValue) {
        loaderValue = derefSchema(loaderValue, options, state);
      }
    }

    if (loaderValue) {
      if (filePath && !cache[filePath]) {
        cache[filePath] = loaderValue;
      }

      if (refVal.indexOf('#') >= 0) {
        var refPaths = refVal.split('#');
        var refPath = refPaths[1];
        var refNewVal = utils.getRefPathValue(loaderValue, refPath);
        if (refNewVal) {
          newVal = refNewVal;
        }
      }
      else {
        newVal = loaderValue;
      }
    }

    return newVal;
  }
  else if (refType === 'local') {
    return utils.getRefPathValue(parent, refVal);
  }
}

var jsonSchemaKeywords = ['member', 'property', 'schema', 'targetschema', 'type', 'element', 'properties',
  'definitions'];

function buildNodeHistory(node, history) {
  if (!history) {
    history = [];
  }

  if (node && node.key && jsonSchemaKeywords.indexOf(node.key) === -1) {
    history.push(node.key);
  }

  if (!node || !node.parent) {
    return history;
  }

  return buildNodeHistory(node.parent, history);
}

function derefSchema(schema, options, state) {

  if (!state) {
    state = {
      circular: false,
      history: [],
      circularRefs: []
    };
  }

  if (state.circular) {
    return;
  }

  return traverse(schema).map(function (node) {
    if (node && node['$ref'] && typeof node['$ref'] === 'string') {
      var refType = utils.getRefType(node);
      var refVal = utils.getRefValue(node);

      var nodeHistory = buildNodeHistory(this.parent);

      var refPaths = refVal.split('/');
      var finalRef = refPaths[refPaths.length - 1];

      if ((refType === 'local' && nodeHistory.indexOf(finalRef) >= 0) || (state.history.indexOf(refVal) >= 0)) {
        state.circular = true;
        state.circularRefs.push(refVal);
        this.update(node, true);
        return;
      }

      state.history.push(refVal);

      var newValue = getRefSchema(refVal, refType, schema, options, state);
      if (newValue) {
        this.update(newValue);
        if (state.circularRefs.indexOf(refVal) === -1) {
          state.history.pop();
        }
      }
    }
  });
}

/**
 * Derefs `$ref`'s in json schema to actual resolved values.
 * Supports local, file and web refs.
 * @param schema The json schema
 * @param options
 *          baseFolder - the base folder to get relative path files from. Default is `process.cwd()`
 * @returns {*}
 */
function deref(schema, options) {
  if (!options) {
    options = {};
  }

  options = _.defaults(options, defaults);

  cache = {};

  var state = {
    circular: false,
    history: [],
    circularRefs: []
  };

  var firstPass = derefSchema(schema, options, state);

  if (!firstPass || state.circular) {
    return new Error('circular references found: ' + state.circularRefs.toString());
  }

  return derefSchema(firstPass, options);
}

deref.prototype.getRefPathValue = utils.getRefPathValue;

module.exports = deref;<commit_msg>comments<commit_after>var _ = require('lodash');
var utils = require('./utils');
var traverse = require('traverse');

var defaults = {
  baseFolder: process.cwd()
};

var jsonSchemaKeywords = ['member', 'property', 'schema', 'targetschema', 'type', 'element', 'properties',
  'definitions'];

var loaders = {
  'file': require('./loaders/file')
};

var cache = {};

/**
 * Returns the reference schema that refVal points to.
 * If the ref val points to a ref within a file, the file is loaded and fully derefed, before we get the
 * pointing property. Derefed files are cahced.
 *
 * @param refVal
 * @param refType
 * @param parent
 * @param options
 * @param state
 * @returns {*}
 */
function getRefSchema(refVal, refType, parent, options, state) {
  if (refType && loaders[refType]) {
    var newVal;

    var filePath = utils.getRefFilePath(refVal);

    var loaderValue;
    if (cache[filePath]) {
      loaderValue = cache[filePath];
    }

    if (!loaderValue) {
      loaderValue = loaders[refType](refVal, options);
      if (loaderValue) {
        loaderValue = derefSchema(loaderValue, options, state);
      }
    }

    if (loaderValue) {
      if (filePath && !cache[filePath]) {
        cache[filePath] = loaderValue;
      }

      if (refVal.indexOf('#') >= 0) {
        var refPaths = refVal.split('#');
        var refPath = refPaths[1];
        var refNewVal = utils.getRefPathValue(loaderValue, refPath);
        if (refNewVal) {
          newVal = refNewVal;
        }
      }
      else {
        newVal = loaderValue;
      }
    }

    return newVal;
  }
  else if (refType === 'local') {
    return utils.getRefPathValue(parent, refVal);
  }
}

/**
 * Builds parental history of a node within an object. To be used in traversal.
 * @param node
 * @param history
 * @returns {*}
 */
function buildNodeHistory(node, history) {
  if (!history) {
    history = [];
  }

  if (node && node.key && jsonSchemaKeywords.indexOf(node.key.toLowerCase()) === -1) {
    history.push(node.key);
  }

  if (!node || !node.parent) {
    return history;
  }

  return buildNodeHistory(node.parent, history);
}

/**
 * Derefs schema
 * @param schema
 * @param options
 * @param state
 */
function derefSchema(schema, options, state) {

  if (!state) {
    state = {
      circular: false,
      history: [],
      circularRefs: []
    };
  }

  if (state.circular) {
    return;
  }

  return traverse(schema).map(function (node) {
    if (node && node['$ref'] && typeof node['$ref'] === 'string') {
      var refType = utils.getRefType(node);
      var refVal = utils.getRefValue(node);

      var nodeHistory = buildNodeHistory(this.parent);

      var refPaths = refVal.split('/');
      var finalRef = refPaths[refPaths.length - 1];

      if ((refType === 'local' && nodeHistory.indexOf(finalRef) >= 0) || (state.history.indexOf(refVal) >= 0)) {
        state.circular = true;
        state.circularRefs.push(refVal);
        this.update(node, true);
        return;
      }

      state.history.push(refVal);

      var newValue = getRefSchema(refVal, refType, schema, options, state);
      if (newValue) {
        this.update(newValue);
        if (state.circularRefs.indexOf(refVal) === -1) {
          state.history.pop();
        }
      }
    }
  });
}

/**
 * Derefs `$ref`'s in json schema to actual resolved values.
 * Supports local, file and web refs.
 * @param schema The json schema
 * @param options
 *          baseFolder - the base folder to get relative path files from. Default is `process.cwd()`
 * @returns {*}
 */
function deref(schema, options) {
  if (!options) {
    options = {};
  }

  options = _.defaults(options, defaults);

  cache = {};

  var state = {
    circular: false,
    history: [],
    circularRefs: []
  };

  var firstPass = derefSchema(schema, options, state);

  if (!firstPass || state.circular) {
    return new Error('circular references found: ' + state.circularRefs.toString());
  }

  // we need to do a 2nd pass
  return derefSchema(firstPass, options);
}

deref.prototype.getRefPathValue = utils.getRefPathValue;

module.exports = deref;<|endoftext|>


<commit_before>var utils = require('./utils')

exports.State      = require('./state')

exports.Model             = require('./model')
exports.GroupedCollection = require('./collection').GroupedCollection
exports.Collection        = require('./collection').Collection
exports.Observable        = require('./observable')
exports.observableArray   = exports.Observable.Array

exports.Template   = require('./template')
exports.Fragment   = require('./fragment')

exports.Routes = {}

var isServer  = exports.isServer  = utils.isServer
  , isClient = exports.isClient = utils.isClient
exports.UUID = utils.UUID

if (isClient) {
  var page = require('page')
    , qs   = require('qs')

  window.swac = {
    debug: false,
    State: exports.State,
    navigate: function(path) {
      var ctx = new page.Context(path, null)
      page.dispatch(ctx)
      if (!ctx.unhandled)
        ctx.pushState()
    }
  }

  function sameOrigin(href) {
    var origin = location.protocol + "//" + location.hostname + ":" + location.port
    return href.indexOf('http') == -1 || href.indexOf(origin) === 0
  }

  $(function() {
    $('body').on('click', 'a', function(e) {
      if (Boolean($(this).data('extern'))) return
      if (this.protocol === 'javascript:') return
      if (this.hash || !$(this).attr('href') || $(this).attr('href') == '#') return
      if (!sameOrigin($(this).attr('href'))) return
      e.preventDefault()
      // if (this.pathname !== location.pathname)
      var path = this.pathname + this.search
      if ($(this).data('confirm') && !confirm($(this).data('confirm'))) return
      var ctx = new page.Context(path, {
        trigger: typeof $(this).data('trigger') === 'undefined' ? true : Boolean($(this).data('trigger'))
      })
      page.dispatch(ctx)
      if (!ctx.unhandled && !Boolean($(this).data('silent')))
        ctx.pushState()
    })
    page({ click: false, dispatch: true })
    $('body').on('submit', 'form', function(e) {
      if ($(this).data('side') == 'server') return
      var method = $(this).attr('method').toLowerCase()
        , ctx, path = this.action
      if (path.indexOf(window.location.origin) === 0)
        path = path.substr(window.location.origin.length)
      if (method === 'post') {
        var _method = $(this).find('input[name=_method]')
        if (_method.length) method = _method.val()
        path = '/_' + method + path
        ctx = new page.Context(path, { body: qs.parse($(this).serialize()) })
        page.dispatch(ctx)
      } else {
        if (path.indexOf('?') > -1) path += '&'
        else path += '?'
        path += $(this).serialize()
        ctx = new page.Context(path)
        page.dispatch(ctx)
        if (!ctx.unhandled)
          ctx.pushState()
      }
      if (!ctx.unhandled)
        e.preventDefault()
    })
  })
}

if (utils.isClient) {
  var routing    = require('./routing')
  exports.init   = routing.init
  exports.get    = routing.get
  exports.post   = routing.post
  exports.put    = routing.put
  exports.delete = routing.delete
}<commit_msg>Add Possibility to Add Functionality to the State Transfer<commit_after>var utils   = require('./utils')
  , implode = require('./implode')

exports.State = require('./state')

exports.Model             = require('./model')
exports.GroupedCollection = require('./collection').GroupedCollection
exports.Collection        = require('./collection').Collection
exports.Observable        = require('./observable')
exports.observableArray   = exports.Observable.Array

exports.Template   = require('./template')
exports.Fragment   = require('./fragment')

exports.Routes = {}

var isServer  = exports.isServer  = utils.isServer
  , isClient = exports.isClient = utils.isClient
exports.UUID = utils.UUID

exports.register = function(name, helper) {
  implode.register(name, helper, [])
}

if (isClient) {
  var page = require('page')
    , qs   = require('qs')

  window.swac = {
    debug: false,
    State: exports.State,
    navigate: function(path) {
      var ctx = new page.Context(path, null)
      page.dispatch(ctx)
      if (!ctx.unhandled)
        ctx.pushState()
    }
  }

  function sameOrigin(href) {
    var origin = location.protocol + "//" + location.hostname + ":" + location.port
    return href.indexOf('http') == -1 || href.indexOf(origin) === 0
  }

  $(function() {
    $('body').on('click', 'a', function(e) {
      if (Boolean($(this).data('extern'))) return
      if (this.protocol === 'javascript:') return
      if (this.hash || !$(this).attr('href') || $(this).attr('href') == '#') return
      if (!sameOrigin($(this).attr('href'))) return
      e.preventDefault()
      // if (this.pathname !== location.pathname)
      var path = this.pathname + this.search
      if ($(this).data('confirm') && !confirm($(this).data('confirm'))) return
      var ctx = new page.Context(path, {
        trigger: typeof $(this).data('trigger') === 'undefined' ? true : Boolean($(this).data('trigger'))
      })
      page.dispatch(ctx)
      if (!ctx.unhandled && !Boolean($(this).data('silent')))
        ctx.pushState()
    })
    page({ click: false, dispatch: true })
    $('body').on('submit', 'form', function(e) {
      if ($(this).data('side') == 'server') return
      var method = $(this).attr('method').toLowerCase()
        , ctx, path = this.action
      if (path.indexOf(window.location.origin) === 0)
        path = path.substr(window.location.origin.length)
      if (method === 'post') {
        var _method = $(this).find('input[name=_method]')
        if (_method.length) method = _method.val()
        path = '/_' + method + path
        ctx = new page.Context(path, { body: qs.parse($(this).serialize()) })
        page.dispatch(ctx)
      } else {
        if (path.indexOf('?') > -1) path += '&'
        else path += '?'
        path += $(this).serialize()
        ctx = new page.Context(path)
        page.dispatch(ctx)
        if (!ctx.unhandled)
          ctx.pushState()
      }
      if (!ctx.unhandled)
        e.preventDefault()
    })
  })

  var routing    = require('./routing')
  exports.init   = routing.init
  exports.get    = routing.get
  exports.post   = routing.post
  exports.put    = routing.put
  exports.delete = routing.delete
}<|endoftext|>