<commit_before>/**
 * User.js
 *
 * @description :: TODO: You might write a short summary of how this model works and what it represents here.
 * @docs        :: http://sailsjs.org/documentation/concepts/models-and-orm/models
 */

module.exports = {

    attributes: {

        login : {
            type: 'string',
            unique: true,
        },

        ip : {
            type: 'string',
            unique: true,
            ip: true,
        },

        name : {
            type: 'string',
            required: true,
        },

        phone : {
            type: 'string',
        },

        team: {
            model: 'team',
            required: true,
        },

        accessToken : {
            type: 'string',
        },
        renewToken : {
            type: 'string',
        },
    },

    /**
     * Check validness of a login using the provided ip
     *
     * @param  {String}   ip
     * @param  {Function} cb
     */
    attemptIpAuth: function (ip, cb) {
        User.findOne({
            ip: ip,
        })
        .exec(cb);
    },

    /**
     * Check validness of an auth using the provided login
     *
     * @param  {String}   login
     * @param  {Function} cb
     */
    attemptLoginAuth: function (login, cb) {
        User.findOne({
            login: login,
        })
        // If the database has no user, we create the first admin user with this login
        .exec((error, result) => {
            if(!error && !result) {
                User.count((error, result) => {
                    if(result === 0) {
                        sails.log.warn('The database contain no users. We will create an admin user with the login: '+login);
                        Team.create({
                            name: 'Admins',
                            role: 'admin',
                            group: 'orga',
                        }).exec((error, team) => {
                            if(error) {
                                cb(error);
                            }
                            else {
                                User.create({
                                    login: login,
                                    team: team.id,
                                }).exec(cb);
                            }
                        });
                    }
                    else {
                        cb(error, result);
                    }
                })
            }
            else {
                cb(error, result);
            }
        });
    },
};
<commit_msg>Fix auto admin creation on db empty<commit_after>/**
 * User.js
 *
 * @description :: TODO: You might write a short summary of how this model works and what it represents here.
 * @docs        :: http://sailsjs.org/documentation/concepts/models-and-orm/models
 */

module.exports = {

    attributes: {

        login : {
            type: 'string',
            unique: true,
        },

        ip : {
            type: 'string',
            unique: true,
            ip: true,
        },

        name : {
            type: 'string',
            required: true,
        },

        phone : {
            type: 'string',
        },

        team: {
            model: 'team',
            required: true,
        },

        accessToken : {
            type: 'string',
        },
        renewToken : {
            type: 'string',
        },
    },

    /**
     * Check validness of a login using the provided ip
     *
     * @param  {String}   ip
     * @param  {Function} cb
     */
    attemptIpAuth: function (ip, cb) {
        User.findOne({
            ip: ip,
        })
        .exec(cb);
    },

    /**
     * Check validness of an auth using the provided login
     *
     * @param  {String}   login
     * @param  {Function} cb
     */
    attemptLoginAuth: function (login, cb) {
        User.findOne({
            login: login,
        })
        // If the database has no user, we create the first admin user with this login
        .exec((error, result) => {
            if(!error && !result) {
                User.count((error, result) => {
                    if(result === 0) {
                        sails.log.warn('The database contain no users. We will create an admin user with the login: '+login);
                        Team.create({
                            name: 'Admins',
                            role: 'admin',
                            group: 'orga',
                        }).exec((error, team) => {
                            if(error) {
                                cb(error);
                            }
                            else {
                                User.create({
                                    login: login,
                                    name: 'admin',
                                    team: team.id,
                                }).exec(cb);
                            }
                        });
                    }
                    else {
                        cb(error, result);
                    }
                })
            }
            else {
                cb(error, result);
            }
        });
    },
};
<|endoftext|>


<commit_before><commit_msg>fixes topic endpoint to include viz execution<commit_after><|endoftext|>


<commit_before>//orangeStand by Michael Leonffu
var MongoClient = require('mongodb').MongoClient
var configDB = require('./../config/database.js')
ObjectId = require('mongodb').ObjectID

//This handles putting the data into the database to present onto the website; all this really does is a mongodb insert or update.

var orangeStand = function(orchard, pickedRankingOranges, pickedMatchHistoryOranges, calculatedJuice, orangeStandMenu){
	// rankingsJuice requires all the information that goes into the rankings tab in the UI:
	// 	Team number, team name (not from any spesififc picker or peeler)
	//	This is ranking information form the ranking picker and peeler ->
	// 		Rank,
	// 		record T-W-L,
	// 		Qp, Rp,
	//	This would be from the averages picker and peeler ->
	// 		OPR, CCWM, OPR, OPR, OPR
	// Both combine into making the rankings tab; rankings Juice.

	//rankings should be in the form of:
	// ranking:[
	// 	{
	// 		rank: 123,
	// 		teamNumber: 123,
	// 		teamName: 123,
	// 		record:{
	// 			wins: 123,
	// 			losses: 123,
	// 			ties: 123
	// 		},
	// 		qualifyingPoints: 123,
	// 		rankingPoints: 123,
	// 		averageScore: .123,
	// 		averageMarginalScore: .123,
	// 		average:{
	// 			auto: .123,
	// 			driver: .123,
	// 			end: .123
	// 		}
	// 	}
	// ]

	// form of average picker peeler is in
	// {
	// 	juice: {
	// 		'123' : .123
	// 	},
	// 	error: .123
	// }

	// form of rankings picker peeler is in
	// {
	// 	rankings: [
	// 		{
	// 			teamName: 'abc',
	// 			teamNumber: 123,
	// 			record: {
	// 				wins: 123,
	// 				lossess: 123,
	// 				ties: 123
	// 			},
	// 			qualifyingPoints: 123,
	// 			rankingPoints: 123,
	// 			rank: 123
	// 		}
	// 	]
	// }

	// console.log('orchard', orchard)
	// console.log('pickedRankingOranges', pickedRankingOranges)
	// console.log('calculatedJuice', calculatedJuice)
	// console.log('pickedMatchHistoryOranges',pickedMatchHistoryOranges[0].gameData)

	//Rankings:
	var ranking = []

	for (var i = 0; i < pickedRankingOranges.length; i++) {
		//pickedRankingOranges[i]
		ranking[i] = {
			rank: i+1,
			teamNumber: pickedRankingOranges[i]._id,
			teamName: 'Anna Li', //Will get the thing latter
			record: {
				wins: pickedRankingOranges[i].wins,
				losses: pickedRankingOranges[i].losses,
				ties: pickedRankingOranges[i].ties
			},
			qualifyingPoints: pickedRankingOranges[i].qualifyingPoints,
			rankingPoints: pickedRankingOranges[i].rankingPoints,
			averageScore: calculatedJuice.calculatedOffensiveJuice.juice[String(pickedRankingOranges[i]._id)],
			averageMarginalScore: calculatedJuice.calculatedMarginalJuice.juice[String(pickedRankingOranges[i]._id)],
			average:{
				auto: 01,
				driver: 22,
				end: 99
			}
		}
	}

	//Match history:
	var matchHistory = []

	var rankingsJson = {}

	for (var i = 0; i < ranking.length; i++) {
		//ranking[i]
		rankingsJson[String(ranking[i].teamNumber)] = ranking[i]
	}

	for (var i = 0; i < pickedMatchHistoryOranges.length; i++) {
		//pickedMatchHistoryOranges[i]
		matchHistory[i] = {
			matchNumber: pickedMatchHistoryOranges[i]._id.matchNumber,
			alliance: pickedMatchHistoryOranges[i]._id.alliance,
			team1: {
				teamNumber: pickedMatchHistoryOranges[i].teams.team1,
				teamName: 'Anna Li',
				rank: rankingsJson[String(pickedMatchHistoryOranges[i].teams.team1)].rank
			},
			team2: {
				teamNumber: pickedMatchHistoryOranges[i].teams.team2,
				teamName: 'Anna Li',
				rank: rankingsJson[String(pickedMatchHistoryOranges[i].teams.team2)].rank
			},
			result: {
				total: pickedMatchHistoryOranges[i].matchData.resultInformation.score.total[String(pickedMatchHistoryOranges[i]._id.alliance)],
				penalty: pickedMatchHistoryOranges[i].matchData.resultInformation.score.penalty[String(pickedMatchHistoryOranges[i]._id.alliance)],
				final: pickedMatchHistoryOranges[i].matchData.resultInformation.score.final[String(pickedMatchHistoryOranges[i]._id.alliance)]
			},
			prediction: 'red',
			winner: pickedMatchHistoryOranges[i].matchData.resultInformation.winner,
			gameInformation: pickedMatchHistoryOranges[i].gameData.gameInformation
		}
	}

	MongoClient.connect(configDB.url, function(err,db){
		if(err){
			console.log(err)
			return
		}
		db.collection('eventOut').save(
			{
				_id: orchard,	//orcahrd is toaeventkey
				lastUpdated: new Date(), //Time of insert/update
				ranking: ranking,
				matchHistory: matchHistory
			},
			function(err, result){
				if(err){
					orangeStandMenu('Failure')
					console.log(err)
					db.close()
					return
				}else{
					if(result.result.ok == 1){
						orangeStandMenu('Sucess')
						db.close()
					}else{
						orangeStandMenu('Failure 2.0')
						db.close()
					}
				}
			}
		)
	})
}

module.exports = {
	orangeStand: orangeStand
}

// To use in another file:
// var orangeStand = require('./orangeStand')
// orangeStand.orangeStand(pickedOranges, STUFf)
// Where STUFf is the callback function returning a json<commit_msg>Added timmer to stand<commit_after>//orangeStand by Michael Leonffu
var MongoClient = require('mongodb').MongoClient
var configDB = require('./../config/database.js')
ObjectId = require('mongodb').ObjectID

//This handles putting the data into the database to present onto the website; all this really does is a mongodb insert or update.

var orangeStand = function(orchard, pickedRankingOranges, pickedMatchHistoryOranges, calculatedJuice, orangeStandMenu){
	console.log('[START]-orangeStand')
	var standTime = new Date()

	// rankingsJuice requires all the information that goes into the rankings tab in the UI:
	// 	Team number, team name (not from any spesififc picker or peeler)
	//	This is ranking information form the ranking picker and peeler ->
	// 		Rank,
	// 		record T-W-L,
	// 		Qp, Rp,
	//	This would be from the averages picker and peeler ->
	// 		OPR, CCWM, OPR, OPR, OPR
	// Both combine into making the rankings tab; rankings Juice.

	//rankings should be in the form of:
	// ranking:[
	// 	{
	// 		rank: 123,
	// 		teamNumber: 123,
	// 		teamName: 123,
	// 		record:{
	// 			wins: 123,
	// 			losses: 123,
	// 			ties: 123
	// 		},
	// 		qualifyingPoints: 123,
	// 		rankingPoints: 123,
	// 		averageScore: .123,
	// 		averageMarginalScore: .123,
	// 		average:{
	// 			auto: .123,
	// 			driver: .123,
	// 			end: .123
	// 		}
	// 	}
	// ]

	// form of average picker peeler is in
	// {
	// 	juice: {
	// 		'123' : .123
	// 	},
	// 	error: .123
	// }

	// form of rankings picker peeler is in
	// {
	// 	rankings: [
	// 		{
	// 			teamName: 'abc',
	// 			teamNumber: 123,
	// 			record: {
	// 				wins: 123,
	// 				lossess: 123,
	// 				ties: 123
	// 			},
	// 			qualifyingPoints: 123,
	// 			rankingPoints: 123,
	// 			rank: 123
	// 		}
	// 	]
	// }

	// console.log('orchard', orchard)
	// console.log('pickedRankingOranges', pickedRankingOranges)
	// console.log('calculatedJuice', calculatedJuice)
	// console.log('pickedMatchHistoryOranges',pickedMatchHistoryOranges[0].gameData)

	//Rankings:
	var ranking = []

	for (var i = 0; i < pickedRankingOranges.length; i++) {
		//pickedRankingOranges[i]
		ranking[i] = {
			rank: i+1,
			teamNumber: pickedRankingOranges[i]._id,
			teamName: 'Anna Li', //Will get the thing latter
			record: {
				wins: pickedRankingOranges[i].wins,
				losses: pickedRankingOranges[i].losses,
				ties: pickedRankingOranges[i].ties
			},
			qualifyingPoints: pickedRankingOranges[i].qualifyingPoints,
			rankingPoints: pickedRankingOranges[i].rankingPoints,
			averageScore: calculatedJuice.calculatedOffensiveJuice.juice[String(pickedRankingOranges[i]._id)],
			averageMarginalScore: calculatedJuice.calculatedMarginalJuice.juice[String(pickedRankingOranges[i]._id)],
			average:{
				auto: 01,
				driver: 22,
				end: 99
			}
		}
	}

	//Match history:
	var matchHistory = []

	var rankingsJson = {}

	for (var i = 0; i < ranking.length; i++) {
		//ranking[i]
		rankingsJson[String(ranking[i].teamNumber)] = ranking[i]
	}

	for (var i = 0; i < pickedMatchHistoryOranges.length; i++) {
		//pickedMatchHistoryOranges[i]
		matchHistory[i] = {
			matchNumber: pickedMatchHistoryOranges[i]._id.matchNumber,
			alliance: pickedMatchHistoryOranges[i]._id.alliance,
			team1: {
				teamNumber: pickedMatchHistoryOranges[i].teams.team1,
				teamName: 'Anna Li',
				rank: rankingsJson[String(pickedMatchHistoryOranges[i].teams.team1)].rank
			},
			team2: {
				teamNumber: pickedMatchHistoryOranges[i].teams.team2,
				teamName: 'Anna Li',
				rank: rankingsJson[String(pickedMatchHistoryOranges[i].teams.team2)].rank
			},
			result: {
				total: pickedMatchHistoryOranges[i].matchData.resultInformation.score.total[String(pickedMatchHistoryOranges[i]._id.alliance)],
				penalty: pickedMatchHistoryOranges[i].matchData.resultInformation.score.penalty[String(pickedMatchHistoryOranges[i]._id.alliance)],
				final: pickedMatchHistoryOranges[i].matchData.resultInformation.score.final[String(pickedMatchHistoryOranges[i]._id.alliance)]
			},
			prediction: 'red',
			winner: pickedMatchHistoryOranges[i].matchData.resultInformation.winner,
			gameInformation: pickedMatchHistoryOranges[i].gameData.gameInformation
		}
	}

	//Average Scores:
	var averageScores = []

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

	MongoClient.connect(configDB.url, function(err,db){
		if(err){
			console.log(err)
			return
		}
		db.collection('eventOut').save(
			{
				_id: orchard,	//orcahrd is toaeventkey
				lastUpdated: new Date(), //Time of insert/update
				ranking: ranking,
				matchHistory: matchHistory
			},
			function(err, result){
				if(err){
					orangeStandMenu('Failure')
					console.log(err)
					db.close()
					return
				}else{
					if(result.result.ok == 1){
						console.log('Operation orangeStand time(Milliseconds):',new Date(new Date()-standTime).getMilliseconds())
						console.log('[DONE]-orangeStand')
						orangeStandMenu('Sucess')
						db.close()
					}else{
						orangeStandMenu('Failure 2.0')
						db.close()
					}
				}
			}
		)
	})
}

module.exports = {
	orangeStand: orangeStand
}

// To use in another file:
// var orangeStand = require('./orangeStand')
// orangeStand.orangeStand(pickedOranges, STUFf)
// Where STUFf is the callback function returning a json<|endoftext|>


<commit_before>// Originally found in JinsuNogi.

// Description:
// Automatically confirms the "You cannot switch to another channel while in conversation with an NPC." error message when attempting to change channels in NPC conversation.

// Walkthrough:
// IDA unicode string view -> code.interface.msg.etc.no_channelmove_npctalk
// xrefs
// Should be in a switch statement where you can see other denail strings being
// referenced.
// Change the first jz in this function to skip all the checks.

var firstJz = scan('0F 84 ?? ?? ?? ?? 89 5D F0 89 5D FC 8B 8E');

patch(firstJz, [0x90, 0xE9]);
<commit_msg>Fix for the latest update.<commit_after>// Originally found in JinsuNogi.

// Description:
// Automatically confirms the "You cannot switch to another channel while in conversation with an NPC." error message when attempting to change channels in NPC conversation.

// Walkthrough:
// IDA unicode string view -> code.interface.msg.etc.no_channelmove_npctalk
// xrefs
// Should be in a switch statement where you can see other denail strings being
// referenced.
// Change the first jz in this function to skip all the checks.

var firstJz = scan('0F 84 ? ? ? ? 89 5D F0 89 5D FC 8B CE');

patch(firstJz, [0x90, 0xE9]);
<|endoftext|>


<commit_before><commit_msg>Fixes bug in asset middleware<commit_after><|endoftext|>


<commit_before>/*
On window resize, call updateHeight() to resize the height of the page
components so that there's no global scroll for the page.
*/
$(window).resize(updateHeight);

/* Template helpers */
UI.registerHelper("isCurrentPageHome", function () {
  return Session.get('currentPage') === 'home';
});
UI.registerHelper("isUserLoggedIn", function () {
  return Meteor.user();
});
UI.registerHelper("isCurrentPageChat", function () {
  return Session.get('currentPage') === 'chat';
});

UI.registerHelper('isCurrentPage', function (page_name){
  return Session.get('currentPage') == page_name;
});

UI.registerHelper('currentServer', function () {
  var currentRoom = Session.get('room') || {};
  return currentRoom.server_name;
});

UI.registerHelper('currentRoom', function () {
  var currentRoom = Session.get('room') || {};
  if (currentRoom.roomtype == 'channel') {
    return currentRoom.channel_name;
  } else if (currentRoom.roomtype == 'pm') {
    return new Spacebars.SafeString(
      '<icon class="fa fa-user fa-inverted"></icon> ' + currentRoom.nick);
  }
});

/* Configure Accounts.ui for authentication */
Accounts.ui.config({
  requestPermissions: {
    github: ['user:email', '(no scope)']
  },
  passwordSignupFields: 'USERNAME_AND_EMAIL',
  extraSignupFields: []
});

Template.header.events({
  'click .drawer-toggle': function (e) {
    e.preventDefault();
    e.stopPropagation();
    var $this = $(e.currentTarget);
    var drawerType = $this.data('target-drawer-type');
    var revDrawerType = drawerType == 'left'? 'right': 'left';
    if ($this.hasClass('active')) {
      $('.drawer-container').removeClass('show-drawer').removeClass(
        'show-drawer-' + drawerType);
      $this.removeClass('active');
    } else {
      $('.drawer-container').addClass('show-drawer').addClass(
        'show-drawer-' + drawerType).removeClass(
        'show-drawer-' + revDrawerType);
      $('.drawer-toggle-' + revDrawerType).removeClass('active');
      $this.addClass('active');
    }
  }
});<commit_msg>Add handlers to hide chat page drawers.<commit_after>/*
On window resize, call updateHeight() to resize the height of the page
components so that there's no global scroll for the page.
*/
$(window).resize(updateHeight);

/* Template helpers */
UI.registerHelper("isCurrentPageHome", function () {
  return Session.get('currentPage') === 'home';
});
UI.registerHelper("isUserLoggedIn", function () {
  return Meteor.user();
});
UI.registerHelper("isCurrentPageChat", function () {
  return Session.get('currentPage') === 'chat';
});

UI.registerHelper('isCurrentPage', function (page_name){
  return Session.get('currentPage') == page_name;
});

UI.registerHelper('currentServer', function () {
  var currentRoom = Session.get('room') || {};
  return currentRoom.server_name;
});

UI.registerHelper('currentRoom', function () {
  var currentRoom = Session.get('room') || {};
  if (currentRoom.roomtype == 'channel') {
    return currentRoom.channel_name;
  } else if (currentRoom.roomtype == 'pm') {
    return new Spacebars.SafeString(
      '<icon class="fa fa-user fa-inverted"></icon> ' + currentRoom.nick);
  }
});

/* Configure Accounts.ui for authentication */
Accounts.ui.config({
  requestPermissions: {
    github: ['user:email', '(no scope)']
  },
  passwordSignupFields: 'USERNAME_AND_EMAIL',
  extraSignupFields: []
});

/* Manage drawers */
Template.header.events({
  'click .drawer-toggle': function (e) {
    e.preventDefault();
    e.stopPropagation();
    var $this = $(e.currentTarget);
    var drawerType = $this.data('target-drawer-type');
    var revDrawerType = drawerType == 'left'? 'right': 'left';
    if ($this.hasClass('active')) {
      $('.drawer-container').removeClass('show-drawer').removeClass(
        'show-drawer-' + drawerType);
      $this.removeClass('active');
    } else {
      $('.drawer-container').addClass('show-drawer').addClass(
        'show-drawer-' + drawerType).removeClass(
        'show-drawer-' + revDrawerType);
      $('.drawer-toggle-' + revDrawerType).removeClass('active');
      $this.addClass('active');
    }
  }
});

function hideDrawers () {
  $('.drawer-container').removeClass('show-drawer')
    .removeClass('show-drawer-left')
    .removeClass('show-drawer-right');
  $('.drawer-toggle').removeClass('active');
}

Template.chat.events({
  'click': function (e) {
    var $target = $(e.target);
    if ($target.parents('.drawer-left, .drawer-right').length == 0 &&
        !$target.hasClass('.drawer')) {
      return hideDrawers();
    }
  }
});

Deps.autorun(function () {
  var currentRoom = Session.get('room');
  hideDrawers();
})<|endoftext|>


<commit_before>describe('utilities', function() {

  'use strict';

  before(function(done) {
    var self = this;
    requirejs(
        ['utilities'],
        function(utilities) {
          self.mod = utilities;
          done();
        }, done);

    self.clock = sinon.useFakeTimers();
  });

  after(function() {
    this.clock.restore();
  });

  describe('currencyToInteger', function() {

    it('should remove any £ and , values', function() {
      expect(this.mod.currencyToInteger('£2,374,000')).to.equal(2374000);
    });

    it('should remove any decimal place', function() {
      expect(this.mod.currencyToInteger('£53,000.34')).to.equal(53000);
    });

  });

  describe('numberToCurrency', function() {

    it('should round to the nearest integer', function() {
      expect(this.mod.numberToCurrency('237400.12')).to.equal('£237,400');
      expect(this.mod.numberToCurrency('58.90')).to.equal('£59');
    });

  });

  describe('convertCamelCaseToDashed', function() {
    [
      ['FooBar', 'foo-bar'],
      ['FOOBar', 'foo-bar'],
      ['FooBarBaz', 'foo-bar-baz'],
    ].forEach(function(fixture) {
      var input = fixture[0],
          expected = fixture[1];

      it('should convert ' + input + ' into ' + expected, function() {
        expect(this.mod.convertCamelCaseToDashed(input)).to.equal(expected);
      });
    });
  });

  describe('log', function() {
    var sandbox;

    beforeEach(function() {
      sandbox = sinon.sandbox.create();

      // stub some console methods
      sandbox.stub(window.console, 'log');
      sandbox.stub(window.console, 'warn');
    });

    afterEach(function() {
      sandbox.restore();
    });

    it('should output a console.log message by default', function() {
      this.mod.log('test');

      expect(console.log.callCount).to.be.equal(1);
    });

    it('should output a console.warn message if specified', function() {
      this.mod.log('test', 'warn');

      expect(console.warn.callCount).to.be.equal(1);
    });

    it('should not attempt to call console if browser does not support it', function() {
      var stubDoesConsoleExist = sinon.stub(this.mod, 'doesConsoleExist', function() {
        return false;
      });

      this.mod.log('test');

      expect(console.log.callCount).to.be.equal(0);

      stubDoesConsoleExist.restore();
    });
  });

  describe('doesConsoleExist', function() {
    it('return true if the console method exists', function() {
      expect(this.mod.doesConsoleExist('warn')).to.be.equal(true);
    });

    it('return false if the console method does not exist', function() {
      expect(this.mod.doesConsoleExist('blah')).to.be.equal(false);
    });
  });

  describe('debounce', function() {
    it('calls the method after certain amount of time', function() {
      var func = sinon.stub(),
          time = 2000;
      this.mod.debounce(func, time)();
      expect(func.callCount).to.be.equal(0);
      this.clock.tick(time);
      expect(func.callCount).to.be.equal(1);
    })
  });
});
<commit_msg>Add more permutations to tease out corner cases<commit_after>describe('utilities', function() {

  'use strict';

  before(function(done) {
    var self = this;
    requirejs(
        ['utilities'],
        function(utilities) {
          self.mod = utilities;
          done();
        }, done);

    self.clock = sinon.useFakeTimers();
  });

  after(function() {
    this.clock.restore();
  });

  describe('currencyToInteger', function() {

    it('should remove any £ and , values', function() {
      expect(this.mod.currencyToInteger('£2,374,000')).to.equal(2374000);
    });

    it('should remove any decimal place', function() {
      expect(this.mod.currencyToInteger('£53,000.34')).to.equal(53000);
    });

  });

  describe('numberToCurrency', function() {

    it('should round to the nearest integer', function() {
      expect(this.mod.numberToCurrency('237400.12')).to.equal('£237,400');
      expect(this.mod.numberToCurrency('58.90')).to.equal('£59');
    });

  });

  describe('convertCamelCaseToDashed', function() {
    [
      // Permutations of upper and lower case (to catch corner cases)
      ['a', 'a'],
      ['A', 'a'],
      ['aa', 'aa'],
      ['Aa', 'aa'],
      ['aA', 'aa'],
      ['AA', 'aa'],
      ['aaa', 'aaa'],
      ['Aaa', 'aaa'],
      ['aAa', 'a-aa'],
      ['aaA', 'aa-a'],
      ['AAa', 'a-aa'],
      ['AaA', 'aa-a'],
      ['aAA', 'a-aa'],
      ['AAA', 'aaa'],
      ['AbAbAb', 'ab-ab-ab'],
      ['ABAbAb', 'ab-ab-ab'],
      ['AbABAb', 'ab-ab-ab'],
      ['AbAbAB', 'ab-ab-ab'],
      ['ABABAb', 'abab-ab'],
      ['AbABAB', 'ab-abab'],
      ['AbABAb', 'ab-ab-ab'],
      ['AbcAbcAbc', 'abc-abc-abc'],
      ['ABCAbcAbc', 'abc-abc-abc'],
      ['AbcABCAbc', 'abc-abc-abc'],
      ['AbcAbcABC', 'abc-abc-abc'],

      // Examples (from the original test)
      ['FooBar', 'foo-bar'],
      ['FOOBar', 'foo-bar'],
      ['FooBarBaz', 'foo-bar-baz'],
    ].forEach(function(fixture) {
      var input = fixture[0],
          expected = fixture[1];

      it('should convert ' + input + ' into ' + expected, function() {
        expect(this.mod.convertCamelCaseToDashed(input)).to.equal(expected);
      });
    });
  });

  describe('log', function() {
    var sandbox;

    beforeEach(function() {
      sandbox = sinon.sandbox.create();

      // stub some console methods
      sandbox.stub(window.console, 'log');
      sandbox.stub(window.console, 'warn');
    });

    afterEach(function() {
      sandbox.restore();
    });

    it('should output a console.log message by default', function() {
      this.mod.log('test');

      expect(console.log.callCount).to.be.equal(1);
    });

    it('should output a console.warn message if specified', function() {
      this.mod.log('test', 'warn');

      expect(console.warn.callCount).to.be.equal(1);
    });

    it('should not attempt to call console if browser does not support it', function() {
      var stubDoesConsoleExist = sinon.stub(this.mod, 'doesConsoleExist', function() {
        return false;
      });

      this.mod.log('test');

      expect(console.log.callCount).to.be.equal(0);

      stubDoesConsoleExist.restore();
    });
  });

  describe('doesConsoleExist', function() {
    it('return true if the console method exists', function() {
      expect(this.mod.doesConsoleExist('warn')).to.be.equal(true);
    });

    it('return false if the console method does not exist', function() {
      expect(this.mod.doesConsoleExist('blah')).to.be.equal(false);
    });
  });

  describe('debounce', function() {
    it('calls the method after certain amount of time', function() {
      var func = sinon.stub(),
          time = 2000;
      this.mod.debounce(func, time)();
      expect(func.callCount).to.be.equal(0);
      this.clock.tick(time);
      expect(func.callCount).to.be.equal(1);
    })
  });
});
<|endoftext|>


<commit_before>'use strict';

angular.module('casusMIT3.index', ['ngRoute','AdalAngular'])

.config(['$routeProvider', function($routeProvider) {
  $routeProvider.when('/index', {
    templateUrl: 'index/index.html',
    controller: 'indexCtrl',
    requireADLogin: true
  });
}])

.controller('indexCtrl', ['adalAuthenticationService', '$http', function(adalService,$http) {

  test();

  function test(){
  $http.get('https://api.powerbi.com/beta/myorg/dashboards')
      .succes(function (d) {
        console.log("yay");
      })
      .error(function (d) {
        console.log("nope");
      })
}

}]);<commit_msg>Added Power BI Data factory<commit_after>'use strict';

angular.module('casusMIT3.index', ['ngRoute','AdalAngular'])

.config(['$routeProvider', function($routeProvider) {
  $routeProvider.when('/index', {
    templateUrl: 'index/index.html',
    controller: 'indexCtrl',
    requireADLogin: true
  });
}])

.controller('indexCtrl', ['adalAuthenticationService', '$http', function(adalService,$http) {

  test();

  function test(){
  $http.get('https://api.powerbi.com/beta/myorg/dashboards')
      .then(function () {
        console.log("yay");
      })

}

}]);<|endoftext|>


<commit_before>var Map = require('./map');

var Renderer = module.exports = function(context, width, height) {
  this.width = width;
  this.height = height;
  this.tileX = canvas.width / width;
  this.tileY = canvas.height / height;
  this.map = new Map(width, height);
  this.map.genMap();
  this.map.genPortal();
  this.score = 0;
  var fps = 60;
  this.frameCounter = 0;
  this.portalColor;

  this.draw = function() {
    this.frameCounter++;
    // Recursive call for continuous animation
    setTimeout(function() {
      context.clearRect(0, 0, canvas.width, canvas.height);
      var self = this;
      requestAnimationFrame(self.draw);

      if(this.frameCounter % 5 === 0) {
        var colorSeedR = Math.floor(Math.random() * 256);
        var colorSeedG = Math.floor(Math.random() * 256);
        var colorSeedB = Math.floor(Math.random() * 256);
        this.portalColor = 'rgba(' + colorSeedR + ', ' + colorSeedG + ', ' + colorSeedB + ', 1.0)';
        this.frameCounter = 0;
      }

      this.map.mapArray.forEach(function(row, y) {
        row.forEach(function(tile, x) {
          if(tile === 3) {
            self.drawTile("rgba(0, 0, 255, 0.9)", x, y);
          } else if(tile === 5) {
            self.drawTile("rgba(250, 255, 0, 0.9)", x, y);
          } else if(tile === 4) {
            self.drawTile(self.portalColor, x, y);
          } else if(tile === 2) {
            self.drawTile("rgba(150, 70, 70, 0.9)", x, y);
          } else if(tile === 1) {
            self.drawTile("rgba(0, 0, 0, 0.8)", x, y);
          } else {
            self.drawTile("rgba(15, 200, 35, 0.8)", x, y);
          }
        });
      });
      this.drawScore();
    }.bind(this), 1000 / fps);
  }.bind(this);

  this.drawTile = function(color, x, y) {
    context.fillStyle = color;
    context.fillRect(
      x * this.tileX, y * this.tileY,
      this.tileX, this.tileY
    );
  };

  this.drawScore = function() {
    context.fillStyle = "rgba(20, 255, 255, 0.9)";
    context.font = '2em serif';
    context.fillText('Score: ' + this.score, 20, canvas.height - 20);
  }

  this.refreshDimensions = function() {
    canvas.height = window.innerHeight;
    canvas.width = window.innerWidth;
    this.tileX = canvas.width / this.width;
    this.tileY = canvas.height / this.height;
    this.draw();
  }.bind(this);

  this.moveEntity = function(x, y, dx, dy) {
    var fromVal = this.map.mapArray[y][x];
    var newVal = this.map.mapArray[y + dy][x + dx];

    if(newVal !== 5 && newVal !== 4) {
      this.map.mapArray[y + dy][x + dx] = fromVal;
      this.map.mapArray[y][x] = newVal;
    }
  }.bind(this);
};

<commit_msg>variable spacing<commit_after>var Map = require('./map');

var Renderer = module.exports = function(context, width, height) {
  this.width = width;
  this.height = height;

  this.tileX = canvas.width / width;
  this.tileY = canvas.height / height;

  this.map = new Map(width, height);
  this.map.genMap();
  this.map.genPortal();

  this.score = 0;
  this.highScore = 0;

  var fps = 60;
  this.frameCounter = 0;
  this.portalColor;

  this.draw = function() {
    this.frameCounter++;
    // Recursive call for continuous animation
    setTimeout(function() {
      context.clearRect(0, 0, canvas.width, canvas.height);
      var self = this;
      requestAnimationFrame(self.draw);

      if(this.frameCounter % 5 === 0) {
        var colorSeedR = Math.floor(Math.random() * 256);
        var colorSeedG = Math.floor(Math.random() * 256);
        var colorSeedB = Math.floor(Math.random() * 256);
        this.portalColor = 'rgba(' + colorSeedR + ', ' + colorSeedG + ', ' + colorSeedB + ', 1.0)';
        this.frameCounter = 0;
      }

      this.map.mapArray.forEach(function(row, y) {
        row.forEach(function(tile, x) {
          if(tile === 3) {
            self.drawTile("rgba(0, 0, 255, 0.9)", x, y);
          } else if(tile === 5) {
            self.drawTile("rgba(250, 255, 0, 0.9)", x, y);
          } else if(tile === 4) {
            self.drawTile(self.portalColor, x, y);
          } else if(tile === 2) {
            self.drawTile("rgba(150, 70, 70, 0.9)", x, y);
          } else if(tile === 1) {
            self.drawTile("rgba(0, 0, 0, 0.8)", x, y);
          } else {
            self.drawTile("rgba(15, 200, 35, 0.8)", x, y);
          }
        });
      });
      this.drawScore();
    }.bind(this), 1000 / fps);
  }.bind(this);

  this.drawTile = function(color, x, y) {
    context.fillStyle = color;
    context.fillRect(
      x * this.tileX, y * this.tileY,
      this.tileX, this.tileY
    );
  };

  this.drawScore = function() {
    context.fillStyle = "rgba(20, 255, 255, 0.9)";
    context.font = '2em serif';
    context.fillText('Score: ' + this.score, 20, canvas.height - 20);
  }

  this.refreshDimensions = function() {
    canvas.height = window.innerHeight;
    canvas.width = window.innerWidth;
    this.tileX = canvas.width / this.width;
    this.tileY = canvas.height / this.height;
    this.draw();
  }.bind(this);

  this.moveEntity = function(x, y, dx, dy) {
    var fromVal = this.map.mapArray[y][x];
    var newVal = this.map.mapArray[y + dy][x + dx];

    if(newVal !== 5 && newVal !== 4) {
      this.map.mapArray[y + dy][x + dx] = fromVal;
      this.map.mapArray[y][x] = newVal;
    }
  }.bind(this);
};

<|endoftext|>


<commit_before>'use strict';

/* Services */

angular.module('myApp.services', [])

    .value('FIREBASE_URL', 'https://waitandeat-demo-ver1.firebaseio.com/')
    // Preferred way to make a service
    // .factory('FIREBASE_URL', function() {
    //     return 'https://waitandeat-demo-ver1.firebaseio.com/';
    // });

	.factory('dataService', function ($firebase, FIREBASE_URL) {
		var dataRef =  new Firebase(FIREBASE_URL);
		var fireData = $firebase(dataRef);

		return fireData;
	})

	.factory('partyService', function($firebase, FIREBASE_URL){
		var partiesRef = new Firebase(FIREBASE_URL + 'parties');
    	var parties = $firebase(partiesRef);

    	var partyServiceObject = {
    		parties: parties,
    		saveParty: function (party) {
				parties.$add(party);
    		}
    	};
    	return partyServiceObject;
	})

	.factory('textMessageService', function($firebase, FIREBASE_URL, partyService){
		var textMessageRef = new Firebase(FIREBASE_URL + 'textMessages');
        var textMessages = $firebase(textMessageRef);

        var textMessageObject = {
        	sendTextMessage: function (party) {
	        	var newTextMessage = {
		        	phoneNumber: party.phone,
		            size: party.size,
		            name: party.name
	        	};
	        	textMessages.$add(newTextMessage);
		        party.notified = 'Yes';
		        partyService.parties.$save(party.$id);
        	}
        };

        return textMessageObject;

	})

	.factory('authService', function($firebaseSimpleLogin, $location, $rootScope, FIREBASE_URL) {
		var authRef = new Firebase(FIREBASE_URL);
    	var auth = $firebaseSimpleLogin(authRef);

        var authServiceObject = {
        	register: function (user) {
        		auth.$createUser(user.email, user.password)
		            .then(function(data) {
                console.log(data);
                authServiceObject.login(user);
            });
        	},
            login: function(user) {
                auth.$login('password', user)
                    .then(function(data) {
                            console.log(data);
                            $location.path('/waitlist');
                        });
                    },
            logout: function () {
            	   		auth.$logout();
       				 	$location.path('/');
            }
        };

        $rootScope.$on("$firebaseSimpleLogin:login", function (e, user) {
        	$rootScope.currentUser = user;
        });

        $rootScope.$on("$firebaseSimpleLogin:logout", function () {
        	$rootScope.currentUser = null;
        });

        return authServiceObject;
       });<commit_msg>refactored party service and injected data service<commit_after>'use strict';

/* Services */

angular.module('myApp.services', [])

    .value('FIREBASE_URL', 'https://waitandeat-demo-ver1.firebaseio.com/')
    // Preferred way to make a service
    // .factory('FIREBASE_URL', function() {
    //     return 'https://waitandeat-demo-ver1.firebaseio.com/';
    // });

	.factory('dataService', function ($firebase, FIREBASE_URL) {
		var dataRef =  new Firebase(FIREBASE_URL);
		var fireData = $firebase(dataRef);

		return fireData;
	})

	.factory('partyService', function(dataService){
    	var parties = dataService.$child('parties');

    	var partyServiceObject = {
    		parties: parties,
    		saveParty: function (party) {
				parties.$add(party);
    		}
    	};
    	return partyServiceObject;
	})

	.factory('textMessageService', function($firebase, FIREBASE_URL, partyService){
		var textMessageRef = new Firebase(FIREBASE_URL + 'textMessages');
        var textMessages = $firebase(textMessageRef);

        var textMessageObject = {
        	sendTextMessage: function (party) {
	        	var newTextMessage = {
		        	phoneNumber: party.phone,
		            size: party.size,
		            name: party.name
	        	};
	        	textMessages.$add(newTextMessage);
		        party.notified = 'Yes';
		        partyService.parties.$save(party.$id);
        	}
        };

        return textMessageObject;

	})

	.factory('authService', function($firebaseSimpleLogin, $location, $rootScope, FIREBASE_URL) {
		var authRef = new Firebase(FIREBASE_URL);
    	var auth = $firebaseSimpleLogin(authRef);

        var authServiceObject = {
        	register: function (user) {
        		auth.$createUser(user.email, user.password)
		            .then(function(data) {
                console.log(data);
                authServiceObject.login(user);
            });
        	},
            login: function(user) {
                auth.$login('password', user)
                    .then(function(data) {
                            console.log(data);
                            $location.path('/waitlist');
                        });
                    },
            logout: function () {
            	   		auth.$logout();
       				 	$location.path('/');
            }
        };

        $rootScope.$on("$firebaseSimpleLogin:login", function (e, user) {
        	$rootScope.currentUser = user;
        });

        $rootScope.$on("$firebaseSimpleLogin:logout", function () {
        	$rootScope.currentUser = null;
        });

        return authServiceObject;
       });<|endoftext|>


<commit_before>'use strict';

/* Services */

// Demonstrate how to register services
// In this case it is a simple value service.
angular.module('myApp.services', [])
.value('FIREBASE_URL', 'https://focalhost.firebaseio.com/')
.factory('dataService', function($firebase, FIREBASE_URL) {
  var dataRef = new Firebase(FIREBASE_URL);
  var fireData = $firebase(dataRef);
  return fireData;
})

.factory('partyService', function(dataService) {
  var users = dataService.$child('users');

  var partyServiceObject = {
    saveParty: function(party, userId) {
      users.$child(userId).$child('parties').$add(party);
    },
    getPartiesByUserId: function(userId) {
      return users.$child(userId).$child('parties');
    }
  };

  return partyServiceObject;
})

.factory('textMessageService', function(dataService, partyService) {
  var textMessages = dataService.$child('textMessages');

  var textMessageServiceObject = {
    sendTextMessage: function(party, userId) {
      var newTextMessage = {
        phoneNumber: party.phone,
        size: party.size,
        name: party.name
      };
      textMessages.$add(newTextMessage);
      partyService.getPartiesByUserId(userId).$child(party.$id).$update({notified: 'Yes'});
    }
  };
  return textMessageServiceObject;
})

.factory('authService', function($firebaseSimpleLogin, $location, $rootScope, FIREBASE_URL) {
  var authRef = new Firebase(FIREBASE_URL);
  var auth = $firebaseSimpleLogin(authRef);

  var authServiceObject = {
    register: function(user) {
      auth.$createUser(user.email, user.password).then(function(data) {
        console.log(data);
        authServiceObject.login(user);
      });
    },
    login: function(user) {
      auth.$login('password', user).then(function(data) {
        console.log(data);
        $location.path('/waitlist');
      });
    },
    logout: function() {
      auth.$logout();
      $location.path('/');
    },
    getCurrentUser: function() {
      return auth.$getCurrentUser();
    }
  };

  $rootScope.$on("$firebaseSimpleLogin:login", function(e, user) {
    $rootScope.currentUser = user;
  });

  $rootScope.$on("$firebaseSimpleLogin:logout", function() {
    $rootScope.currentUser = null;
  })

  return authServiceObject
})
<commit_msg>adds functionality to send emails with emails object in firebase<commit_after>'use strict';

/* Services */

// Demonstrate how to register services
// In this case it is a simple value service.
angular.module('myApp.services', [])
.value('FIREBASE_URL', 'https://focalhost.firebaseio.com/')
.factory('dataService', function($firebase, FIREBASE_URL) {
  var dataRef = new Firebase(FIREBASE_URL);
  var fireData = $firebase(dataRef);
  return fireData;
})

.factory('partyService', function(dataService) {
  var users = dataService.$child('users');

  var partyServiceObject = {
    saveParty: function(party, userId) {
      users.$child(userId).$child('parties').$add(party);
    },
    getPartiesByUserId: function(userId) {
      return users.$child(userId).$child('parties');
    }
  };

  return partyServiceObject;
})

.factory('textMessageService', function(dataService, partyService) {
  var textMessages = dataService.$child('textMessages');

  var textMessageServiceObject = {
    sendTextMessage: function(party, userId) {
      var newTextMessage = {
        phoneNumber: party.phone,
        size: party.size,
        name: party.name
      };
      textMessages.$add(newTextMessage);
      partyService.getPartiesByUserId(userId).$child(party.$id).$update({notified: 'Yes'});
    }
  };
  return textMessageServiceObject;
})

.factory('authService', function($firebaseSimpleLogin, $location, $rootScope, FIREBASE_URL, dataService) {
  var authRef = new Firebase(FIREBASE_URL);
  var auth = $firebaseSimpleLogin(authRef);
  var emails = dataService.$child('emails');

  var authServiceObject = {
    register: function(user) {
      auth.$createUser(user.email, user.password).then(function(data) {
        console.log(data);
        emails.$add({email: user.email})
        authServiceObject.login(user);
      });
    },
    login: function(user) {
      auth.$login('password', user).then(function(data) {
        console.log(data);
        $location.path('/waitlist');
      });
    },
    logout: function() {
      auth.$logout();
      $location.path('/');
    },
    getCurrentUser: function() {
      return auth.$getCurrentUser();
    }
  };

  $rootScope.$on("$firebaseSimpleLogin:login", function(e, user) {
    $rootScope.currentUser = user;
  });

  $rootScope.$on("$firebaseSimpleLogin:logout", function() {
    $rootScope.currentUser = null;
  })

  return authServiceObject
})
<|endoftext|>


<commit_before>define([
        'threejs',
        'dobuki',
        './imagestore.js',
        '../core/localization/location.js',
    ],
    function(THREE, DOK, ImageStore, Location) {
        var AgentsView = function (cameraHandler, spriteRenderer, cellSize, game) {
            var range = 100;
            var worldWidth = game.getWidth();
            var worldHeight = game.getHeight();

            var tempArray = [];

            var collection = new DOK.Collection({
                    type: "grid",
                    get x() {
                        return cameraHandler.getCamPos().x - Math.floor(range / 2);
                    },
                    get y() {
                        return cameraHandler.getCamPos().y - Math.floor(range / 2);
                    },
                    width: range,
                    height: range,
                    agentsCache: {},
                },
                function (x, y) {
                    var tileX = ((x % worldWidth) + worldWidth) % worldWidth;
                    var tileY = ((y % worldHeight) + worldHeight) % worldHeight;
                    if(this.options.agentsCache[tileX+"-"+tileY] === undefined) {
                        this.options.agentsCache[tileX+"-"+tileY] = game.getWorld().getAgentsAt(new Location(tileX,tileY));
                    }
                    var agents = this.options.agentsCache[tileX+"-"+tileY];
                    tempArray.length = 0;
                    for(var a in agents) {
                        var agent = agents[a];
                        var img = ImageStore.getImageFromAgent(agent);

                        var spriteObj = DOK.SpriteObject.create(
                            x * cellSize, y * cellSize, cellSize,
                            cellSize*3, cellSize*3,
                            null,
                            1,
                            img
                        );
                        spriteObj.type = 'face';
                        tempArray.push(spriteObj);
                    }

                    return tempArray;
                }
            );

            function update() {
                collection.forEach(spriteRenderer.display);
            }

            function clearCache(x,y) {
                var tileX = ((x % worldWidth) + worldWidth) % worldWidth;
                var tileY = ((y % worldHeight) + worldHeight) % worldHeight;
                var key = tileX + "-" + tileY;
                delete collection.options.agentsCache[key];
            }

            game.getWorld().setAgentCallback(function(agent, locationFrom, locationTo) {
                clearCache(locationFrom.getX(), locationFrom.getY());
                clearCache(locationTo.getX(), locationTo.getY());
            });

            this.update = update;
        }

        return AgentsView;
});
<commit_msg>location can be null<commit_after>define([
        'threejs',
        'dobuki',
        './imagestore.js',
        '../core/localization/location.js',
    ],
    function(THREE, DOK, ImageStore, Location) {
        var AgentsView = function (cameraHandler, spriteRenderer, cellSize, game) {
            var range = 100;
            var worldWidth = game.getWidth();
            var worldHeight = game.getHeight();

            var tempArray = [];

            var collection = new DOK.Collection({
                    type: "grid",
                    get x() {
                        return cameraHandler.getCamPos().x - Math.floor(range / 2);
                    },
                    get y() {
                        return cameraHandler.getCamPos().y - Math.floor(range / 2);
                    },
                    width: range,
                    height: range,
                    agentsCache: {},
                },
                function (x, y) {
                    var tileX = ((x % worldWidth) + worldWidth) % worldWidth;
                    var tileY = ((y % worldHeight) + worldHeight) % worldHeight;
                    if(this.options.agentsCache[tileX+"-"+tileY] === undefined) {
                        this.options.agentsCache[tileX+"-"+tileY] = game.getWorld().getAgentsAt(new Location(tileX,tileY));
                    }
                    var agents = this.options.agentsCache[tileX+"-"+tileY];
                    tempArray.length = 0;
                    for(var a in agents) {
                        var agent = agents[a];
                        var img = ImageStore.getImageFromAgent(agent);

                        var spriteObj = DOK.SpriteObject.create(
                            x * cellSize, y * cellSize, cellSize,
                            cellSize*3, cellSize*3,
                            null,
                            1,
                            img
                        );
                        spriteObj.type = 'face';
                        tempArray.push(spriteObj);
                    }

                    return tempArray;
                }
            );

            function update() {
                collection.forEach(spriteRenderer.display);
            }

            function clearCache(x,y) {
                var tileX = ((x % worldWidth) + worldWidth) % worldWidth;
                var tileY = ((y % worldHeight) + worldHeight) % worldHeight;
                var key = tileX + "-" + tileY;
                delete collection.options.agentsCache[key];
            }

            game.getWorld().setAgentCallback(function(agent, locationFrom, locationTo) {
                if(locationFrom)
                    clearCache(locationFrom.getX(), locationFrom.getY());
                if(locationTo)
                    clearCache(locationTo.getX(), locationTo.getY());
            });

            this.update = update;
        }

        return AgentsView;
});
<|endoftext|>


<commit_before>require('dotenv').config({path: '../.env'})
var pg = require('pg')
var _ = require ('lodash')

pg.connect(process.env.PG_CONNECTION, function(err, client, done) {
  if (err) {
    console.error(err)
    result.send('db connection error')
    done()
    return
  }
  var query = client.query('SELECT * FROM  "Entry"')
  var results = []
  query.on('row', function(row) {
    results.push(row);
  });

  // After all data is returned, close connection and return results
  query.on('end', function() {
    insertResults(results)
  })

  function insertResults(results) {

    var mergedPlaylists = _(results).map(function(entry) {
      // strip the extra db data we don't need
      return entry.data
    }).filter(function(data) {
      // select only playlists
      return typeof data.playlists !== 'undefined'
    }).groupBy(function(data) {
      // group playlists by their username
      return data.username
    })
      .values()
      .map(function(user) {
        //combine a users entries together
        return _(user).reduce(mergeArrayReduction)
      })
      .each(function(user) {
        user.playlists = _(user.playlists).groupBy(function(playlist) {
          return playlist.name
        }).value()//.reduce(mergeArrayReduction)
      })
      .value()
    //should modify this to just return the first playlist
    console.log(mergedPlaylists[0].playlists['admin'])
    return
    var songsFromPlaylists = _(results).groupBy(function(entry) {
      return entry.data.username
    }).map(function(entry) {
      return entry.data.playlists
    })
      .compact()
      .value()
    console.log(songsFromPlaylists)
    return
    importSongs()

    return
    console.log(results)
    var users = _(results).map(function(entry) {

      var playlistNames = _(entry.data.playlists)

      return {
        username: entry.data.username
      }
    })
      .uniq()
      .value()

    console.log(users)

    return
    // merge all songs into one array removing dupes
    if (typeof entry.data.song !== 'undefined') {

    } else if (typeof entry.data.playlists !== 'undefined') {

    }
    importUsers()
    importPlaylists()
  }
});

function mergeArrayReduction(object, current) {
  return _.merge(object, current, mergeArrays)
}

function mergeArrays(a, b) {
  if (_.isArray(a)) {
    return a.concat(b);
  }
}

<commit_msg>song extraction<commit_after>require('dotenv').config({path: '../.env'})
var pg = require('pg')
var _ = require ('lodash')

pg.connect(process.env.PG_CONNECTION, function(err, client, done) {
  if (err) {
    console.error(err)
    result.send('db connection error')
    done()
    return
  }
  var query = client.query('SELECT * FROM  "Entry"')
  var results = []
  query.on('row', function(row) {
    results.push(row);
  });

  // After all data is returned, close connection and return results
  query.on('end', function() {
    insertResults(results)
  })

  function insertResults(results) {

    var entriesByUser = _(results).map(function(entry) {
      // strip the extra db data we don't need
      return entry.data
    }).filter(function(data) {
      // select only playlists
      return typeof data.playlists !== 'undefined'
    }).groupBy(function(data) {
      // group playlists by their username
      return data.username
    }).value()

    var users = Object.keys(entriesByUser);
    var lastUserEntry = _(users)
        .map(function(user) {
          var lastUserEntryIndex = entriesByUser[user].length - 1
          return entriesByUser[user][lastUserEntryIndex]
        }).value()

    // we now have the last entry that each user submitted. that's a good thing

    var songs = _(lastUserEntry)
      .map(function(entry) {
        // get just the playlists
        return entry.playlists
      })
      .flatten() //merge arrays
      .map(function(playlist) {
        // get just the songs
        return playlist.songs.data
      })
      .flatten() //merge arrays
      .uniq() //remove dupes
      .value()

    insertSongs(songs)
    done()
    console.log('done');
    process.exit(0)
  }
});
function insertSongs(songs) {

}<|endoftext|>


<commit_before>// test
var React = require('react');
var PaginationNumberItem = React.createClass({
  render: function() {
    if (this.props.pagenum) {
      return (

          {this.props.pagenum}

      );
    } else {
      return (

          ...

      );
    }
  }
});
var Pagination = React.createClass({
  getInitialState: function() {
    return Object.assign({}, {
      total: 1,
      pageList: [10, 20, 30, 50],
      pageSize: 10,
      pageNumber: 1,
      loading: false,
      onChangePageSize: function(pageSize) {
      },
      onSelectPage: function(pageNumber, pageSize) {
      }
    }, this.props);
  },
  createPageList: function() {
    var pageList = this.state.pageList.map(function(v) {
      return '<option value="'+v+'">'+v+'</option>';
    });
    return {
      __html: pageList
    };
  },
  buildPageNumberElements: function() {
    var pageNumberElements = [];
    var pages = Math.ceil(this.state.total / this.state.pageSize);
    var currentPage = this.state.pageNumber;
    if (pages <= 6) {
      for(var i = 0; i < pages; i++) {
        var page = i + 1;
        pageNumberElements.push(<PaginationNumberItem pagenum={page} />);
      }
    } else {
      if (currentPage <= 3 || currentPage >= pages - 2) {
        for(var i = 0; i < 3; i++) {
          var page = i + 1;
          pageNumberElements.push(<PaginationNumberItem pagenum={page} />);
        }
        pageNumberElements.push(<PaginationNumberItem />);
      } else {
        for(var i = currentPage - 3; i < currentPage; i++) {
          var page = i + 1;
          pageNumberElements.push(<PaginationNumberItem pagenum={page} />);
        }
        if (currentPage + 3 != pages) {
          pageNumberElements.push(<PaginationNumberItem />);
        }
      }
      for(var i = pages - 3; i < pages; i++) {
        var page = i + 1;
        pageNumberElements.push(<PaginationNumberItem pagenum={page} />);
      }
    }
    return pageNumberElements;
  },
  render: function() {
    var pageNumberList = this.buildPageNumberElements();
    return (

          共{this.state.total}条记录，显示行数
          <select name="" dangerouslySetInnerHTML={this.createPageList()}></select>
          页

          {pageNumberList}

转到

<input type="text" name="page_num" />

页

<button>go</button>

    );
  }
});

module.exports = Pagination;<commit_msg>Update paginationComponent.js<commit_after>// test
var React = require('react');
var PaginationNumberItem = React.createClass({
  render: function() {
    if (this.props.pagenum) {
      return (

          {this.props.pagenum}

      );
    } else {
      return (

          ...

      );
    }
  }
});
var PaginationSelectControlOption = React.createClass({
  render: function() {
    return (
      <option value={this.props.value}>{this.props.value}</option>
    );
  }
});
var Pagination = React.createClass({
  getInitialState: function() {
    return Object.assign({}, {
      total: 1,
      pageList: [10, 20, 30, 50],
      pageSize: 10,
      pageNumber: 1,
      loading: false,
      onChangePageSize: function(pageSize) {
      },
      onSelectPage: function(pageNumber, pageSize) {
      }
    }, this.props);
  },
  buildPageNumberElements: function() {
    var pageNumberElements = [];
    var pages = Math.ceil(this.state.total / this.state.pageSize);
    var currentPage = this.state.pageNumber;
    if (pages <= 6) {
      for(var i = 0; i < pages; i++) {
        var page = i + 1;
        pageNumberElements.push(<PaginationNumberItem key={page} pagenum={page} />);
      }
    } else {
      if (currentPage <= 3 || currentPage >= pages - 2) {
        for(var i = 0; i < 3; i++) {
          var page = i + 1;
          pageNumberElements.push(<PaginationNumberItem key={page} pagenum={page} />);
        }
        pageNumberElements.push(<PaginationNumberItem />);
      } else {
        for(var i = currentPage - 3; i < currentPage; i++) {
          var page = i + 1;
          pageNumberElements.push(<PaginationNumberItem key={page} pagenum={page} />);
        }
        if (currentPage + 3 != pages) {
          pageNumberElements.push(<PaginationNumberItem />);
        }
      }
      for(var i = pages - 3; i < pages; i++) {
        var page = i + 1;
        pageNumberElements.push(<PaginationNumberItem key={page} pagenum={page} />);
      }
    }
    return pageNumberElements;
  },
  render: function() {
    var pageNumberList = this.buildPageNumberElements();
    var paginationSelectOptions = this.state.pageList.map(function(v) {
      return <PaginationSelectControlOption key={v} value={v} />;
    });
    return (

          共{this.state.total}条记录，显示行数
          <select name="">
            {paginationSelectOptions}
          </select>
          页

          {pageNumberList}

转到

<input type="text" name="page_num" />

页

<button>go</button>

    );
  }
});

module.exports = Pagination;<|endoftext|>


<commit_before>function toggle_current (elem) {
  var parent_li = elem.closest('li');
  parent_li.siblings('li.current').removeClass('current');
  parent_li.siblings().find('li.current').removeClass('current');
  parent_li.find('> ul li.current').removeClass('current');
  parent_li.toggleClass('current');
}

$(document).ready(function() {
  // Nav menu link click operations
  $(document).on('click', ".nav-toc .current ul li a", function() {
    var target = $(this);
    // Close menu when you click a link.
    //// $("[data-toggle='nav-shift']").removeClass("shift");
    //// $("[data-toggle='rst-versions']").toggleClass("shift");
    // Handle dynamic display of l3 and l4 nav lists
    toggle_current(target);
    if (typeof(window.SphinxTheme) != 'undefined') {
      window.SphinxTheme.sticky_nav.hash_change();
    }
  });

  //// $(document).on('click', "[data-toggle='rst-current-version']", function() {
  ////   $("[data-toggle='rst-versions']").toggleClass("shift-up");
  //// });

  // Make tables responsive
  //// $("table.docutils:not(.field-list)").wrap("

");

  // Add expand links to all parents of nested ul
  $('.nav-toc ul').siblings('a').each(function () {
    var link = $(this);
    expand = $('');
    expand.on('click', function (ev) {
      toggle_current(link);
      ev.stopPropagation();
      return false;
    });
    link.prepend(expand);
  });
});

// Sphinx theme state
window.SphinxTheme = (function (jquery) {
  var sticky_nav = (function () {
    var nav_bar,
        win,
        win_scroll = false,
        link_scroll = false,
        win_position = 0,

        enable = function () {
          init();
          reset();
          win.on('hashchange', reset);

          // Set scrolling
          win.on('scroll', function () {
            if (!link_scroll) {
              win_scroll = true;
            }
          });

          setInterval(function () {
            if (win_scroll) {
              win_scroll = false;
              var new_win_position = win.scrollTop(),
                  nav_position = nav_bar.scrollTop(),
                  new_nav_position = nav_position + (new_win_position - win_position);
              nav_bar.scrollTop(new_nav_position);
              win_position = new_win_position;
            }
          }, 25);
        },

        init = function () {
          nav_bar = jquery('nav.nav-side:first');
          win = jquery(window);
        },

        reset = function () {
          // Get anchor from URL and open up nested nav
          var anchor = encodeURI(window.location.hash);
          if (anchor) {
            try {
              var link = $('.nav-toc').find('[href="' + anchor + '"]');
              $('.nav-toc li.toctree-l1 li.current').removeClass('current');
              link.closest('li.toctree-l2').addClass('current');
              link.closest('li.toctree-l3').addClass('current');
              link.closest('li.toctree-l4').addClass('current');
            }
            catch (err) {
              console.log("Error expanding nav for anchor", err);
            }
          }
        },

        hash_change = function () {
          link_scroll = true;
          win.one('hashchange', function () {
            link_scroll = false;
          });
        };

    jquery(init);

    return {
      enable: enable,
      hash_change: hash_change
    };
  }());

  return {
    sticky_nav: sticky_nav
  };
}($));
<commit_msg>added log<commit_after>function toggle_current (elem) {
  console.log("toggle_current", elem);
  var parent_li = elem.closest('li');
  parent_li.siblings('li.current').removeClass('current');
  parent_li.siblings().find('li.current').removeClass('current');
  parent_li.find('> ul li.current').removeClass('current');
  parent_li.toggleClass('current');
}

$(document).ready(function() {
  console.log("ready");
  // Nav menu link click operations
  $(document).on('click', ".nav-toc .current ul li a", function() {
    var target = $(this);
    // Close menu when you click a link.
    //// $("[data-toggle='nav-shift']").removeClass("shift");
    //// $("[data-toggle='rst-versions']").toggleClass("shift");
    // Handle dynamic display of l3 and l4 nav lists
    toggle_current(target);
    if (typeof(window.SphinxTheme) != 'undefined') {
      console.log("SphinxTheme defined");
      window.SphinxTheme.sticky_nav.hash_change();
    }
  });

  //// $(document).on('click', "[data-toggle='rst-current-version']", function() {
  ////   $("[data-toggle='rst-versions']").toggleClass("shift-up");
  //// });

  // Make tables responsive
  //// $("table.docutils:not(.field-list)").wrap("

");

  // Add expand links to all parents of nested ul
  $('.nav-toc ul').siblings('a').each(function () {
    var link = $(this);
    expand = $('');
    expand.on('click', function (ev) {
      console.log("ready click");
      toggle_current(link);
      ev.stopPropagation();
      return false;
    });
    link.prepend(expand);
  });
});

// Sphinx theme state
window.SphinxTheme = (function (jquery) {
  console.log("SphinxTheme");
  var sticky_nav = (function () {
    console.log("sticky_nav");
    var nav_bar,
        win,
        win_scroll = false,
        link_scroll = false,
        win_position = 0,

        enable = function () {
	  console.log("sticky_nav enable");
          init();
          reset();
          win.on('hashchange', reset);

          // Set scrolling
          win.on('scroll', function () {
	    console.log("sticky_nav scroll");
            if (!link_scroll) {
              win_scroll = true;
            }
          });

          setInterval(function () {
	    console.log("sticky_nav setInterval");
            if (win_scroll) {
              win_scroll = false;
              var new_win_position = win.scrollTop(),
                  nav_position = nav_bar.scrollTop(),
                  new_nav_position = nav_position + (new_win_position - win_position);
              nav_bar.scrollTop(new_nav_position);
              win_position = new_win_position;
            }
          }, 25);
        },

        init = function () {
	  console.log("sticky_nav init");
          nav_bar = jquery('nav.nav-side:first');
          win = jquery(window);
        },

        reset = function () {
	  console.log("sticky_nav reset");
          // Get anchor from URL and open up nested nav
          var anchor = encodeURI(window.location.hash);
          if (anchor) {
            try {
              var link = $('.nav-toc').find('[href="' + anchor + '"]');
              $('.nav-toc li.toctree-l1 li.current').removeClass('current');
              link.closest('li.toctree-l2').addClass('current');
              link.closest('li.toctree-l3').addClass('current');
              link.closest('li.toctree-l4').addClass('current');
            }
            catch (err) {
              console.log("Error expanding nav for anchor", err);
            }
          }
        },

        hash_change = function () {
	  console.log("sticky_nav hash_change");
          link_scroll = true;
          win.one('hashchange', function () {
	    console.log("sticky_nav hash_change one");
            link_scroll = false;
          });
        };

    jquery(init);

    return {
      enable: enable,
      hash_change: hash_change
    };
  }());

  return {
    sticky_nav: sticky_nav
  };
}($));
<|endoftext|>


<commit_before>(function() {
	function SpotifyAPI($http, $q, appSettings) {
		var self = this;
		var API_ENDPOINT = "https://api.spotify.com/v1";

		var getHeaders = function(authorization) {
			var headers = {
				"Content-Type": "application/json"
			};

			if (authorization && authorization.isValid())
				headers.Authorization = authorization.tokenType + " " + authorization.accessToken;

			return headers;
		};

		var loadAll = function(config, authorization) {
			var deferred = $q.defer();

			var load = function(config, accumulator) {
				$http(config)
					.then(function(result) {
						accumulator = accumulator.concat(result.data.items);
						if (result.data.next) {
							load({
								url: result.data.next,
								headers: config.headers
							}, accumulator);
						} else {
							deferred.resolve(accumulator);
						}
					})
					.catch(deferred.reject);
			};
			load(config, []);

			return deferred.promise;
		};

		self.loadUserId = function(authorization) {
			return $http({
				url: API_ENDPOINT + "/me",
				params: {
					fields: "id"
				},
				headers: getHeaders(authorization)
			})
				.then(function(result) {
					return result.data.id;
				});
		};

		self.loadPlaylists = function(userId, authorization) {
			return loadAll({
				url: API_ENDPOINT + "/users/" + userId + "/playlists",
				params: {
					fields: ["next", "items.id", "items.name", "items.owner.id", "items.uri"].join(","),
					limit: 50
				},
				headers: getHeaders(authorization)
			})
				.then(function(data) {
					return {
						items: data
							.filter(function(playlist) {
								return playlist.owner.id == userId;
							})
							.map(function(playlist) {
								return {
									id: playlist.id,
									name: playlist.name,
									uri: playlist.uri
								};
							})
					};
				});
		};

		self.loadTracksInPlaylist = function(userId, playlistId, authorization) {
			var snapshotId = $http({
				url: API_ENDPOINT + "/users/" + userId + "/playlists/" + playlistId,
				params: {
					fields: "snapshot_id"
				},
				headers: getHeaders(authorization)
			});
			var tracks = loadAll({
				url: API_ENDPOINT + "/users/" + userId + "/playlists/" + playlistId + "/tracks",
				params: {
					fields: ["next", "items.track.id", "items.track.uri"].join(","),
					limit: 100
				},
				headers: getHeaders(authorization)
			});

			return $q.all([snapshotId, tracks])
				.then(function(allData) {
					return {
						snapshotId: allData[0].data.snapshot_id,
						items: allData[1]
							.map(function(playlistItem) {
								return {
									id: playlistItem.track.id,
									uri: playlistItem.track.uri
								};
							})
					};
				});
		};
	}

	angular.module("spotify-playlist-deduplicator").service("spotifyAPI", SpotifyAPI);
})();
<commit_msg>Different convention for private members.<commit_after>(function() {
	function SpotifyAPI($http, $q, appSettings) {
		var self = this;
		self._API_ENDPOINT = "https://api.spotify.com/v1";

		self._getHeaders = function(authorization) {
			var headers = {
				"Content-Type": "application/json"
			};

			if (authorization && authorization.isValid())
				headers.Authorization = authorization.tokenType + " " + authorization.accessToken;

			return headers;
		};

		self._loadAll = function(config, authorization) {
			var deferred = $q.defer();

			var load = function(config, accumulator) {
				$http(config)
					.then(function(result) {
						accumulator = accumulator.concat(result.data.items);
						if (result.data.next) {
							load({
								url: result.data.next,
								headers: config.headers
							}, accumulator);
						} else {
							deferred.resolve(accumulator);
						}
					})
					.catch(deferred.reject);
			};
			load(config, []);

			return deferred.promise;
		};

		self.loadUserId = function(authorization) {
			return $http({
				url: self._API_ENDPOINT + "/me",
				params: {
					fields: "id"
				},
				headers: self._getHeaders(authorization)
			})
				.then(function(result) {
					return result.data.id;
				});
		};

		self.loadPlaylists = function(userId, authorization) {
			return self._loadAll({
				url: self._API_ENDPOINT + "/users/" + userId + "/playlists",
				params: {
					fields: ["next", "items.id", "items.name", "items.owner.id", "items.uri"].join(","),
					limit: 50
				},
				headers: self._getHeaders(authorization)
			})
				.then(function(data) {
					return {
						items: data
							.filter(function(playlist) {
								return playlist.owner.id == userId;
							})
							.map(function(playlist) {
								return {
									id: playlist.id,
									name: playlist.name,
									uri: playlist.uri
								};
							})
					};
				});
		};

		self.loadTracksInPlaylist = function(userId, playlistId, authorization) {
			var snapshotId = $http({
				url: self._API_ENDPOINT + "/users/" + userId + "/playlists/" + playlistId,
				params: {
					fields: "snapshot_id"
				},
				headers: self._getHeaders(authorization)
			});
			var tracks = self._loadAll({
				url: self._API_ENDPOINT + "/users/" + userId + "/playlists/" + playlistId + "/tracks",
				params: {
					fields: ["next", "items.track.id", "items.track.uri"].join(","),
					limit: 100
				},
				headers: self._getHeaders(authorization)
			});

			return $q.all([snapshotId, tracks])
				.then(function(allData) {
					return {
						snapshotId: allData[0].data.snapshot_id,
						items: allData[1]
							.map(function(playlistItem) {
								return {
									id: playlistItem.track.id,
									uri: playlistItem.track.uri
								};
							})
					};
				});
		};
	}

	angular.module("spotify-playlist-deduplicator").service("spotifyAPI", SpotifyAPI);
})();
<|endoftext|>


<commit_before>// Amara, universalsubtitles.org
//
// Copyright (C) 2012 Participatory Culture Foundation
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU Affero General Public License as
// published by the Free Software Foundation, either version 3 of the
// License, or (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU Affero General Public License for more details.
//
// You should have received a copy of the GNU Affero General Public License
// along with this program.  If not, see
// http://www.gnu.org/licenses/agpl-3.0.html.

goog.provide('unisubs.widget.HangingVideoTab');

/**
 * @constructor
 * @param {boolean=} opt_forAnchoring If true, will add a style that gives
 *     the tab absolute position.
 * @implements {unisubs.widget.VideoTab}
 */
unisubs.widget.HangingVideoTab = function(opt_forAnchoring) {
    goog.ui.Component.call(this);
    this.anchorElem_ = null;
    this.imageElem_ = null;
    this.spanElem_ = null;
    this.nudgeElem_ = null;
    this.nudgeSpanElem_ = null;
    this.nudgeClickCallback_ = null;
    this.shareSpanElem_ = null;
    this.shareElem_ = null;
    this.forAnchoring_ = !!opt_forAnchoring;
    this.spinnerGifURL_ = unisubs.imageAssetURL('spinner.gif');
    this.logoURL_ = unisubs.imageAssetURL('small_logo.png');
    this.imageLoader_ = new goog.net.ImageLoader();
    this.imageLoader_.addImage('spinner', this.spinnerGifURL_);
    this.imageLoader_.addImage('small_logo', this.logoURL_);
    this.imageLoader_.start();
};
goog.inherits(unisubs.widget.HangingVideoTab, goog.ui.Component);

unisubs.widget.HangingVideoTab.prototype.createDom = function() {
    unisubs.widget.HangingVideoTab.superClass_.createDom.call(this);
    goog.dom.classes.add(
        this.getElement(),
        "cleanslate", "unisubs-videoTab", 'unisubs-videoTab-' +
            (this.forAnchoring_ ? 'anchoring' : 'static'));
    var $d = goog.bind(this.getDomHelper().createDom, this.getDomHelper());
    this.imageElem_ = $d('img', {'alt': 'small logo'});
    this.spanElem_ = $d('span', 'unisubs-tabTextchoose');
    this.anchorElem_ =
        $d('a', {'className': 'unisubs-subtitleMeLink', 'href':'javascript:void(0);'},
           this.imageElem_, this.spanElem_);
    this.nudgeSpanElem_ = $d('span', 'unisubs-tabTextfinish', 'NUDGE TEXT');
    this.nudgeElem_ = $d('a', {'href':'#'}, this.nudgeSpanElem_);
    goog.dom.append(this.getElement(),
                    this.anchorElem_, this.nudgeElem_);
};

unisubs.widget.HangingVideoTab.prototype.enterDocument = function() {
    unisubs.widget.HangingVideoTab.superClass_.enterDocument.call(this);
    this.showNudge(false);
    this.getHandler().
        listen(this.nudgeElem_, 'click', this.nudgeClicked_);
};

unisubs.widget.HangingVideoTab.prototype.getAnchorElem = function() {
    return this.anchorElem_;
};

unisubs.widget.HangingVideoTab.prototype.showLoading = function() {
    this.imageElem_.src = this.spinnerGifURL_;
    goog.dom.setTextContent(this.spanElem_, "Loading");
};

/**
* Shows the error message on the video tab and never attaches
* any interaction handlers on the widget.
* @param {str=} msg An optional message explaining what went wrong
**/
unisubs.widget.HangingVideoTab.prototype.showError = function(msg) {
    this.imageElem_.src = this.logoURL_;
    goog.dom.setTextContent(this.spanElem_, msg || "Subs Unavailable");
    this.getHandler().listen(
        this.anchorElem_,
        'click',
        function(e) {
            e.preventDefault();
        });
};

/**
 * Just stops loading. If state has changed, stop loading by
 * calling showContent instead.
 *
 */
unisubs.widget.HangingVideoTab.prototype.stopLoading = function() {
    this.imageElem_.src = this.logoURL_;
    if (this.text_)
        goog.dom.setTextContent(this.spanElem_, this.text_);
};

/**
 * Stops loading, and shows text appropriate for content.
 * @param {boolean} hasSubtitles Do subs currently exist for this video?
 * @param {unisubs.widget.SubtitleState=} opt_playSubState Subtitles
 *     that are currently loaded to play in widget.
 */
unisubs.widget.HangingVideoTab.prototype.showContent = function(
    hasSubtitles, opt_playSubState)
{

    console.log(hasSubtitles);
    if (!hasSubtitles && window.VIDEO_TEAM_NAME !== '' && window.VIDEO_TEAM_WORKFLOW_ENABLED === true) {
        this.show(false);
    }

    this.imageElem_.src = this.logoURL_;
    var text;
    if (opt_playSubState)
        text = opt_playSubState.LANGUAGE ?
            unisubs.languageNameForCode(opt_playSubState.LANGUAGE) :
            "Original Language";
    else
        text = hasSubtitles ? "Select Language" : "Subtitle Me";
    this.text_ = text;
    goog.dom.setTextContent(this.spanElem_, text);
};

unisubs.widget.HangingVideoTab.prototype.nudgeClicked_ = function(e) {
    e.preventDefault();
    unisubs.Tracker.getInstance().trackPageview('Clicks_Improve_Subtitles_or_translation');
    if (this.nudgeClickCallback_)
        this.nudgeClickCallback_();
};

unisubs.widget.HangingVideoTab.prototype.showNudge = function(shows) {
    unisubs.style.setVisibility(this.nudgeElem_, shows);
    unisubs.style.setVisibility(this.nudgeSpanElem_, shows);
     if (shows){
         unisubs.style.setProperty(this.nudgeElem_, 'width', null);

     }else{
         unisubs.style.setWidth(this.nudgeElem_, 0);
     }
    return;
};

/*
 * Creates the share button next to the 'subtitle me', only if
 * this is an off site widget. When clicked will be taken to the
 * url provided.
 * @param shareURL {goog.URI} The url for the 'share' link.
 * @param newWindow {bool=} If true will open on new window.
 */
unisubs.widget.HangingVideoTab.prototype.createShareButton = function (shareURL, newWindow) {
    // users can make share button never show by setting UNISUBS_HIDESHARE.
    // see https://www.pivotaltracker.com/story/show/13700869
    if (!unisubs.isEmbeddedInDifferentDomain() || window['UNISUBS_HIDESHARE']) {
        // no point in taking to the unisubs site if we're here already
        return;
    }
    if(!this.shareElem_){
        var $d = goog.bind(this.getDomHelper().createDom, this.getDomHelper());
        this.shareSpanElem_ = $d('span', {'href':'', 'class':'unisubs-tabTextShare'}, 'Share');
        this.shareElem_ = $d('a', {'href':'', 'class':''}, this.shareSpanElem_);
        this.getElement().appendChild(this.shareElem_);
    }
    var target= newWindow ? "_blank" : "_self";
    goog.dom.setProperties(this.shareElem_, {"href": shareURL.toString(), "target":target});
};

unisubs.widget.HangingVideoTab.prototype.updateNudge = function(text, fn) {
    goog.dom.setTextContent(this.nudgeSpanElem_, text);
    this.nudgeClickCallback_ = fn;
};
unisubs.widget.HangingVideoTab.prototype.show = function(shown) {
    unisubs.style.showElement(this.getElement(), shown);
};
unisubs.widget.HangingVideoTab.prototype.disposeInternal = function() {
    unisubs.widget.HangingVideoTab.superClass_.disposeInternal.call(this);
    this.imageLoader_.dispose();
};
<commit_msg>And reverting that.<commit_after>// Amara, universalsubtitles.org
//
// Copyright (C) 2012 Participatory Culture Foundation
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU Affero General Public License as
// published by the Free Software Foundation, either version 3 of the
// License, or (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU Affero General Public License for more details.
//
// You should have received a copy of the GNU Affero General Public License
// along with this program.  If not, see
// http://www.gnu.org/licenses/agpl-3.0.html.

goog.provide('unisubs.widget.HangingVideoTab');

/**
 * @constructor
 * @param {boolean=} opt_forAnchoring If true, will add a style that gives
 *     the tab absolute position.
 * @implements {unisubs.widget.VideoTab}
 */
unisubs.widget.HangingVideoTab = function(opt_forAnchoring) {
    goog.ui.Component.call(this);
    this.anchorElem_ = null;
    this.imageElem_ = null;
    this.spanElem_ = null;
    this.nudgeElem_ = null;
    this.nudgeSpanElem_ = null;
    this.nudgeClickCallback_ = null;
    this.shareSpanElem_ = null;
    this.shareElem_ = null;
    this.forAnchoring_ = !!opt_forAnchoring;
    this.spinnerGifURL_ = unisubs.imageAssetURL('spinner.gif');
    this.logoURL_ = unisubs.imageAssetURL('small_logo.png');
    this.imageLoader_ = new goog.net.ImageLoader();
    this.imageLoader_.addImage('spinner', this.spinnerGifURL_);
    this.imageLoader_.addImage('small_logo', this.logoURL_);
    this.imageLoader_.start();
};
goog.inherits(unisubs.widget.HangingVideoTab, goog.ui.Component);

unisubs.widget.HangingVideoTab.prototype.createDom = function() {
    unisubs.widget.HangingVideoTab.superClass_.createDom.call(this);
    goog.dom.classes.add(
        this.getElement(),
        "cleanslate", "unisubs-videoTab", 'unisubs-videoTab-' +
            (this.forAnchoring_ ? 'anchoring' : 'static'));
    var $d = goog.bind(this.getDomHelper().createDom, this.getDomHelper());
    this.imageElem_ = $d('img', {'alt': 'small logo'});
    this.spanElem_ = $d('span', 'unisubs-tabTextchoose');
    this.anchorElem_ =
        $d('a', {'className': 'unisubs-subtitleMeLink', 'href':'javascript:void(0);'},
           this.imageElem_, this.spanElem_);
    this.nudgeSpanElem_ = $d('span', 'unisubs-tabTextfinish', 'NUDGE TEXT');
    this.nudgeElem_ = $d('a', {'href':'#'}, this.nudgeSpanElem_);
    goog.dom.append(this.getElement(),
                    this.anchorElem_, this.nudgeElem_);
};

unisubs.widget.HangingVideoTab.prototype.enterDocument = function() {
    unisubs.widget.HangingVideoTab.superClass_.enterDocument.call(this);
    this.showNudge(false);
    this.getHandler().
        listen(this.nudgeElem_, 'click', this.nudgeClicked_);
};

unisubs.widget.HangingVideoTab.prototype.getAnchorElem = function() {
    return this.anchorElem_;
};

unisubs.widget.HangingVideoTab.prototype.showLoading = function() {
    this.imageElem_.src = this.spinnerGifURL_;
    goog.dom.setTextContent(this.spanElem_, "Loading");
};

/**
* Shows the error message on the video tab and never attaches
* any interaction handlers on the widget.
* @param {str=} msg An optional message explaining what went wrong
**/
unisubs.widget.HangingVideoTab.prototype.showError = function(msg) {
    this.imageElem_.src = this.logoURL_;
    goog.dom.setTextContent(this.spanElem_, msg || "Subs Unavailable");
    this.getHandler().listen(
        this.anchorElem_,
        'click',
        function(e) {
            e.preventDefault();
        });
};

/**
 * Just stops loading. If state has changed, stop loading by
 * calling showContent instead.
 *
 */
unisubs.widget.HangingVideoTab.prototype.stopLoading = function() {
    this.imageElem_.src = this.logoURL_;
    if (this.text_)
        goog.dom.setTextContent(this.spanElem_, this.text_);
};

/**
 * Stops loading, and shows text appropriate for content.
 * @param {boolean} hasSubtitles Do subs currently exist for this video?
 * @param {unisubs.widget.SubtitleState=} opt_playSubState Subtitles
 *     that are currently loaded to play in widget.
 */
unisubs.widget.HangingVideoTab.prototype.showContent = function(
    hasSubtitles, opt_playSubState)
{

    if (!hasSubtitles && window.VIDEO_TEAM_NAME !== '' && window.VIDEO_TEAM_WORKFLOW_ENABLED === true) {
        this.show(false);
    }

    this.imageElem_.src = this.logoURL_;
    var text;
    if (opt_playSubState)
        text = opt_playSubState.LANGUAGE ?
            unisubs.languageNameForCode(opt_playSubState.LANGUAGE) :
            "Original Language";
    else
        text = hasSubtitles ? "Select Language" : "Subtitle Me";
    this.text_ = text;
    goog.dom.setTextContent(this.spanElem_, text);
};

unisubs.widget.HangingVideoTab.prototype.nudgeClicked_ = function(e) {
    e.preventDefault();
    unisubs.Tracker.getInstance().trackPageview('Clicks_Improve_Subtitles_or_translation');
    if (this.nudgeClickCallback_)
        this.nudgeClickCallback_();
};

unisubs.widget.HangingVideoTab.prototype.showNudge = function(shows) {
    unisubs.style.setVisibility(this.nudgeElem_, shows);
    unisubs.style.setVisibility(this.nudgeSpanElem_, shows);
     if (shows){
         unisubs.style.setProperty(this.nudgeElem_, 'width', null);

     }else{
         unisubs.style.setWidth(this.nudgeElem_, 0);
     }
    return;
};

/*
 * Creates the share button next to the 'subtitle me', only if
 * this is an off site widget. When clicked will be taken to the
 * url provided.
 * @param shareURL {goog.URI} The url for the 'share' link.
 * @param newWindow {bool=} If true will open on new window.
 */
unisubs.widget.HangingVideoTab.prototype.createShareButton = function (shareURL, newWindow) {
    // users can make share button never show by setting UNISUBS_HIDESHARE.
    // see https://www.pivotaltracker.com/story/show/13700869
    if (!unisubs.isEmbeddedInDifferentDomain() || window['UNISUBS_HIDESHARE']) {
        // no point in taking to the unisubs site if we're here already
        return;
    }
    if(!this.shareElem_){
        var $d = goog.bind(this.getDomHelper().createDom, this.getDomHelper());
        this.shareSpanElem_ = $d('span', {'href':'', 'class':'unisubs-tabTextShare'}, 'Share');
        this.shareElem_ = $d('a', {'href':'', 'class':''}, this.shareSpanElem_);
        this.getElement().appendChild(this.shareElem_);
    }
    var target= newWindow ? "_blank" : "_self";
    goog.dom.setProperties(this.shareElem_, {"href": shareURL.toString(), "target":target});
};

unisubs.widget.HangingVideoTab.prototype.updateNudge = function(text, fn) {
    goog.dom.setTextContent(this.nudgeSpanElem_, text);
    this.nudgeClickCallback_ = fn;
};
unisubs.widget.HangingVideoTab.prototype.show = function(shown) {
    unisubs.style.showElement(this.getElement(), shown);
};
unisubs.widget.HangingVideoTab.prototype.disposeInternal = function() {
    unisubs.widget.HangingVideoTab.superClass_.disposeInternal.call(this);
    this.imageLoader_.dispose();
};
<|endoftext|>


<commit_before>/*
Copyright 2016 Brazil Ltd.

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

    http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
const path = require('path');
const fs = require('fs');
const childProcess = require('child_process');

const expire = require('./lib/expire.js');
const reserve = require('./lib/reserve.js');
const updateArchive = require('./lib/updateArchive.js');
const runScheduler = require('./lib/runScheduler.js');

const configFile = path.join(
  path.dirname(require.main.filename || __filename),
  'config.json'
);
let config = {};
try {
  config = JSON.parse(fs.readFileSync(configFile));
} catch (e) {
  if (e.code === 'ENOENT') {
    console.log('%s: Create new config file.', new Date().toISOString());
    config = {
      mirakurunPath: 'http://unix:/var/run/mirakurun.sock:/',
      chinachuDir: '',
      schedulerIntervalTime: 3600000,
      archiveIntervalTime: 1800000,
      extraDiskSpace: 50000000,
      recordSeconds: 3600,
      recordRules: [],
    };
    fs.writeFileSync(configFile, JSON.stringify(config, null, '  '));
  }
}
const chinachuConfigFile = path.join(config.chinachuDir, 'config.json');
let chinachuConfig = {};
try {
  chinachuConfig = JSON.parse(fs.readFileSync(chinachuConfigFile));
} catch (e) {
  console.error('%s: %s', new Date().toISOString(), e.message);
  chinachuConfig = {};
}
const commonOptions = {
  mirakurunPath: config.mirakurunPath || chinachuConfig.mirakurunPath || 'http://unix:/var/run/mirakurun.sock:/',
  chinachuDir: config.chinachuDir,
  schedulerIntervalTime: (
    isNaN(config.schedulerIntervalTime) ? 3600000 : config.schedulerIntervalTime
  ),
  archiveIntervalTime: (
    isNaN(config.archiveIntervalTime) ? 1800000 : config.archiveIntervalTime
  ),
  extraDiskSpace: isNaN(config.extraDiskSpace) ? 50000000 : config.extraDiskSpace,
  recordSeconds: isNaN(config.recordSeconds) ? 3600 : config.recordSeconds,
  recordRules: config.recordRules || [],
  recordedDir: path.resolve(config.chinachuDir, chinachuConfig.recordedDir),
  archiveFile: path.join(config.chinachuDir, 'web/archive.json'),
  recordedFile: path.join(config.chinachuDir, 'data/recorded.json'),
  recordingFile: path.join(config.chinachuDir, 'data/recording.json'),
  reservesFile: path.join(config.chinachuDir, 'data/reserves.json'),
};

function updater() {
  updateArchive(commonOptions).then(
    () => setTimeout(updater, commonOptions.archiveIntervalTime),
    () => setTimeout(updater, commonOptions.archiveIntervalTime)
  );
}

function scheduler() {
  runScheduler(commonOptions);
  setTimeout(scheduler, commonOptions.schedulerIntervalTime);
}

function main() {
  const promises = [];

  if (commonOptions.extraDiskSpace > 0) {
    promises.push(expire(commonOptions));
  }
  if (commonOptions.recordRules.length > 0) {
    const start = (
      (Math.floor(Date.now() / commonOptions.recordSeconds / 1000) + 1) *
      commonOptions.recordSeconds * 1000
    );
    const end = start + (commonOptions.recordSeconds * 1000);
    promises.push(reserve(commonOptions, start, end));
  }
  Promise.all(promises).then(() => setTimeout(main, 60000), () => setTimeout(main, 60000));
}

try {
  childProcess.execSync(`renice -n 10 -p ${process.pid}`);
  childProcess.execSync(`ionice -c 2 -n 7 -p ${process.pid}`);
} catch (e) {
  console.error('%s: %s', new Date().toISOString(), e.message);
}

if (commonOptions.archiveIntervalTime > 0) {
  updater();
}
if (commonOptions.schedulerIntervalTime > 0) {
  scheduler();
}
main();
<commit_msg>miyoutv-agent: 各処理を独立<commit_after>/*
Copyright 2016 Brazil Ltd.

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

    http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
const path = require('path');
const fs = require('fs');
const childProcess = require('child_process');

const expire = require('./lib/expire.js');
const reserve = require('./lib/reserve.js');
const updateArchive = require('./lib/updateArchive.js');
const runScheduler = require('./lib/runScheduler.js');

const configFile = path.join(
  path.dirname(require.main.filename || __filename),
  'config.json'
);
let config = {};
try {
  config = JSON.parse(fs.readFileSync(configFile));
} catch (e) {
  if (e.code === 'ENOENT') {
    console.log('%s: Create new config file.', new Date().toISOString());
    config = {
      mirakurunPath: 'http://unix:/var/run/mirakurun.sock:/',
      chinachuDir: '',
      schedulerIntervalTime: 3600000,
      archiveIntervalTime: 1800000,
      extraDiskSpace: 50000000,
      recordSeconds: 3600,
      recordRules: [],
    };
    fs.writeFileSync(configFile, JSON.stringify(config, null, '  '));
  }
}
const chinachuConfigFile = path.join(config.chinachuDir, 'config.json');
let chinachuConfig = {};
try {
  chinachuConfig = JSON.parse(fs.readFileSync(chinachuConfigFile));
} catch (e) {
  console.error('%s: %s', new Date().toISOString(), e.message);
  chinachuConfig = {};
}
const commonOptions = {
  mirakurunPath: config.mirakurunPath || chinachuConfig.mirakurunPath || 'http://unix:/var/run/mirakurun.sock:/',
  chinachuDir: config.chinachuDir,
  schedulerIntervalTime: (
    isNaN(config.schedulerIntervalTime) ? 3600000 : config.schedulerIntervalTime
  ),
  archiveIntervalTime: (
    isNaN(config.archiveIntervalTime) ? 1800000 : config.archiveIntervalTime
  ),
  extraDiskSpace: isNaN(config.extraDiskSpace) ? 50000000 : config.extraDiskSpace,
  recordSeconds: isNaN(config.recordSeconds) ? 3600 : config.recordSeconds,
  recordRules: config.recordRules || [],
  recordedDir: path.resolve(config.chinachuDir, chinachuConfig.recordedDir),
  archiveFile: path.join(config.chinachuDir, 'web/archive.json'),
  recordedFile: path.join(config.chinachuDir, 'data/recorded.json'),
  recordingFile: path.join(config.chinachuDir, 'data/recording.json'),
  reservesFile: path.join(config.chinachuDir, 'data/reserves.json'),
};

function updater() {
  updateArchive(commonOptions).then(
    () => setTimeout(updater, commonOptions.archiveIntervalTime),
    () => setTimeout(updater, commonOptions.archiveIntervalTime)
  );
}

function scheduler() {
  runScheduler(commonOptions);
  setTimeout(scheduler, commonOptions.schedulerIntervalTime);
}

function reserver() {
  const start = (
    (Math.floor(Date.now() / commonOptions.recordSeconds / 1000) + 1) *
    commonOptions.recordSeconds * 1000
  );
  const end = start + (commonOptions.recordSeconds * 1000);
  reserve(commonOptions, start, end).then(
    () => setTimeout(reserver, 60000),
    () => setTimeout(reserver, 60000)
  );
}

function sweeper() {
  expire(commonOptions).then(
    () => setTimeout(sweeper, 60000),
    () => setTimeout(sweeper, 60000)
  );
}

function main() {
  if (commonOptions.archiveIntervalTime > 0) {
    updater();
  }
  if (commonOptions.schedulerIntervalTime > 0) {
    scheduler();
  }
  if (typeof commonOptions.recordRules === 'object' && commonOptions.recordRules.length > 0) {
    reserver();
  }
  if (commonOptions.extraDiskSpace > 0) {
    sweeper();
  }
}

try {
  childProcess.execSync(`renice -n 10 -p ${process.pid}`);
  childProcess.execSync(`ionice -c 2 -n 7 -p ${process.pid}`);
} catch (e) {
  console.error('%s: %s', new Date().toISOString(), e.message);
}
main();
<|endoftext|>