<commit_before>// Licensed to Cloudera, Inc. under one
// or more contributor license agreements.  See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership.  Cloudera, Inc. licenses this file
// to you 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.

(function ($, window, document, undefined) {

  var PLUGIN_NAME = "jHueTableExtender2";

  var DEFAULT_OPTIONS = {
    stickyHeader: true,
    stickyFirstColumn: true,
    headerSorting: true,
    mainScrollable: window,
    labels: {
      GO_TO_COLUMN: "Go to column:",
      PLACEHOLDER: "column name...",
      LOCK: "Lock row",
      UNLOCK: "Unlock row",
      ROW_DETAILS: "Show row details"
    }
  };

  function Plugin(sourceTable, options) {
    var self = this;
    self.setOptions(options);
    self.disposeFunctions = [];

    if (!self.options.stickyHeader && !self.options.stickyFirstColumn) {
      return;
    }

    self.$sourceTable = $(sourceTable);
    self.$parent = self.$sourceTable.parent();
    self.$mainScrollable = self.options.mainScrollable ? $(self.options.mainScrollable) : self.$parent;

    self.$firstCellTable = null;
    self.$firstColumnTable = null;
    self.$headerTable = null;
    self.updateHeaderWidths = $.noop;

    self.initParent();
    self.redraw();

    var widthThrottle = -1;

    if (self.options.stickyFirstColumn) {
      self.$parent.on('scroll.tableExtender', function () {
        self.repositionLeftColumn();
        if (self.options.stickyHeader) {
          window.clearTimeout(widthThrottle);
          widthThrottle = window.setTimeout(self.updateHeaderWidths.bind(self), 50);
        }
      });
    }

    if (self.options.stickyHeader) {
      self.$mainScrollable.on('scroll.tableExtender', self.repositionHeader.bind(self));
      var widthInterval = window.setInterval(self.updateHeaderWidths.bind(self), 100);
      self.disposeFunctions.push(function () {
        window.clearInterval(widthInterval);
      })
    }

    self.disposeFunctions.push(huePubSub.subscribe('table.extender.redraw', function (parentId) {
      if (parentId === self.options.parentId) {
        self.redraw();
      }
    }).remove);
  }

  Plugin.prototype.destroy = function () {
    var self = this;
    self.$parent.off('.tableExtender');
    self.$mainScrollable.off('.tableExtender');
    self.disposeFunctions.forEach(function (dispose) {
      dispose();
    })
  };

  Plugin.prototype.setOptions = function (options) {
    var self = this;
    self.options = $.extend({}, DEFAULT_OPTIONS, options);
    self.options.labels = $.extend({}, DEFAULT_OPTIONS.labels, HUE_I18n.jHueTableExtender, options ? options.labels : {})
  };

  Plugin.prototype.initParent = function () {
    var self = this;
    var parentPosition = self.$parent.css('position');
    self.$parent.css('position', (!parentPosition || parentPosition === 'static') ? 'relative' : parentPosition);
  };

  Plugin.prototype.createEmptyTableClone = function () {
    var self = this;
    var $result = $('
');
    $result.attr('class', self.$sourceTable.attr('class'));
    $result.attr('style', self.$sourceTable.attr('style'));
    $result.css({ 'position': 'absolute', 'top': 0, 'left': 0 });
    return $result;
  };

  Plugin.prototype.redraw = function () {
    var self = this;
    if (self.options.stickyHeader) {
      self.drawHeader();
    }
    if (self.options.stickyFirstColumn) {
      self.drawFirstColumn();
    }
  };

  Plugin.prototype.drawHeader = function () {
    var self = this;
    var $headerTable = self.createEmptyTableClone().css('z-index', 1);

    // Clone the header
    var $sourceHeaders = self.$sourceTable.find('thead>tr th');
    var $clonedHeaders = $sourceHeaders.clone();
    $clonedHeaders.wrapAll('

').parent().wrap('
').parent().appendTo($headerTable);

    $clonedHeaders.each(function (index, clonedTh) {
      var $clonedTh = $(clonedTh);
      var $sourceTh = $sourceHeaders.eq(index);
      $clonedTh.width($sourceTh.width());
      $clonedTh.click(function () {
        $sourceTh.click();
        window.setTimeout(self.drawHeader.bind(self), 0);
      })
    });
    $headerTable.width(self.$sourceTable.width());

    self.updateHeaderWidths = function () {
      var sourceTableWidth = self.$sourceTable.width();
      if (self.$headerTable && sourceTableWidth !== self.$headerTable.width()) {
        self.$headerTable.width(sourceTableWidth);
        $clonedHeaders.each(function (index, clonedTh) {
          var $clonedTh = $(clonedTh);
          var $sourceTh = $sourceHeaders.eq(index);
          $clonedTh.width($sourceTh.width());
        });
      }
    };

    if (self.$headerTable) {
      self.$headerTable.remove();
    }

    self.$headerTable = $headerTable;
    self.$headerTable.appendTo(self.$parent);
  };

  Plugin.prototype.lockRow = function (index) {
    var self = this;
  };

  Plugin.prototype.drawLockedRows = function () {
    var self = this;
  };

  Plugin.prototype.drawFirstColumn = function () {
    var self = this;

    var $firstColumnTable = self.createEmptyTableClone().css('z-index', 2);

    // Clone the header for the first cell
    var $sourceFirstHeader = self.$sourceTable.find('thead>tr th:eq(0)');
    var $clonedFirstHeader = $sourceFirstHeader.clone();
    $clonedFirstHeader.wrap('

').parent().wrap('
').parent().appendTo($firstColumnTable);
    $firstColumnTable.width($sourceFirstHeader.outerWidth(true));

    // Create a separate table for the upper left header cell only
    var $firstCellTable = $firstColumnTable.clone().css('z-index', 3);

    $firstCellTable.find('th').click(function () {
      $sourceFirstHeader.click();
      window.setTimeout(self.drawFirstColumn.bind(self), 0);
    });

    // Clone the cells under the header for the first column
    var $clonedFirstCells = self.$sourceTable.find("tbody>tr td:nth-child(1)").clone();
    $clonedFirstCells.wrapAll('
').parent().appendTo($firstColumnTable);
    $clonedFirstCells.wrap('
');

    var foundEmptyCell = false;
    $clonedFirstCells.each(function (index, cell) {
      var $cell = $(cell);

      if ($cell.html() === '') {
        foundEmptyCell = true;
        return false;
      }
      if (self.options.lockSelectedRow) {
        $('').addClass('fa fa-lock pointer muted').attr('title', self.options.labels.LOCK).on('click', function() {
          self.drawLockedRow(index);
        }).prependTo($cell);
      }
      $cell.addClass('lockable');
      $('').addClass('fa fa-expand pointer muted').attr('title', self.options.labels.ROW_DETAILS).on('click', function(){
        huePubSub.publish('table.row.show.details', { idx: index, table: self.$sourceTable });
      }).prependTo($cell);
    });

    if (foundEmptyCell) {
      // In IE the cell can be empty at initial render, if so we defer the rendering
      window.setTimeout(self.drawFirstColumn.bind(self), 100);
      return;
    }

    // Append the table for the first columns
    if (self.$firstColumnTable) {
      self.$firstColumnTable.remove();
    }
    self.$firstColumnTable = $firstColumnTable;
    self.$firstColumnTable.css('left', self.$parent.scrollLeft() + 'px');
    self.$firstColumnTable.appendTo(self.$parent);

    // Append the table for the first cell (header of first column)
    if (self.$firstCellTable) {
      self.$firstCellTable.remove();
    }
    self.$firstCellTable = $firstCellTable;
    self.$firstCellTable.width(self.$firstColumnTable.outerWidth(true)); // Width is only known after the first col render
    self.$firstCellTable.css('left', self.$parent.scrollLeft() + 'px');
    self.$firstCellTable.appendTo(self.$parent);
  };

  Plugin.prototype.repositionLeftColumn = function () {
    var self = this;
    if (self.$firstColumnTable) {
      self.$firstColumnTable.css('left', self.$parent.scrollLeft() + 'px');
      self.$firstCellTable.css('left', self.$parent.scrollLeft() + 'px');
    }
  };

  Plugin.prototype.repositionHeader = function () {
    var self = this;
    if (!self.$firstCellTable || !self.$headerTable) {
      return;
    }
    var diff = self.$sourceTable.offset().top - self.$mainScrollable.offset().top;

    if (self.$firstCellTable && diff < 0) {
      self.$firstCellTable.css('padding-top', -diff + 'px');
    } else if (self.$firstCellTable && self.$firstCellTable.position().top !== 0) {
      self.$firstCellTable.css('padding-top', '0');
    }

    if (self.$headerTable && diff < 0) {
      self.$headerTable.css('padding-top', -diff + 'px');
    } else if (self.$headerTable && self.$headerTable.position().top !== 0) {
      self.$headerTable.css('padding-top', '0');
    }
  };

  $.fn[PLUGIN_NAME] = function (options) {
    return this.each(function () {
      if ($.data(this, 'plugin_' + PLUGIN_NAME)) {
        $.data(this, 'plugin_' + PLUGIN_NAME).destroy();
      }
      $.data(this, 'plugin_' + PLUGIN_NAME, new Plugin(this, options));
    });
  }
})(jQuery, window, document);
<commit_msg>HUE-8398 [editor] Fix broken result table after multiple queries in embedded mode<commit_after>// Licensed to Cloudera, Inc. under one
// or more contributor license agreements.  See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership.  Cloudera, Inc. licenses this file
// to you 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.

(function ($, window, document, undefined) {

  var PLUGIN_NAME = "jHueTableExtender2";

  var DEFAULT_OPTIONS = {
    stickyHeader: true,
    stickyFirstColumn: true,
    headerSorting: true,
    mainScrollable: window,
    classToRemove: 'resultTable',
    labels: {
      GO_TO_COLUMN: "Go to column:",
      PLACEHOLDER: "column name...",
      LOCK: "Lock row",
      UNLOCK: "Unlock row",
      ROW_DETAILS: "Show row details"
    }
  };

  function Plugin(sourceTable, options) {
    var self = this;
    self.setOptions(options);
    self.disposeFunctions = [];

    if (!self.options.stickyHeader && !self.options.stickyFirstColumn) {
      return;
    }

    self.$sourceTable = $(sourceTable);
    self.$parent = self.$sourceTable.parent();
    self.$mainScrollable = self.options.mainScrollable ? $(self.options.mainScrollable) : self.$parent;

    self.$firstCellTable = null;
    self.$firstColumnTable = null;
    self.$headerTable = null;
    self.updateHeaderWidths = $.noop;

    self.initParent();
    self.redraw();

    var widthThrottle = -1;

    if (self.options.stickyFirstColumn) {
      self.$parent.on('scroll.tableExtender', function () {
        self.repositionLeftColumn();
        if (self.options.stickyHeader) {
          window.clearTimeout(widthThrottle);
          widthThrottle = window.setTimeout(self.updateHeaderWidths.bind(self), 50);
        }
      });
    }

    if (self.options.stickyHeader) {
      self.$mainScrollable.on('scroll.tableExtender', self.repositionHeader.bind(self));
      var widthInterval = window.setInterval(self.updateHeaderWidths.bind(self), 100);
      self.disposeFunctions.push(function () {
        window.clearInterval(widthInterval);
      })
    }

    self.disposeFunctions.push(huePubSub.subscribe('table.extender.redraw', function (parentId) {
      if (parentId === self.options.parentId) {
        self.redraw();
      }
    }).remove);
  }

  Plugin.prototype.destroy = function () {
    var self = this;
    $('.table-extender-header_' + self.options.parentId).remove();
    $('.table-extender-first-col-' + self.options.parentId).remove();
    $('.table-extender-first-cell-' + self.options.parentId).remove();
    self.$parent.off('.tableExtender');
    self.$mainScrollable.off('.tableExtender');
    self.disposeFunctions.forEach(function (dispose) {
      dispose();
    });
  };

  Plugin.prototype.setOptions = function (options) {
    var self = this;
    self.options = $.extend({}, DEFAULT_OPTIONS, options);
    self.options.labels = $.extend({}, DEFAULT_OPTIONS.labels, HUE_I18n.jHueTableExtender, options ? options.labels : {})
  };

  Plugin.prototype.initParent = function () {
    var self = this;
    var parentPosition = self.$parent.css('position');
    self.$parent.css('position', (!parentPosition || parentPosition === 'static') ? 'relative' : parentPosition);
  };

  Plugin.prototype.createEmptyTableClone = function () {
    var self = this;
    var $result = $('
');
    $result.attr('class', self.$sourceTable.attr('class'));
    $result.removeClass(self.options.classToRemove);
    $result.attr('style', self.$sourceTable.attr('style'));
    $result.css({ 'position': 'absolute', 'top': 0, 'left': 0 });
    return $result;
  };

  Plugin.prototype.redraw = function () {
    var self = this;
    if (self.options.stickyHeader) {
      self.drawHeader();
    }
    if (self.options.stickyFirstColumn) {
      self.drawFirstColumn();
    }
  };

  Plugin.prototype.drawHeader = function () {
    var self = this;
    var $headerTable = self.createEmptyTableClone().css('z-index', 1);
    $headerTable.addClass('table-extender-header_' + self.options.parentId);

    // Clone the header
    var $sourceHeaders = self.$sourceTable.find('thead>tr th');
    var $clonedHeaders = $sourceHeaders.clone();
    $clonedHeaders.wrapAll('

').parent().wrap('
').parent().appendTo($headerTable);

    $clonedHeaders.each(function (index, clonedTh) {
      var $clonedTh = $(clonedTh);
      var $sourceTh = $sourceHeaders.eq(index);
      $clonedTh.width($sourceTh.width());
      $clonedTh.click(function () {
        $sourceTh.click();
        window.setTimeout(self.drawHeader.bind(self), 0);
      })
    });
    $headerTable.width(self.$sourceTable.width());

    self.updateHeaderWidths = function () {
      var sourceTableWidth = self.$sourceTable.width();
      if (self.$headerTable && sourceTableWidth !== self.$headerTable.width()) {
        self.$headerTable.width(sourceTableWidth);
        $clonedHeaders.each(function (index, clonedTh) {
          var $clonedTh = $(clonedTh);
          var $sourceTh = $sourceHeaders.eq(index);
          $clonedTh.width($sourceTh.width());
        });
      }
    };

    $('.table-extender-header_' + self.options.parentId).remove();

    self.$headerTable = $headerTable;
    self.$headerTable.appendTo(self.$parent);
  };

  Plugin.prototype.lockRow = function (index) {
    var self = this;
  };

  Plugin.prototype.drawLockedRows = function () {
    var self = this;
  };

  Plugin.prototype.drawFirstColumn = function () {
    var self = this;

    var $firstColumnTable = self.createEmptyTableClone().css('z-index', 2);
    $firstColumnTable.addClass('table-extender-first-col-' + self.options.parentId);
    // Clone the header for the first cell
    var $sourceFirstHeader = self.$sourceTable.find('thead>tr th:eq(0)');
    var $clonedFirstHeader = $sourceFirstHeader.clone();
    $clonedFirstHeader.wrap('

').parent().wrap('
').parent().appendTo($firstColumnTable);
    $firstColumnTable.width($sourceFirstHeader.outerWidth(true));

    // Create a separate table for the upper left header cell only
    var $firstCellTable = $firstColumnTable.clone().css('z-index', 3);
    $firstCellTable.addClass('table-extender-first-cell-' + self.options.parentId);

    $firstCellTable.find('th').click(function () {
      $sourceFirstHeader.click();
      window.setTimeout(self.drawFirstColumn.bind(self), 0);
    });

    // Clone the cells under the header for the first column
    var $clonedFirstCells = self.$sourceTable.find("tbody>tr td:nth-child(1)").clone();
    $clonedFirstCells.wrapAll('
').parent().appendTo($firstColumnTable);
    $clonedFirstCells.wrap('
');

    var foundEmptyCell = false;
    $clonedFirstCells.each(function (index, cell) {
      var $cell = $(cell);

      if ($cell.html() === '') {
        foundEmptyCell = true;
        return false;
      }
      if (self.options.lockSelectedRow) {
        $('').addClass('fa fa-lock pointer muted').attr('title', self.options.labels.LOCK).on('click', function() {
          self.drawLockedRow(index);
        }).prependTo($cell);
      }
      $cell.addClass('lockable');
      $('').addClass('fa fa-expand pointer muted').attr('title', self.options.labels.ROW_DETAILS).on('click', function(){
        huePubSub.publish('table.row.show.details', { idx: index, table: self.$sourceTable });
      }).prependTo($cell);
    });

    if (foundEmptyCell) {
      // In IE the cell can be empty at initial render, if so we defer the rendering
      window.setTimeout(self.drawFirstColumn.bind(self), 100);
      return;
    }

    // Append the table for the first columns
    $('.table-extender-first-col-' + self.options.parentId).remove();
    self.$firstColumnTable = $firstColumnTable;
    self.$firstColumnTable.css('left', self.$parent.scrollLeft() + 'px');
    self.$firstColumnTable.appendTo(self.$parent);

    // Append the table for the first cell (header of first column)
    $('.table-extender-first-cell-' + self.options.parentId).remove();
    self.$firstCellTable = $firstCellTable;
    self.$firstCellTable.width(self.$firstColumnTable.outerWidth(true)); // Width is only known after the first col render
    self.$firstCellTable.css('left', self.$parent.scrollLeft() + 'px');
    self.$firstCellTable.appendTo(self.$parent);
  };

  Plugin.prototype.repositionLeftColumn = function () {
    var self = this;
    if (self.$firstColumnTable) {
      self.$firstColumnTable.css('left', self.$parent.scrollLeft() + 'px');
      self.$firstCellTable.css('left', self.$parent.scrollLeft() + 'px');
    }
  };

  Plugin.prototype.repositionHeader = function () {
    var self = this;
    if (!self.$firstCellTable || !self.$headerTable) {
      return;
    }
    var diff = self.$sourceTable.offset().top - self.$mainScrollable.offset().top;

    if (self.$firstCellTable && diff < 0) {
      self.$firstCellTable.css('padding-top', -diff + 'px');
    } else if (self.$firstCellTable && self.$firstCellTable.position().top !== 0) {
      self.$firstCellTable.css('padding-top', '0');
    }

    if (self.$headerTable && diff < 0) {
      self.$headerTable.css('padding-top', -diff + 'px');
    } else if (self.$headerTable && self.$headerTable.position().top !== 0) {
      self.$headerTable.css('padding-top', '0');
    }
  };

  $.fn[PLUGIN_NAME] = function (options) {
    return this.each(function () {
      if ($.data(this, 'plugin_' + PLUGIN_NAME)) {
        $.data(this, 'plugin_' + PLUGIN_NAME).destroy();
      }
      $.data(this, 'plugin_' + PLUGIN_NAME, new Plugin(this, options));
    });
  }
})(jQuery, window, document);
<|endoftext|>


<commit_before>'use strict'

const config = require('config')

if (config.specs.validateOnStart) {
	require('./validate-schemas')
}

const express = require('express')
const cors = require('cors')
const logger = require('morgan')
const session = require('express-session')
const MongoStore = require('connect-mongo')(session)
const routes = require('./routes')
const { rolesMiddleware } = require('./lib/permissions')

const app = module.exports = express()

app.settings['x-powered-by'] = false

app.use(cors({
	origin: true,
	credentials: true
}))

if (config.log.format) {
	app.use(logger(config.log.format))
}

app.use(session({
	secret: config.session.secret,
	cookie: {
		secure: true,
		httpOnly: false
	},
	resave: true,
	saveUninitialized: false,
	store: new MongoStore({
		url: config.mongo.url,
		ttl: config.session.ttl
	})
}))

app.use(rolesMiddleware)

// Dev only: to be replaced by NG2 version
app.use('/login', (req, res) => res.sendfile(__dirname + '/login.html'))

app.use('/', routes.index)
app.use('/auth', routes.auth)
app.use('/people', routes.people)
app.use('/organizations', routes.organizations)
app.use('/activities', routes.activities)
app.use('/schemas', routes.schemas)
app.use('/layouts', routes.layouts)
app.use('/enums', routes.enums)
app.use('/columns', routes.columns)
app.use('/export', routes.export)

// Error handlers
app.use(routes.errors.notFound)
app.use(routes.errors.serverError(config.http.detailedErrors))
<commit_msg>Dropping secure for cookies<commit_after>'use strict'

const config = require('config')

if (config.specs.validateOnStart) {
	require('./validate-schemas')
}

const express = require('express')
const cors = require('cors')
const logger = require('morgan')
const session = require('express-session')
const MongoStore = require('connect-mongo')(session)
const routes = require('./routes')
const { rolesMiddleware } = require('./lib/permissions')

const app = module.exports = express()

app.settings['x-powered-by'] = false

app.use(cors({
	origin: true,
	credentials: true
}))

if (config.log.format) {
	app.use(logger(config.log.format))
}

app.use(session({
	secret: config.session.secret,
	cookie: {
		httpOnly: false
	},
	resave: true,
	saveUninitialized: false,
	store: new MongoStore({
		url: config.mongo.url,
		ttl: config.session.ttl
	})
}))

app.use(rolesMiddleware)

// Dev only: to be replaced by NG2 version
app.use('/login', (req, res) => res.sendfile(__dirname + '/login.html'))

app.use('/', routes.index)
app.use('/auth', routes.auth)
app.use('/people', routes.people)
app.use('/organizations', routes.organizations)
app.use('/activities', routes.activities)
app.use('/schemas', routes.schemas)
app.use('/layouts', routes.layouts)
app.use('/enums', routes.enums)
app.use('/columns', routes.columns)
app.use('/export', routes.export)

// Error handlers
app.use(routes.errors.notFound)
app.use(routes.errors.serverError(config.http.detailedErrors))
<|endoftext|>


<commit_before>const mongoose = require('mongoose');
const express = require('express');
const bodyParser = require('body-parser');
const oauthshim = require('oauth-shim');

// ----------------------- //
// -----  Middleware ----- //
// ----------------------- //

var app = express();
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({
    extended: true
}));

// --------------------- //
// ----- OAuth API ----- //
// --------------------- //
function oauthHandler(req, res, next) {
    // Check that this is a login redirect with an access_token (not a RESTful API call via proxy)
    if (req.oauthshim &&
        req.oauthshim.redirect &&
        req.oauthshim.data &&
        req.oauthshim.data.access_token &&
        req.oauthshim.options &&
        !req.oauthshim.options.path) {}
    next()
}
app.all('/api/auth',
    oauthshim.interpret,
    oauthHandler,
    oauthshim.proxy,
    oauthshim.redirect,
    oauthshim.unhandled);

// --------------------- //
// ----- Mongo API ----- //
// --------------------- //
var domain = process.env.MONGO_DOMAIN;
mongoose.connect(
        process.env.MONGO_CONNECTION, {
        db: {
            native_parser: true
        },
        server: {
            poolSize: 5,
            reconnectTries: Number.MAX_VALUE
        },
        replset: {
            rs_name: 'rs0'
        },
        user: process.env.MONGO_USERNAME,
        pass: process.env.MONGO_PASSWORD
    });

mongoose.connection.on('connected', function() {

    // Pull OAuth Networks From Databas + Init OAuth
    mongoose.connection.db.collection("lookup_oncoscape_authentication").find().toArray(function(err, response) {
        var networks = response.map(function(v) {
            v.domain = domain;
            return v;
        });
        oauthshim.init(networks);
    });

    // Generic Method For Querying Mongo
    var processQuery = function(req, res, next, query) {

        mongoose.connection.db.collection(req.params.collection, function(err, collection) {
            if (err) {
                res.status(err.code).send(err.messages);
                res.end();
                return;
            }

            // Limits
            var limit = null
            if (query.$limit) {
                limit = query.$limit;
                delete query.$limit;
            }

            // Skip
            var skip = null;
            if (query.$skip) {
                skip = query.$skip;
                delete query.$skip;
            }

            // Fields
            var fields = {
                _id: 0
            }; // Omit Mongo IDs
            if (query.$fields) {
                query.$fields.forEach(function(field) {
                    this[field] = 1;
                }, fields);
                delete query.$fields;
            }

            // Execute
            var find = collection.find(query, fields);
            if (limit) find = find.limit(limit);
            if (skip) find = find.skip(skip);
            find.toArray(function(err, results) {
                res.send(results);
                res.end();
            });
        });
    };

    // Query using file path (client cache)
    app.get('/api/:collection/:query', function(req, res, next) {
        var query = (req.params.query) ? JSON.parse(req.params.query) : {};
        processQuery(req, res, next, query);
    });

    // Query using get querystring (no client cache)
    app.get('/api/:collection*', function(req, res, next) {
        var query = (req.query.q) ? JSON.parse(req.query.q) : {};
        processQuery(req, res, next, query);
    });

    // If Dev + Running Gulp Proxy Everything Else
    if (process.env.NODE_DEBUG=="1"){
        const httpProxy = require('http-proxy');
        var proxy = httpProxy.createProxyServer();
        app.all('/*', function(req, res, next) {
            proxy.web(req, res, {
                target: 'http://localhost:3000'
            });
        });
    }
});

// Ping Method - Used For Testing
app.get("/api/ping", function(req, res, next) {
    res.send((new Date()).toString());
    res.end();
});

// Start Listening
app.listen(process.env.NODE_PORT, function() {
    console.log("UP");
});
<commit_msg>Updated Color Options<commit_after>const mongoose = require('mongoose');
const express = require('express');
const bodyParser = require('body-parser');
const oauthshim = require('oauth-shim');

// ----------------------- //
// -----  Middleware ----- //
// ----------------------- //

var app = express();
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({
    extended: true
}));

// --------------------- //
// ----- OAuth API ----- //
// --------------------- //
function oauthHandler(req, res, next) {
    // Check that this is a login redirect with an access_token (not a RESTful API call via proxy)
    if (req.oauthshim &&
        req.oauthshim.redirect &&
        req.oauthshim.data &&
        req.oauthshim.data.access_token &&
        req.oauthshim.options &&
        !req.oauthshim.options.path) {}
    next()
}
app.all('/api/auth',
    oauthshim.interpret,
    oauthHandler,
    oauthshim.proxy,
    oauthshim.redirect,
    oauthshim.unhandled);

// --------------------- //
// ----- Mongo API ----- //
// --------------------- //
var domain = process.env.MONGO_DOMAIN;
mongoose.connect(
        "mongodb://oncoscape-dev-db1.sttrcancer.io:27017,oncoscape-dev-db2.sttrcancer.io:27017,oncoscape-dev-db3.sttrcancer.io:27017/tcga?authSource=admin",{
        //process.env.MONGO_CONNECTION, {
        db: {
            native_parser: true
        },
        server: {
            poolSize: 5,
            reconnectTries: Number.MAX_VALUE
        },
        replset: {
            rs_name: 'rs0'
        },
        user: process.env.MONGO_USERNAME,
        pass: process.env.MONGO_PASSWORD
    });

mongoose.connection.on('connected', function() {

    // Pull OAuth Networks From Databas + Init OAuth
    mongoose.connection.db.collection("lookup_oncoscape_authentication").find().toArray(function(err, response) {
        var networks = response.map(function(v) {
            v.domain = domain;
            return v;
        });
        oauthshim.init(networks);
    });

    // Generic Method For Querying Mongo
    var processQuery = function(req, res, next, query) {

        mongoose.connection.db.collection(req.params.collection, function(err, collection) {
            if (err) {
                res.status(err.code).send(err.messages);
                res.end();
                return;
            }

            // Limits
            var limit = null
            if (query.$limit) {
                limit = query.$limit;
                delete query.$limit;
            }

            // Skip
            var skip = null;
            if (query.$skip) {
                skip = query.$skip;
                delete query.$skip;
            }

            // Fields
            var fields = {
                _id: 0
            }; // Omit Mongo IDs
            if (query.$fields) {
                query.$fields.forEach(function(field) {
                    this[field] = 1;
                }, fields);
                delete query.$fields;
            }

            // Execute
            var find = collection.find(query, fields);
            if (limit) find = find.limit(limit);
            if (skip) find = find.skip(skip);
            find.toArray(function(err, results) {
                res.send(results);
                res.end();
            });
        });
    };

    // Query using file path (client cache)
    app.get('/api/:collection/:query', function(req, res, next) {
        var query = (req.params.query) ? JSON.parse(req.params.query) : {};
        processQuery(req, res, next, query);
    });

    // Query using get querystring (no client cache)
    app.get('/api/:collection*', function(req, res, next) {
        var query = (req.query.q) ? JSON.parse(req.query.q) : {};
        processQuery(req, res, next, query);
    });

    // If Dev + Running Gulp Proxy Everything Else
    if (process.env.NODE_DEBUG=="1"){
        const httpProxy = require('http-proxy');
        var proxy = httpProxy.createProxyServer();
        app.all('/*', function(req, res, next) {
            proxy.web(req, res, {
                target: 'http://localhost:3000'
            });
        });
    }
});

// Ping Method - Used For Testing
app.get("/api/ping", function(req, res, next) {
    res.send((new Date()).toString());
    res.end();
});

// Start Listening
app.listen(process.env.NODE_PORT, function() {
    console.log("UP");
});
<|endoftext|>


<commit_before>var pwm = require('pi-blaster.js');

module.exports = function LedManager(config) {
    var self = this;

    var debug = false;
    var interval = null;
    var intervalDelay = 50;
    var currentState = { red: 0, green: 0, blue: 0 };
    var queuedStates = [];
    var cycle = [];

    function process() {
        if(debug) console.log('process', queuedStates.length, cycle.length);
        if(!queuedStates.length && !cycle.length) {
            // no work to do
            if(interval) {
                if(debug) console.log('stopping interval');
                clearInterval(interval);
                interval = null;
            }
            return;
        }

        // there's work - turn on the interval if it's not on yet
        if(!interval) {
            if(debug) console.log('starting interval', queuedStates.length, cycle.length);
            interval = setInterval(process, intervalDelay);
        }

        // and now for the work...
        if(!queuedStates.length && cycle.length) {
            // nothing in the queue, but we have a cycle, so let's use that
            var nextCycle = cycle.shift();
            cycle.push(nextCycle);
            if(debug) console.log('next cycle', nextCycle);
            queueTransitionTo(nextCycle.state, nextCycle.duration);
            // now there should be queued states - let them happen
        }

        if(queuedStates.length) {
            var newState = queuedStates.shift();
            setPins(newState);
        } else {
            if(debug) console.log('odd, no work to do...');
        }
    }

    function queueTransitionTo(targetState, duration) {
        if(debug) console.log('prepping transition', currentState, targetState, duration);
        queuedStates = [];
        var steps = Math.floor(duration / intervalDelay);
        for(var i=0; i < steps; i++) {
            queuedStates.push({
                red: currentState.red + (targetState.red - currentState.red) / steps * i,
                green: currentState.green + (targetState.green - currentState.green) / steps * i,
                blue: currentState.blue + (targetState.blue - currentState.blue) / steps * i,
            });
        }
        queuedStates.push(targetState);
        if(debug) console.log('transition', duration, steps, queuedStates);
    }

    function setPins(newState) {
        if(debug) console.log('setPins', newState, currentState);
        var toSet = ['red', 'green', 'blue'].map(function(c) {
            return { pin: config[c].pin, last: currentState[c], now: newState[c] };
        });

        // var toSet = [
        //     { pin: config.red.pin, last: currentState.red, now: red },
        //     { pin: config.green.pin, last: currentState.green, now: green },
        //     { pin: config.blue.pin, last: lastBlue, now: blue },
        // ];

        // make sure we set the ones with the largest decrease in power first, largest increase in power last (to avoid over-driving our power supply due to the transition)
        toSet.forEach(function(i) { i.delta = i.now - (i.last || 0); });
        toSet.sort(function(a,b) { return a.delta < b.delta ? -1 : a.delta > b.delta ? 1 : 0; });
        toSet.forEach(function(i) { pwm.setPwm(i.pin, i.now); });

        currentState = newState;

        if(debug) console.log('set pins', toSet);
    }

    this.setColor = function setColor(red, green, blue, duration) {
        cycle = [];
        queueTransitionTo({ red: red, green: green, blue: blue}, duration || 0);
        process();
    };
    this.setCycle = function setCycle(newCycle) {
        cycle = newCycle;
        queuedStates = [];
        process();
    };
}
<commit_msg>Add brightness support<commit_after>var pwm = require('pi-blaster.js');

module.exports = function LedManager(config) {
    var self = this;

    var debug = false;
    var interval = null;
    var intervalDelay = 50;
    var currentState = { red: 0, green: 0, blue: 0 };
    var queuedStates = [];
    var cycle = [];

    function process() {
        if(debug) console.log('process', queuedStates.length, cycle.length);
        if(!queuedStates.length && !cycle.length) {
            // no work to do
            if(interval) {
                if(debug) console.log('stopping interval');
                clearInterval(interval);
                interval = null;
            }
            return;
        }

        // there's work - turn on the interval if it's not on yet
        if(!interval) {
            if(debug) console.log('starting interval', queuedStates.length, cycle.length);
            interval = setInterval(process, intervalDelay);
        }

        // and now for the work...
        if(!queuedStates.length && cycle.length) {
            // nothing in the queue, but we have a cycle, so let's use that
            var nextCycle = cycle.shift();
            cycle.push(nextCycle);
            if(debug) console.log('next cycle', nextCycle);
            queueTransitionTo(nextCycle.state, nextCycle.duration);
            // now there should be queued states - let them happen
        }

        if(queuedStates.length) {
            var newState = queuedStates.shift();
            setPins(newState);
        } else {
            if(debug) console.log('odd, no work to do...');
        }
    }

    function queueTransitionTo(targetState, duration) {
        if(debug) console.log('prepping transition', currentState, targetState, duration);
        queuedStates = [];
        var steps = Math.floor(duration / intervalDelay);
        for(var i=0; i < steps; i++) {
            queuedStates.push({
                red: currentState.red + (targetState.red - currentState.red) / steps * i,
                green: currentState.green + (targetState.green - currentState.green) / steps * i,
                blue: currentState.blue + (targetState.blue - currentState.blue) / steps * i,
            });
        }
        queuedStates.push(targetState);
        if(debug) console.log('transition', duration, steps, queuedStates);
    }

    function setPins(newState) {
        if(debug) console.log('setPins', newState, currentState);
        var toSet = ['red', 'green', 'blue'].map(function(c) {
            return { pin: config[c].pin, last: currentState[c] * config[c].brightness, now: newState[c] * config[c].brightness };
        });

        // var toSet = [
        //     { pin: config.red.pin, last: currentState.red, now: red },
        //     { pin: config.green.pin, last: currentState.green, now: green },
        //     { pin: config.blue.pin, last: lastBlue, now: blue },
        // ];

        // make sure we set the ones with the largest decrease in power first, largest increase in power last (to avoid over-driving our power supply due to the transition)
        toSet.forEach(function(i) { i.delta = i.now - (i.last || 0); });
        toSet.sort(function(a,b) { return a.delta < b.delta ? -1 : a.delta > b.delta ? 1 : 0; });
        toSet.forEach(function(i) { pwm.setPwm(i.pin, i.now); });

        currentState = newState;

        if(debug) console.log('set pins', toSet);
    }

    this.setColor = function setColor(red, green, blue, duration) {
        cycle = [];
        queueTransitionTo({ red: red, green: green, blue: blue}, duration || 0);
        process();
    };
    this.setCycle = function setCycle(newCycle) {
        cycle = newCycle;
        queuedStates = [];
        process();
    };
}
<|endoftext|>


<commit_before>var path = require("path");
var express = require("express");
var app = express();

var staticRouteMappings = [
  { directory: path.join(__dirname, "..", "client"), url: "/public" }
];

app.set("port", (process.env.PORT || 3000));
staticRouteMappings.forEach(function(mapping) {
  app.use(mapping.url, express.static(mapping.directory));
});

console.log("/public ==", publicPath);

// TODO Define specific routes.

// From all other routes we return index.html for now...
app.get("/", function(request, response) {
    var indexHtml = path.join(process.env.PWD, "client", "html", "index.html");
    response.sendFile(indexHtml);
});

app.listen(app.get("port"), function() {
    console.log("Node app is running at localhost:" + app.get('port'));
});<commit_msg>Server side configurations in place after the release location came about<commit_after>var path = require("path");
var express = require("express");
var app = express();

var releaseDirectory = path.join(__dirname, "..");

// creating a iterable list of static url we can safely use from the browser without express involving itself
// with them too much
var staticRouteMappings = [
  { directory: path.join(releaseDirectory, "client"), url: "/public" }
];

app.set("port", (process.env.PORT || 3000));
staticRouteMappings.forEach(function(mapping) {
  app.use(mapping.url, express.static(mapping.directory));
});

// From all other routes we return index.html for now...
app.get("/", function(request, response) {
    var indexHtml = path.join(releaseDirectory, "client", "html", "index.html");
    response.sendFile(indexHtml);
});

app.listen(app.get("port"), function() {
    console.log("Node app is running at localhost:" + app.get('port'));
});<|endoftext|>


<commit_before>'use strict';

var $ = require('preconditions').singleton();
var _ = require('lodash');
var async = require('async');
var log = require('npmlog');
log.debug = log.verbose;

var BlockchainExplorer = require('./blockchainexplorer');
var Storage = require('./storage');
var MessageBroker = require('./messagebroker');
var Lock = require('./lock');

var Notification = require('./model/notification');

var WalletService = require('./server');
var Constants = require('./common/constants');

function BlockchainMonitor() {};

BlockchainMonitor.prototype.start = function(opts, cb) {
  opts = opts || {};

  var self = this;

  async.parallel([

    function(done) {
      self.explorers = {
        btc: {},
        bch: {},
      };

      var coinNetworkPairs = [];
      _.each(_.values(Constants.COINS), function(coin) {
        _.each(_.values(Constants.NETWORKS), function(network) {
          coinNetworkPairs.push({
            coin: coin,
            network: network
          });
        });
      });
      _.each(coinNetworkPairs, function(pair) {
        var explorer;
        if (opts.blockchainExplorers && opts.blockchainExplorers[pair.coin] && opts.blockchainExplorers[pair.coin][pair.network]) {
          explorer = opts.blockchainExplorers[pair.coin][pair.network];
        } else {
          var config = {}
          if (opts.blockchainExplorerOpts && opts.blockchainExplorerOpts[pair.coin] && opts.blockchainExplorerOpts[pair.coin][pair.network]) {
            config = opts.blockchainExplorerOpts[pair.coin][pair.network];
          } else {
            return;
          }
          var explorer = new BlockchainExplorer({
            provider: config.provider,
            coin: pair.coin,
            network: pair.network,
            url: config.url,
            userAgent: WalletService.getServiceVersion(),
          });
        }
        $.checkState(explorer);
        self._initExplorer(pair.coin, pair.network, explorer);
        self.explorers[pair.coin][pair.network] = explorer;
      });
      done();
    },
    function(done) {
      if (opts.storage) {
        self.storage = opts.storage;
        done();
      } else {
        self.storage = new Storage();
        self.storage.connect(opts.storageOpts, done);
      }
    },
    function(done) {
      self.messageBroker = opts.messageBroker || new MessageBroker(opts.messageBrokerOpts);
      done();
    },
    function(done) {
      self.lock = opts.lock || new Lock(opts.lockOpts);
      done();
    },
  ], function(err) {
    if (err) {
      log.error(err);
    }
    return cb(err);
  });
};

BlockchainMonitor.prototype._initExplorer = function(coin, network, explorer) {
  var self = this;

  var socket = explorer.initSocket();

  socket.on('connect', function() {
    log.info('Connected to ' + explorer.getConnectionInfo());
    socket.emit('subscribe', 'inv');
  });
  socket.on('connect_error', function() {
    log.error('Error connecting to ' + explorer.getConnectionInfo());
  });
  socket.on('tx', _.bind(self._handleIncomingTx, self, coin, network));
  socket.on('block', _.bind(self._handleNewBlock, self, coin, network));
};

BlockchainMonitor.prototype._handleThirdPartyBroadcasts = function(data, processIt) {
  var self = this;
  if (!data || !data.txid) return;

  self.storage.fetchTxByHash(data.txid, function(err, txp) {
    if (err) {
      log.error('Could not fetch tx from the db');
      return;
    }
    if (!txp || txp.status != 'accepted') return;

    var walletId = txp.walletId;

    if (!processIt) {
      log.info('Detected broadcast ' + data.txid + ' of an accepted txp [' + txp.id + '] for wallet ' + walletId + ' [' + txp.amount + 'sat ]');
      return setTimeout(self._handleThirdPartyBroadcasts.bind(self, data, true), 20 * 1000);
    }

    log.info('Processing accepted txp [' + txp.id + '] for wallet ' + walletId + ' [' + txp.amount + 'sat ]');

    txp.setBroadcasted();

    self.storage.softResetTxHistoryCache(walletId, function() {
      self.storage.storeTx(self.walletId, txp, function(err) {
        if (err)
          log.error('Could not save TX');

        var args = {
          txProposalId: txp.id,
          txid: data.txid,
          amount: txp.getTotalAmount(),
        };

        var notification = Notification.create({
          type: 'NewOutgoingTxByThirdParty',
          data: args,
          walletId: walletId,
        });
        self._storeAndBroadcastNotification(notification);
      });
    });
  });
};

BlockchainMonitor.prototype._handleIncomingPayments = function(coin, network, data) {
  var self = this;
  if (!data || !data.vout) return;

  var outs = _.compact(_.map(data.vout, function(v) {
    var addr = _.keys(v)[0];

    return {
      address: addr,
      amount: +v[addr]
    };
  }));
  if (_.isEmpty(outs)) return;

  async.each(outs, function(out, next) {
    self.storage.fetchAddressByCoin(coin, out.address, function(err, address) {
      if (err) {
        log.error('Could not fetch addresses from the db');
        return next(err);
      }
      if (!address || address.isChange) return next();

      var walletId = address.walletId;
      log.info('Incoming tx for wallet ' + walletId + ' [' + out.amount + 'sat -> ' + out.address + ']');

      var fromTs = Date.now() - 24 * 3600 * 1000;
      self.storage.fetchNotifications(walletId, null, fromTs, function(err, notifications) {
        if (err) return next(err);
        var alreadyNotified = _.any(notifications, function(n) {
          return n.type == 'NewIncomingTx' && n.data && n.data.txid == data.txid;
        });
        if (alreadyNotified) {
          log.info('The incoming tx ' + data.txid + ' was already notified');
          return next();
        }

        var notification = Notification.create({
          type: 'NewIncomingTx',
          data: {
            txid: data.txid,
            address: out.address,
            amount: out.amount,
          },
          walletId: walletId,
        });
        self.storage.softResetTxHistoryCache(walletId, function() {
          self._updateAddressesWithBalance(address, function() {
            self._storeAndBroadcastNotification(notification, next);
          });
        });
      });
    });
  }, function(err) {
    return;
  });
};

BlockchainMonitor.prototype._updateAddressesWithBalance = function(address, cb) {

  var self = this;

  self.storage.fetchAddressesWithBalance(address.walletId, function(err, result) {
    if (err) {
      log.warn('Could not update wallet cache', err);
      return cb(err);
    }
    var addresses = _.map(result,'address');

    if (_.indexOf(addresses, address.address) >= 0) {
      return cb();
    }

    addresses.push(address.address);
    log.info('Activating address ' + address.address);
    self.storage.storeAddressesWithBalance(address.walletId, addresses, function(err) {
      if (err) {
        log.warn('Could not update wallet cache', err);
      }
      return cb(err);
    });
  });
};

BlockchainMonitor.prototype._handleIncomingTx = function(coin, network, data) {
  this._handleThirdPartyBroadcasts(data);
  this._handleIncomingPayments(coin, network, data);
};

BlockchainMonitor.prototype._notifyNewBlock = function(coin, network, hash) {
  var self = this;

  log.info('New ' + network + ' block: ' + hash);
  var notification = Notification.create({
    type: 'NewBlock',
    walletId: network, // use network name as wallet id for global notifications
    data: {
      hash: hash,
      coin: coin,
      network: network,
    },
  });

  self.storage.softResetAllTxHistoryCache(function() {
    self._storeAndBroadcastNotification(notification, function(err) {
      return;
    });
  });
};

BlockchainMonitor.prototype._handleTxConfirmations = function(coin, network, hash) {
  var self = this;

  function processTriggeredSubs(subs, cb) {
    async.each(subs, function(sub) {
      log.info('New tx confirmation ' + sub.txid);
      sub.isActive = false;
      self.storage.storeTxConfirmationSub(sub, function(err) {
        if (err) return cb(err);

        var notification = Notification.create({
          type: 'TxConfirmation',
          walletId: sub.walletId,
          creatorId: sub.copayerId,
          data: {
            txid: sub.txid,
            coin: coin,
            network: network,
            // TODO: amount
          },
        });
        self._storeAndBroadcastNotification(notification, cb);
      });
    });
  };

  var explorer = self.explorers[coin][network];
  if (!explorer) return;

  explorer.getTxidsInBlock(hash, function(err, txids) {
    if (err) {
      log.error('Could not fetch txids from block ' + hash, err);
      return;
    }

    self.storage.fetchActiveTxConfirmationSubs(null, function(err, subs) {
      if (err) return;
      if (_.isEmpty(subs)) return;
      var indexedSubs = _.indexBy(subs, 'txid');
      var triggered = [];
      _.each(txids, function(txid) {
        if (indexedSubs[txid]) triggered.push(indexedSubs[txid]);
      });
      processTriggeredSubs(triggered, function(err) {
        if (err) {
          log.error('Could not process tx confirmations', err);
        }
        return;
      });
    });
  });
};

BlockchainMonitor.prototype._handleNewBlock = function(coin, network, hash) {
  this._notifyNewBlock(coin, network, hash);
  this._handleTxConfirmations(coin, network, hash);
};

BlockchainMonitor.prototype._storeAndBroadcastNotification = function(notification, cb) {
  var self = this;

  self.storage.storeNotification(notification.walletId, notification, function() {
    self.messageBroker.send(notification)
    if (cb) return cb();
  });
};

module.exports = BlockchainMonitor;
<commit_msg>translate bch addr from monitor<commit_after>'use strict';

var $ = require('preconditions').singleton();
var _ = require('lodash');
var async = require('async');
var log = require('npmlog');
log.debug = log.verbose;

var BlockchainExplorer = require('./blockchainexplorer');
var Storage = require('./storage');
var MessageBroker = require('./messagebroker');
var Lock = require('./lock');

var Notification = require('./model/notification');

var WalletService = require('./server');
var Common = require('./common');
var Constants = Common.Constants;
var Utils = Common.Utils;

function BlockchainMonitor() {};

BlockchainMonitor.prototype.start = function(opts, cb) {
  opts = opts || {};

  var self = this;

  async.parallel([

    function(done) {
      self.explorers = {
        btc: {},
        bch: {},
      };

      var coinNetworkPairs = [];
      _.each(_.values(Constants.COINS), function(coin) {
        _.each(_.values(Constants.NETWORKS), function(network) {
          coinNetworkPairs.push({
            coin: coin,
            network: network
          });
        });
      });
      _.each(coinNetworkPairs, function(pair) {
        var explorer;
        if (opts.blockchainExplorers && opts.blockchainExplorers[pair.coin] && opts.blockchainExplorers[pair.coin][pair.network]) {
          explorer = opts.blockchainExplorers[pair.coin][pair.network];
        } else {
          var config = {}
          if (opts.blockchainExplorerOpts && opts.blockchainExplorerOpts[pair.coin] && opts.blockchainExplorerOpts[pair.coin][pair.network]) {
            config = opts.blockchainExplorerOpts[pair.coin][pair.network];
          } else {
            return;
          }
          var explorer = new BlockchainExplorer({
            provider: config.provider,
            coin: pair.coin,
            network: pair.network,
            url: config.url,
            userAgent: WalletService.getServiceVersion(),
          });
        }
        $.checkState(explorer);
        self._initExplorer(pair.coin, pair.network, explorer);
        self.explorers[pair.coin][pair.network] = explorer;
      });
      done();
    },
    function(done) {
      if (opts.storage) {
        self.storage = opts.storage;
        done();
      } else {
        self.storage = new Storage();
        self.storage.connect(opts.storageOpts, done);
      }
    },
    function(done) {
      self.messageBroker = opts.messageBroker || new MessageBroker(opts.messageBrokerOpts);
      done();
    },
    function(done) {
      self.lock = opts.lock || new Lock(opts.lockOpts);
      done();
    },
  ], function(err) {
    if (err) {
      log.error(err);
    }
    return cb(err);
  });
};

BlockchainMonitor.prototype._initExplorer = function(coin, network, explorer) {
  var self = this;

  var socket = explorer.initSocket();

  socket.on('connect', function() {
    log.info('Connected to ' + explorer.getConnectionInfo());
    socket.emit('subscribe', 'inv');
  });
  socket.on('connect_error', function() {
    log.error('Error connecting to ' + explorer.getConnectionInfo());
  });
  socket.on('tx', _.bind(self._handleIncomingTx, self, coin, network));
  socket.on('block', _.bind(self._handleNewBlock, self, coin, network));
};

BlockchainMonitor.prototype._handleThirdPartyBroadcasts = function(data, processIt) {
  var self = this;
  if (!data || !data.txid) return;

  self.storage.fetchTxByHash(data.txid, function(err, txp) {
    if (err) {
      log.error('Could not fetch tx from the db');
      return;
    }
    if (!txp || txp.status != 'accepted') return;

    var walletId = txp.walletId;

    if (!processIt) {
      log.info('Detected broadcast ' + data.txid + ' of an accepted txp [' + txp.id + '] for wallet ' + walletId + ' [' + txp.amount + 'sat ]');
      return setTimeout(self._handleThirdPartyBroadcasts.bind(self, data, true), 20 * 1000);
    }

    log.info('Processing accepted txp [' + txp.id + '] for wallet ' + walletId + ' [' + txp.amount + 'sat ]');

    txp.setBroadcasted();

    self.storage.softResetTxHistoryCache(walletId, function() {
      self.storage.storeTx(self.walletId, txp, function(err) {
        if (err)
          log.error('Could not save TX');

        var args = {
          txProposalId: txp.id,
          txid: data.txid,
          amount: txp.getTotalAmount(),
        };

        var notification = Notification.create({
          type: 'NewOutgoingTxByThirdParty',
          data: args,
          walletId: walletId,
        });
        self._storeAndBroadcastNotification(notification);
      });
    });
  });
};

BlockchainMonitor.prototype._handleIncomingPayments = function(coin, network, data) {
  var self = this;
  if (!data || !data.vout) return;

  var outs = _.compact(_.map(data.vout, function(v) {
    var addr = _.keys(v)[0];

    // This is because a bug on insight, that always return no copay addr
    if (coin == 'bch' && Utils.getAddressCoin(addr) !='bch') {
      addr = Utils.translateAddress(addr, coin);
console.log('[blockchainmonitor.js.164:addr:]',addr); //TODO
    }

    return {
      address: addr,
      amount: +v[addr]
    };
  }));
  if (_.isEmpty(outs)) return;

  async.each(outs, function(out, next) {

    // toDo, remove coin  here: no more same address for diff coins
    self.storage.fetchAddressByCoin(coin, out.address, function(err, address) {
      if (err) {
        log.error('Could not fetch addresses from the db');
        return next(err);
      }
      if (!address || address.isChange) return next();

      var walletId = address.walletId;
      log.info('Incoming tx for wallet ' + walletId + ' [' + out.amount + 'sat -> ' + out.address + ']');

      var fromTs = Date.now() - 24 * 3600 * 1000;
      self.storage.fetchNotifications(walletId, null, fromTs, function(err, notifications) {
        if (err) return next(err);
        var alreadyNotified = _.any(notifications, function(n) {
          return n.type == 'NewIncomingTx' && n.data && n.data.txid == data.txid;
        });
        if (alreadyNotified) {
          log.info('The incoming tx ' + data.txid + ' was already notified');
          return next();
        }

        var notification = Notification.create({
          type: 'NewIncomingTx',
          data: {
            txid: data.txid,
            address: out.address,
            amount: out.amount,
          },
          walletId: walletId,
        });
        self.storage.softResetTxHistoryCache(walletId, function() {
          self._updateAddressesWithBalance(address, function() {
            self._storeAndBroadcastNotification(notification, next);
          });
        });
      });
    });
  }, function(err) {
    return;
  });
};

BlockchainMonitor.prototype._updateAddressesWithBalance = function(address, cb) {

  var self = this;

  self.storage.fetchAddressesWithBalance(address.walletId, function(err, result) {
    if (err) {
      log.warn('Could not update wallet cache', err);
      return cb(err);
    }
    var addresses = _.map(result,'address');

    if (_.indexOf(addresses, address.address) >= 0) {
      return cb();
    }

    addresses.push(address.address);
    log.info('Activating address ' + address.address);
    self.storage.storeAddressesWithBalance(address.walletId, addresses, function(err) {
      if (err) {
        log.warn('Could not update wallet cache', err);
      }
      return cb(err);
    });
  });
};

BlockchainMonitor.prototype._handleIncomingTx = function(coin, network, data) {
  this._handleThirdPartyBroadcasts(data);
  this._handleIncomingPayments(coin, network, data);
};

BlockchainMonitor.prototype._notifyNewBlock = function(coin, network, hash) {
  var self = this;

  log.info('New ' + network + ' block: ' + hash);
  var notification = Notification.create({
    type: 'NewBlock',
    walletId: network, // use network name as wallet id for global notifications
    data: {
      hash: hash,
      coin: coin,
      network: network,
    },
  });

  self.storage.softResetAllTxHistoryCache(function() {
    self._storeAndBroadcastNotification(notification, function(err) {
      return;
    });
  });
};

BlockchainMonitor.prototype._handleTxConfirmations = function(coin, network, hash) {
  var self = this;

  function processTriggeredSubs(subs, cb) {
    async.each(subs, function(sub) {
      log.info('New tx confirmation ' + sub.txid);
      sub.isActive = false;
      self.storage.storeTxConfirmationSub(sub, function(err) {
        if (err) return cb(err);

        var notification = Notification.create({
          type: 'TxConfirmation',
          walletId: sub.walletId,
          creatorId: sub.copayerId,
          data: {
            txid: sub.txid,
            coin: coin,
            network: network,
            // TODO: amount
          },
        });
        self._storeAndBroadcastNotification(notification, cb);
      });
    });
  };

  var explorer = self.explorers[coin][network];
  if (!explorer) return;

  explorer.getTxidsInBlock(hash, function(err, txids) {
    if (err) {
      log.error('Could not fetch txids from block ' + hash, err);
      return;
    }

    self.storage.fetchActiveTxConfirmationSubs(null, function(err, subs) {
      if (err) return;
      if (_.isEmpty(subs)) return;
      var indexedSubs = _.indexBy(subs, 'txid');
      var triggered = [];
      _.each(txids, function(txid) {
        if (indexedSubs[txid]) triggered.push(indexedSubs[txid]);
      });
      processTriggeredSubs(triggered, function(err) {
        if (err) {
          log.error('Could not process tx confirmations', err);
        }
        return;
      });
    });
  });
};

BlockchainMonitor.prototype._handleNewBlock = function(coin, network, hash) {
  this._notifyNewBlock(coin, network, hash);
  this._handleTxConfirmations(coin, network, hash);
};

BlockchainMonitor.prototype._storeAndBroadcastNotification = function(notification, cb) {
  var self = this;

  self.storage.storeNotification(notification.walletId, notification, function() {
    self.messageBroker.send(notification)
    if (cb) return cb();
  });
};

module.exports = BlockchainMonitor;
<|endoftext|>


<commit_before>'use strict';

var express = require('express');
var path = require('path');
var favicon = require('serve-favicon');
var logger = require('morgan');
var cookieParser = require('cookie-parser');
var bodyParser = require('body-parser');
var config = require('./config');
var secrets = require('./secrets');
var mongoose = require('mongoose');
var session = require('express-session');
var MongoStore = require('connect-mongo')(session);
var passport = require('passport');
var GoogleStrategy = require('passport-google-oauth').OAuth2Strategy;
var categories = require('./routes/categories');
var components = require('./routes/components');
var user = require('./routes/user');
var search = require('./routes/search');
var User = require('./models/User')
var port = process.env.PORT || '3000';
var http = require('http');

// mongoose.connect(config.db.mongodb);

var app = express();
app.use(bodyParser.json()); // support json encoded bodies
app.use(bodyParser.urlencoded({ extended: true })); // support encoded bodies
app.use('/docs', express.static(path.join(__dirname, 'docs')));

app.use(session({
  store: new MongoStore({ mongooseConnection: mongoose.connection }),
  secret: secrets.session.secret,
  saveUninitialized: false, // don't create session until something stored
  resave: false //don't save session if unmodified
}));

passport.use(new GoogleStrategy({
    clientID: secrets.google.clientID,
    clientSecret: secrets.google.clientSecret,
    callbackURL: secrets.google.callbackURL
  },
  function(accessToken, refreshToken, profile, done) {
    var userProfile = { displayName: profile.displayName };

    if (profile.emails && profile.emails.length > 0) {
      userProfile.email = profile.emails[0].value;

      // TODO: require a string helper lib
      if (userProfile.email.indexOf('@theappbusiness.com', userProfile.email.length - '@theappbusiness.com'.length) < 1) {
        return done(null, false, { message: 'Only TAB users are permitted for now' })
      }
    } else {
      return done(null, false, { message: 'Failed to determine users email address' });
    }

    if (profile.photos && profile.photos.length > 0) {
      userProfile.photo = profile.photos[0].value;
    }

    User.findOrCreate({ googleId: profile.id }, userProfile, function (err, user) {
      return done(err, user);
    });
  }
));

passport.serializeUser(function(user, done) {
  return done(null, user.googleId); //this is the 'user' property saved in req.session.passport.user
});

passport.deserializeUser(function (id, done) {
  return User.findOne({ googleId: id }, function (error, user) {
    return done(error, user);
  });
});

app.use(passport.initialize());
app.use(passport.session());

app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'jade');

// uncomment after placing your favicon in /public
//app.use(favicon(__dirname + '/public/favicon.ico'));
app.use(logger('dev'));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, '/../build')));

app.use(function(req, res, next) {
  res.header('Access-Control-Allow-Origin', '*');
  res.header('Access-Control-Allow-Methods', 'GET,PUT,POST,DELETE,PATCH');
  res.header('Access-Control-Allow-Headers', 'Content-Type');
  next();
});

// app.use('/categories', ensureApiAuthenticated, categories);
// app.use('/components', ensureApiAuthenticated, components);
// app.use('/user', ensureApiAuthenticated, user);
app.use('/categories', categories);
app.use('/components', components);

app.use('/search', ensureApiAuthenticated, search);

app.get('/auth/google', passport.authenticate('google', { scope: ['profile', 'email'] }));

app.get('/auth/google/callback',
  passport.authenticate('google', { failureRedirect: '/login' }),
  function(req, res) {
    // Successful authentication, redirect home.
    res.redirect('/');
  }
);

app.get('/logout', function(req, res) {
    req.logout();
    res.redirect('/');
});

// Serve index.html for all routes to leave routing up to react-router
// app.all('/*', function(req, res) {
//  res.sendFile('index.html', { root: 'build' });
// });

// catch 404 and forward to error handler
app.use(function(req, res, next) {
  var err = new Error('Not Found');
  err.status = 404;
  next(err);
});

// error handlers

// development error handler
// will print stacktrace
if (app.get('env') === 'development') {
  app.use(function(err, req, res, next) {
    res.status(err.status || 500);
    res.render('error', {
      message: err.message,
      error: err
    });
  });
}

// production error handler
// no stacktraces leaked to user
app.use(function(err, req, res, next) {
  res.status(err.status || 500);
  res.render('error', {
    message: err.message,
    error: {}
  });
});

// Simple route middleware to ensure user is authenticated.
//   Use this route middleware on any resource that needs to be protected.  If
//   the request is authenticated (typically via a persistent login session),
//   the request will proceed.  Otherwise, the user will be redirected to the
//   login page.
function ensureApiAuthenticated(req, res, next) {
  if (req.isAuthenticated()) {
    return next();
  }

  res.status(401);
  res.send();
}

app.set('port', port);

var server = http.createServer(app);

server.listen(port);

console.log('Running the server on ' + port);

module.exports = app;
<commit_msg>getting secret keys from environment variables<commit_after>'use strict';

var express = require('express');
var path = require('path');
var favicon = require('serve-favicon');
var logger = require('morgan');
var cookieParser = require('cookie-parser');
var bodyParser = require('body-parser');
var config = require('./config');
var mongoose = require('mongoose');
var session = require('express-session');
var MongoStore = require('connect-mongo')(session);
var passport = require('passport');
var GoogleStrategy = require('passport-google-oauth').OAuth2Strategy;
var categories = require('./routes/categories');
var components = require('./routes/components');
var user = require('./routes/user');
var search = require('./routes/search');
var User = require('./models/User')
var port = process.env.PORT || '3000';
var http = require('http');
var secrets;
var googleClientId;
var googleClientSecret;
var googleCallbackURL;
var sessionSecret;

if (process.ENV.GOOGLE_CLIENT_ID) {
  googleClientId = process.ENV.GOOGLE_CLIENT_ID;
  googleClientSecret = process.ENV.GOOGLE_CLIENT_SECRET;
  googleCallbackURL = process.ENV.GOOGLE_CALLBACK_URL;
  sessionSecret = process.ENV.SESSION_SECRET;
} else {
  secrets = require('./secrets');
  googleClientId = secrets.google.clientID;
  googleClientSecret = secrets.google.clientSecret;
  googleCallbackURL = secrets.google.callbackURL;
  sessionSecret = secrets.session.secret;
}

// mongoose.connect(config.db.mongodb);

var app = express();
app.use(bodyParser.json()); // support json encoded bodies
app.use(bodyParser.urlencoded({ extended: true })); // support encoded bodies
app.use('/docs', express.static(path.join(__dirname, 'docs')));

app.use(session({
  store: new MongoStore({ mongooseConnection: mongoose.connection }),
  secret: sessionSecret,
  saveUninitialized: false, // don't create session until something stored
  resave: false //don't save session if unmodified
}));

passport.use(new GoogleStrategy({
    clientID: googleClientId,
    clientSecret: googleClientSecret,
    callbackURL: googleCallbackURL
  },
  function(accessToken, refreshToken, profile, done) {
    var userProfile = { displayName: profile.displayName };

    if (profile.emails && profile.emails.length > 0) {
      userProfile.email = profile.emails[0].value;

      // TODO: require a string helper lib
      if (userProfile.email.indexOf('@theappbusiness.com', userProfile.email.length - '@theappbusiness.com'.length) < 1) {
        return done(null, false, { message: 'Only TAB users are permitted for now' })
      }
    } else {
      return done(null, false, { message: 'Failed to determine users email address' });
    }

    if (profile.photos && profile.photos.length > 0) {
      userProfile.photo = profile.photos[0].value;
    }

    User.findOrCreate({ googleId: profile.id }, userProfile, function (err, user) {
      return done(err, user);
    });
  }
));

passport.serializeUser(function(user, done) {
  return done(null, user.googleId); //this is the 'user' property saved in req.session.passport.user
});

passport.deserializeUser(function (id, done) {
  return User.findOne({ googleId: id }, function (error, user) {
    return done(error, user);
  });
});

app.use(passport.initialize());
app.use(passport.session());

app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'jade');

// uncomment after placing your favicon in /public
//app.use(favicon(__dirname + '/public/favicon.ico'));
app.use(logger('dev'));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, '/../build')));

app.use(function(req, res, next) {
  res.header('Access-Control-Allow-Origin', '*');
  res.header('Access-Control-Allow-Methods', 'GET,PUT,POST,DELETE,PATCH');
  res.header('Access-Control-Allow-Headers', 'Content-Type');
  next();
});

// app.use('/categories', ensureApiAuthenticated, categories);
// app.use('/components', ensureApiAuthenticated, components);
// app.use('/user', ensureApiAuthenticated, user);
app.use('/categories', categories);
app.use('/components', components);

app.use('/search', ensureApiAuthenticated, search);

app.get('/auth/google', passport.authenticate('google', { scope: ['profile', 'email'] }));

app.get('/auth/google/callback',
  passport.authenticate('google', { failureRedirect: '/login' }),
  function(req, res) {
    // Successful authentication, redirect home.
    res.redirect('/');
  }
);

app.get('/logout', function(req, res) {
    req.logout();
    res.redirect('/');
});

// Serve index.html for all routes to leave routing up to react-router
// app.all('/*', function(req, res) {
//  res.sendFile('index.html', { root: 'build' });
// });

// catch 404 and forward to error handler
app.use(function(req, res, next) {
  var err = new Error('Not Found');
  err.status = 404;
  next(err);
});

// error handlers

// development error handler
// will print stacktrace
if (app.get('env') === 'development') {
  app.use(function(err, req, res, next) {
    res.status(err.status || 500);
    res.render('error', {
      message: err.message,
      error: err
    });
  });
}

// production error handler
// no stacktraces leaked to user
app.use(function(err, req, res, next) {
  res.status(err.status || 500);
  res.render('error', {
    message: err.message,
    error: {}
  });
});

// Simple route middleware to ensure user is authenticated.
//   Use this route middleware on any resource that needs to be protected.  If
//   the request is authenticated (typically via a persistent login session),
//   the request will proceed.  Otherwise, the user will be redirected to the
//   login page.
function ensureApiAuthenticated(req, res, next) {
  if (req.isAuthenticated()) {
    return next();
  }

  res.status(401);
  res.send();
}

app.set('port', port);

var server = http.createServer(app);

server.listen(port);

console.log('Running the server on ' + port);

module.exports = app;
<|endoftext|>


<commit_before>var express = require('express');
var path = require('path');

var app = express();
var router = express.Router();

// If env is development, use webpack hot reloading
var env = process.env.NODE_ENV
if (!env || env === 'dev' || env === 'development') {
    console.log('DEVOLOPMENT ENVIRONMENT: Turning on WebPack Middleware...');
    require('./index.dev.js').useWebpackMiddleware(app);
} else {
    console.log('PRODUCTION ENVIRONMENT');
    app.use(express.static(path.join(__dirname, '../dist')));
    console.log('PRODUCTION ENVIRONMENT 2');
    // TODO - Uncomment this when ready
    // app.use(favicon(path.join(__dirname, '../dist/imgs', 'favicon.ico')));
}

app.use('/4chan', require('./routes/4chan'));

app.use('/', function(req, res, next) {
  res.render('index');
  res.end();
});

// catch 404 and forward to error handler
app.use(function(req, res, next) {
  var err = new Error('Not Found');
  err.status = 404;
  next(err);
});

// development error handler
// will print stacktrace
if (app.get('env') === 'development') {
  app.use(function(err, req, res, next) {
    console.log(err.message);
  });
}

// production error handler
// no stacktraces leaked to user
app.use(function(err, req, res, next) {
  res.status(err.status || 500);
  res.render('error', {
    message: err.message,
    error: {}
  });
});

module.exports = app;
<commit_msg>Add root path constant to server<commit_after>var express = require('express');
var app = express();
var router = express.Router();

var ROOT = require('path').join(__dirname, '../dist');
var ENV = process.env.NODE_ENV

// If ENV is development, use webpack hot reloading
if (!ENV || ENV === 'dev' || ENV === 'development') {
    console.log('DEVOLOPMENT ENVIRONMENT: Turning on WebPack Middleware...');
    require('./index.dev.js').useWebpackMiddleware(app);
} else {
    console.log('PRODUCTION ENVIRONMENT');
    app.use(express.static(ROOT));
    // TODO - Uncomment this when ready:
    // app.use(favicon(path.join(__dirname, '../dist/imgs', 'favicon.ico')));
}

app.use('/4chan', require('./routes/4chan'));

app.use('/', function(req, res, next) {
  res.sendFile('index.html', { root: ROOT });
  res.end();
});

// catch 404 and forward to error handler
app.use(function(req, res, next) {
  var err = new Error('Not Found');
  err.status = 404;
  next(err);
});

// development error handler
// will print stacktrace
if (app.get('env') === 'development') {
  app.use(function(err, req, res, next) {
    console.log(err.message);
  });
}

// production error handler
// no stacktraces leaked to user
app.use(function(err, req, res, next) {
  res.status(err.status || 500);
  res.render('error', {
    message: err.message,
    error: {}
  });
});

module.exports = app;
<|endoftext|>


<commit_before>var express = require('express');
var path = require('path');
var logger = require('morgan');
var cookieParser = require('cookie-parser');
var bodyParser = require('body-parser');

var play = require('play').Play();

var app = express();

app.use(logger('dev'));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, 'public')));

var voted = {
  // example:
  // '192.168.0.12': {liked: ['3', '1'], disliked: ['1']}
};

var MUSICS_PATH = process.env.MUSICS_PATH || '/home/pi/musics/';

var playlistPaths = {
	'1': path.join(MUSICS_PATH, 'Epic Sax Guy _.mp3'),
	'2': path.join(MUSICS_PATH, 'match0.wav'),
  '3': path.join(MUSICS_PATH, 'beatboxing flute super mario brothers theme.m4a'),
  '4': path.join(MUSICS_PATH, 'beep1.ogg'),
  '5': path.join(MUSICS_PATH, 'badswap.wav'),
  '6': path.join(MUSICS_PATH, 'tetrisb.mid')
};

var db = { playlist: {
  current: {
    id: '3',
    name: 'Super Mario Bros. Theme',
    img: 'https:\/\/upload.wikimedia.org\/wikipedia\/en\/9\/99\/MarioSMBW.png',
    artist: 'Gregg Pollack',
    playing: false
  },
  following: [
    {
      id: '7',
      name: 'From Time',
      img: 'http:\/\/netstorage.metrolyrics.com\/albums\/1378405711drake-nothing-was-the-same-artwork-2.jpg',
      artist: 'Drake ft. Jhene Aiko',
      likes: 55,
      dislikes: 5
    },
    {
      id: '2',
      name: 'Childish Gambino',
      img: 'http:\/\/cdn.pigeonsandplanes.com\/wp-content\/uploads\/2013\/12\/childish21-406x400.jpg',
      artist: null,
      likes: 34,
      dislikes: 2
    },
    {
      id: '1',
      name: 'Price Tag',
      img: 'http:\/\/www.jessiejofficial.com\/files\/2014\/10\/jessie-j-who-you-are.jpg',
      artist: 'Jessie J ft. B\'o.B',
      likes: 24,
      dislikes: 2
    },
    {
      id: '6',
      name: 'Hello World',
      img: 'http:\/\/medias.2kmusic.com\/uploads\/2014\/01\/03\/img-1388766574-23e5e9ed86c330e05fb8b20d0983cff8.jpg',
      artist: 'Kid Ink',
      likes: 20,
      dislikes: 3
    },
    {
      id: '4',
      name: 'Doctor Who Theme',
      img: 'http:\/\/img4.wikia.nocookie.net\/__cb20130125153635\/supersmashbrosgmod\/images\/0\/09\/LuigiSMBW.jpg',
      artist: null,
      likes: 13,
      dislikes: 6
    },
    {
      id: '5',
      name: 'Touch The Sky',
      img: 'http:\/\/upload.wikimedia.org\/wikipedia\/en\/7\/70\/Graduation_(album).jpg',
      artist: 'Kanye West',
      likes: 1,
      dislikes: 0
    },
    {
      id: '8',
      name: 'Nightbook',
      img: null,
      artist: 'Ludovico Einaudo',
      likes: 7,
      dislikes: 20
    }
  ]
}};

function sortSongs(s1, s2) {
  var score1 = s1.likes - s1.dislikes,
    score2 = s2.likes - s2.dislikes;
  return score1 === score2 ? 0 :
      (score1 < score2 ? 1 : -1); // Sort in descending score
}

app.get('/playlist', function(req, res, next) {
	res.status(200).json(db);
});

app.get('/launch', function(req, res, next) {
  if (!db.playlist.current.playing) {
  	play.sound(playlistPaths[db.playlist.current.id]);
  }
});

function findIn(arr, id) {
  var i,
    foundElement,
    len = arr.length;

  for (i = 0, foundElement; foundElement = arr[i]; ++i) {
    if (foundElement === id || foundElement.id === id) return foundElement;
  }

  return false;
}

app.put(/\/(dis)?like\/([^\/]+)/, function(req, res, next) {
  var song,
    votes,
    like = req.path.match(/^\/like\/.*$/),
    id = req.params[1];

  voted[req.ip] = voted[req.ip] || {liked: [], disliked: []};
  votes = like ? voted[req.ip].liked : voted[req.ip].disliked;

  song = findIn(db.playlist.following, id);
  if (!song) return res.status(404).send('No such song: ' + id);

  if (findIn(votes, id)) {
    return res.status(403).send('Already ' + (like ? '' : 'dis')
        + 'liked song: ' + id);
  }

  if (like) ++song.likes;
  else song.dislikes++;

  votes.push(song.id);

  db.playlist.following.sort(sortSongs);
  return res.status(200).send();
});

app.put(/\/un(dis)?like\/([^\/]+)/, function(req, res, next) {
  var song,
    votes,
    unlike = req.path.match(/^\/unlike\/.*$/),
    id = req.params[1];

  voted[req.ip] = voted[req.ip] || {liked: [], disliked: []};
  votes = unlike ? voted[req.ip].liked : voted[req.ip].disliked;

  song = findIn(db.playlist.following, id);
  if (!song) return res.status(404).send('No such song: ' + id);

  if (!findIn(votes, id)) {
    return res.status(403).send('Did not yet ' + (unlike ? '' : 'dis')
        + 'liked song: ' + id);
  }

  console.log('1');
  if (unlike) --song.likes;
  else --song.dislikes;

  for (var el, i = 0; el = votes[i]; ++i) {
    if (id === el) {
      votes.splice(i, 1);
      break;
    }
  }

  db.playlist.following.sort(sortSongs);
  return res.status(200).send();
});

// catch 404 and forward to error handler
app.use(function(req, res, next) {
  var err = new Error('Not Found');
  err.status = 404;
  next(err);
});

// error handlers

// development error handler
// will print stacktrace
if (app.get('env') === 'development') {
  app.use(function(err, req, res, next) {
    res.status(err.status || 500);
    res.json({
      message: err.message,
      error: err
    });
  });
}

// production error handler
// no stacktraces leaked to user
app.use(function(err, req, res, next) {
  res.status(err.status || 500);
  res.send('error: ' + err.message);
});

module.exports = app;
<commit_msg>Fixed launch<commit_after>var express = require('express');
var path = require('path');
var logger = require('morgan');
var cookieParser = require('cookie-parser');
var bodyParser = require('body-parser');

var play = require('play').Play();
play.usePlayer(process.env.PLAYER || 'afplay');

var app = express();

app.use(logger('dev'));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, 'public')));

var voted = {
  // example:
  // '192.168.0.12': {liked: ['3', '1'], disliked: ['1']}
};

var MUSICS_PATH = process.env.MUSICS_PATH || '/home/pi/musics/';

var playlistPaths = {
	'1': path.join(MUSICS_PATH, 'Epic Sax Guy _.m4a'),
	'2': path.join(MUSICS_PATH, 'match0.wav'),
  '3': path.join(MUSICS_PATH, 'beatboxing flute super mario brothers theme.m4a'),
  '4': path.join(MUSICS_PATH, 'beep1.ogg'),
  '5': path.join(MUSICS_PATH, 'badswap.wav'),
  '6': path.join(MUSICS_PATH, 'Epic Sax Guy _.m4a'),
  '7': path.join(MUSICS_PATH, 'Epic Sax Guy _.m4a'),
  '8': path.join(MUSICS_PATH, 'beatboxing flute super mario brothers theme.m4a')
};

var db = { playlist: {
  current: {
    id: '3',
    name: 'Super Mario Bros. Theme',
    img: 'https:\/\/upload.wikimedia.org\/wikipedia\/en\/9\/99\/MarioSMBW.png',
    artist: 'Gregg Pollack',
    playing: false
  },
  following: [
    {
      id: '7',
      name: 'From Time',
      img: 'http:\/\/netstorage.metrolyrics.com\/albums\/1378405711drake-nothing-was-the-same-artwork-2.jpg',
      artist: 'Drake ft. Jhene Aiko',
      likes: 55,
      dislikes: 5
    },
    {
      id: '2',
      name: 'Childish Gambino',
      img: 'http:\/\/cdn.pigeonsandplanes.com\/wp-content\/uploads\/2013\/12\/childish21-406x400.jpg',
      artist: null,
      likes: 34,
      dislikes: 2
    },
    {
      id: '1',
      name: 'Price Tag',
      img: 'http:\/\/www.jessiejofficial.com\/files\/2014\/10\/jessie-j-who-you-are.jpg',
      artist: 'Jessie J ft. B\'o.B',
      likes: 24,
      dislikes: 2
    },
    {
      id: '6',
      name: 'Hello World',
      img: 'http:\/\/medias.2kmusic.com\/uploads\/2014\/01\/03\/img-1388766574-23e5e9ed86c330e05fb8b20d0983cff8.jpg',
      artist: 'Kid Ink',
      likes: 20,
      dislikes: 3
    },
    {
      id: '4',
      name: 'Doctor Who Theme',
      img: 'http:\/\/img4.wikia.nocookie.net\/__cb20130125153635\/supersmashbrosgmod\/images\/0\/09\/LuigiSMBW.jpg',
      artist: null,
      likes: 13,
      dislikes: 6
    },
    {
      id: '5',
      name: 'Touch The Sky',
      img: 'http:\/\/upload.wikimedia.org\/wikipedia\/en\/7\/70\/Graduation_(album).jpg',
      artist: 'Kanye West',
      likes: 1,
      dislikes: 0
    },
    {
      id: '8',
      name: 'Nightbook',
      img: null,
      artist: 'Ludovico Einaudo',
      likes: 7,
      dislikes: 20
    }
  ]
}};

function sortSongs(s1, s2) {
  var score1 = s1.likes - s1.dislikes,
    score2 = s2.likes - s2.dislikes;
  return score1 === score2 ? 0 :
      (score1 < score2 ? 1 : -1); // Sort in descending score
}

function playNextSong(next) {
  console.log('choosing next song');
  db.playlist.current = db.playlist.following[0];
  db.playlist.following.splice(0, 1);  // Removes the first song

  if (0 === db.length) return next();

  console.log('launching next song');
  play.sound(playlistPaths[db.playlist.current.id], function () {
    console.log('finished');
    playNextSong(next);
  });
}

app.get('/playlist', function(req, res, next) {
	res.status(200).json(db);
});

app.get('/launch', function(req, res, next) {
  if (!db.playlist.current.playing) {
    console.log('first');
    play.sound(playlistPaths[db.playlist.current.id], function () {
      console.log('first done');
      playNextSong(next);
    });
  }
  res.status(200).send('ok');
});

function findIn(arr, id) {
  var i,
    foundElement,
    len = arr.length;

  for (i = 0, foundElement; foundElement = arr[i]; ++i) {
    if (foundElement === id || foundElement.id === id) return foundElement;
  }

  return false;
}

app.put(/\/(dis)?like\/([^\/]+)/, function(req, res, next) {
  var song,
    votes,
    like = req.path.match(/^\/like\/.*$/),
    id = req.params[1];

  voted[req.ip] = voted[req.ip] || {liked: [], disliked: []};
  votes = like ? voted[req.ip].liked : voted[req.ip].disliked;

  song = findIn(db.playlist.following, id);
  if (!song) return res.status(404).send('No such song: ' + id);

  if (findIn(votes, id)) {
    return res.status(403).send('Already ' + (like ? '' : 'dis')
        + 'liked song: ' + id);
  }

  if (like) ++song.likes;
  else song.dislikes++;

  votes.push(song.id);

  db.playlist.following.sort(sortSongs);
  return res.status(200).send();
});

app.put(/\/un(dis)?like\/([^\/]+)/, function(req, res, next) {
  var song,
    votes,
    unlike = req.path.match(/^\/unlike\/.*$/),
    id = req.params[1];

  voted[req.ip] = voted[req.ip] || {liked: [], disliked: []};
  votes = unlike ? voted[req.ip].liked : voted[req.ip].disliked;

  song = findIn(db.playlist.following, id);
  if (!song) return res.status(404).send('No such song: ' + id);

  if (!findIn(votes, id)) {
    return res.status(403).send('Did not yet ' + (unlike ? '' : 'dis')
        + 'liked song: ' + id);
  }

  if (unlike) --song.likes;
  else --song.dislikes;

  for (var el, i = 0; el = votes[i]; ++i) {
    if (id === el) {
      votes.splice(i, 1);
      break;
    }
  }

  db.playlist.following.sort(sortSongs);
  return res.status(200).send();
});

// catch 404 and forward to error handler
app.use(function(req, res, next) {
  var err = new Error('Not Found');
  err.status = 404;
  next(err);
});

// error handlers

// development error handler
// will print stacktrace
if (app.get('env') === 'development') {
  app.use(function(err, req, res, next) {
    res.status(err.status || 500);
    res.json({
      message: err.message,
      error: err
    });
  });
}

// production error handler
// no stacktraces leaked to user
app.use(function(err, req, res, next) {
  res.status(err.status || 500);
  res.send('error: ' + err.message);
});

module.exports = app;
<|endoftext|>


<commit_before>import express from 'express';
import bodyParser from 'body-parser';
import path from 'path';
import Sequelize from 'sequelize';
import cookieParser from 'cookie-parser';
import flash from 'connect-flash';
import User from './models/user';

// ROUTES

import authRoutes from './routes/auth';

const passport = require('passport');
const LocalStrategy = require('passport-local');

const app = express();

app.use(bodyParser.urlencoded({ extended: true }));
app.use(require('connect-multiparty')());

app.use(express.static(path.join(__dirname, '/public')));
app.use(flash());

app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'ejs');

// PASSPORT CONFIGURATION
app.use(require('express-session')({
  secret: 'Anywhere I go',
  resave: false,
  saveUninitialized: false
}));

app.use(passport.initialize());
app.use(passport.session());
passport.use(User.createStrategy());
passport.serializeUser(User.serializeUser());
passport.deserializeUser(User.deserializeUser());

app.use((req, res, next) => {
  res.locals.currentUser = req.user;
  res.locals.error = req.flash('error');
  res.locals.success = req.flash('success');
  if (req.user != undefined) console.log(res.locals.currentUser.dataValues);
  next();
});

// ROUTES CONFIG
app.use(authRoutes);

// MiddleWares

const isLoggedIn = (req, res, next) => {
  if (req.isAuthenticated()) {
    return next();
  }
  res.redirect('/login');
};

// If no route is matched return a 404
app.use((req, res, next) => {
  res.status(501).send({
    status: false,
    message: 'This API doesn\'t support that function.'
  });
  next();
});

app.listen(process.env.PORT || 3002, () => {
  console.log('serving on port 3002');
});

export default app;
<commit_msg>adjusting server file while using console to debug<commit_after>import express from 'express';
import bodyParser from 'body-parser';
import path from 'path';
import Sequelize from 'sequelize';
import cookieParser from 'cookie-parser';
import flash from 'connect-flash';
import User from './models/user';

// ROUTES

import authRoutes from './routes/auth';

const passport = require('passport');
const LocalStrategy = require('passport-local');

const app = express();

app.use(bodyParser.urlencoded({ extended: true }));
app.use(require('connect-multiparty')());

app.use(express.static(path.join(__dirname, '/public')));
app.use(flash());

app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'ejs');

// PASSPORT CONFIGURATION
app.use(require('express-session')({
  secret: 'Anywhere I go',
  resave: false,
  saveUninitialized: false
}));

app.use(passport.initialize());
app.use(passport.session());
passport.use(User.createStrategy());
passport.serializeUser(User.serializeUser());
passport.deserializeUser(User.deserializeUser());

app.use((req, res, next) => {
  res.locals.currentUser = req.user;
  res.locals.error = req.flash('error');
  res.locals.success = req.flash('success');
  if (req.user != undefined) console.log('from here--->', res.locals.currentUser.dataValues);
  next();
});

// ROUTES CONFIG
app.use(authRoutes);

// MiddleWares

const isLoggedIn = (req, res, next) => {
  if (req.isAuthenticated()) {
    return next();
  }
  res.redirect('/login');
};

// If no route is matched return a 404
app.use((req, res, next) => {
  res.status(501).send({
    status: false,
    message: 'This API doesn\'t support that function.'
  });
  next();
});

app.listen(process.env.PORT || 3002, () => {
  console.log('serving on port 3002');
});

export default app;
<|endoftext|>


<commit_before>/**
 * Main application file
 */

'use strict';

// Set default node environment to development
process.env.NODE_ENV = process.env.NODE_ENV || 'development';

var express = require('express');
var mongoose = require('mongoose');
var config = require('./config/environment');

// Connect to database
mongoose.connect(config.mongo.uri, config.mongo.options);

// Populate DB with sample data
if (config.seedDB) {
	require('./config/seed');
}

// Setup server
var app = express();
var server = require('http').createServer(app);

var http = require('http');
var favicon = require('serve-favicon');

var _favicon = favicon('/public/favicon.ico');

var server = http.createServer(function onRequest(req, res) {
	_favicon(req, res, function onNext(err) {
		if (err) {
			res.statusCode = 500;
			res.end();
			return;
		}

		// continue to process the request here, etc.

		res.statusCode = 404;
		res.end('oops');
	});
});

require('./config/express')(app);
require('./routes')(app);

// Start server
server.listen(config.port, config.ip, function() {
	console.log('Express server listening on %d, in %s mode', config.port, app.get('env'));
});

// Expose app
exports = module.exports = app;<commit_msg>more more<commit_after>/**
 * Main application file
 */

'use strict';

// Set default node environment to development
process.env.NODE_ENV = process.env.NODE_ENV || 'development';

var express = require('express');
var mongoose = require('mongoose');
var config = require('./config/environment');

// Connect to database
mongoose.connect(config.mongo.uri, config.mongo.options);

// Populate DB with sample data
if (config.seedDB) {
	require('./config/seed');
}

// Setup server
var app = express();
var server = require('http').createServer(app);

var http = require('http');
var favicon = require('serve-favicon');

var _favicon = favicon('dist/public/favicon.ico');

var server = http.createServer(function onRequest(req, res) {
	_favicon(req, res, function onNext(err) {
		if (err) {
			res.statusCode = 500;
			res.end();
			return;
		}

		// continue to process the request here, etc.

		res.statusCode = 404;
		res.end('oops');
	});
});

require('./config/express')(app);
require('./routes')(app);

// Start server
server.listen(config.port, config.ip, function() {
	console.log('Express server listening on %d, in %s mode', config.port, app.get('env'));
});

// Expose app
exports = module.exports = app;<|endoftext|>


<commit_before>"use strict";

const path = require("path");
const config = require("config");
const helmet = require("helmet");
const express = require("express");
const favicon = require("serve-favicon");
const bodyParser = require("body-parser");
const compression = require("compression");

const routes = require("./routes");
const session = require("./auth/session");
const passport = require("./auth/passport");
const crawler = require("./controllers/crawler");
const dbhelper = require("./controllers/dbhelper");
const assetsMap = require("../public/assets/assets.json");

// connect mongodb.
dbhelper.connect((err) =>
{
    const msg = "\nDatabase Server not started, some features will be shut down.";
    if (err)
    {
        console.error(`${msg}\n${err.message}`);
    }
    else
    {
        if (config.crawler.enabled)
        {
            setTimeout(crawler.start, config.crawler.delay);
        }
    }
});

// init express.
const app = express();

// view engine setup.
app.set("views", path.resolve(__dirname, "./views"));
app.set("view engine", "pug");

// security.
app.use(helmet());

// compression.
app.use(compression());

// favicon setup.
app.use(favicon(path.resolve(__dirname, "../public/favicon.ico")));

app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
app.use(session);
app.use(passport.initialize());
app.use(passport.session());

// static file setup.
app.use(express.static(path.resolve(__dirname, "../public")));

// router setup.
app.use("/", routes);

// assets map setup.
app.locals.map = assetsMap;

// catch 404 and forward to global error handler.
app.use((req, res, next) =>
{
    const err = new Error("404 Not Found");
    err.status = 404;
    next(err);
});

// global error handler.
app.use((err, req, res, next) =>
{
    res.status(err.status || 500).render("error_404", { map: app.locals.map });
});

module.exports = app;
<commit_msg>add cache-control<commit_after>"use strict";

const path = require("path");
const config = require("config");
const helmet = require("helmet");
const express = require("express");
const favicon = require("serve-favicon");
const bodyParser = require("body-parser");
const compression = require("compression");

const routes = require("./routes");
const session = require("./auth/session");
const passport = require("./auth/passport");
const crawler = require("./controllers/crawler");
const dbhelper = require("./controllers/dbhelper");
const assetsMap = require("../public/assets/assets.json");

// connect mongodb.
dbhelper.connect((err) =>
{
    const msg = "\nDatabase Server not started, some features will be shut down.";
    if (err)
    {
        console.error(`${msg}\n${err.message}`);
    }
    else
    {
        if (config.crawler.enabled)
        {
            setTimeout(crawler.start, config.crawler.delay);
        }
    }
});

// init express.
const app = express();

// view engine setup.
app.set("views", path.resolve(__dirname, "./views"));
app.set("view engine", "pug");

// security.
app.use(helmet());

// compression.
app.use(compression());

// favicon setup.
app.use(favicon(path.resolve(__dirname, "../public/favicon.ico")));

app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
app.use(session);
app.use(passport.initialize());
app.use(passport.session());

// static file setup.
app.use(express.static(path.resolve(__dirname, "../public"), { maxAge: "1y" }));

// router setup.
app.use("/", routes);

// assets map setup.
app.locals.map = assetsMap;

// catch 404 and forward to global error handler.
app.use((req, res, next) =>
{
    const err = new Error("404 Not Found");
    err.status = 404;
    next(err);
});

// global error handler.
app.use((err, req, res, next) =>
{
    res.status(err.status || 500).render("error_404", { map: app.locals.map });
});

module.exports = app;
<|endoftext|>


<commit_before>'use strict';

const CFG = {};

// Copy app configuration from config.json
Object.assign( CFG, require('../config.json') );

// App version is loaded from package.json
CFG.APP_VERSION = process.env.npm_package_version || (require('../package.json').version);

// Production run
CFG.DIST = (process.argv.indexOf("--dist") >= 0);

// Root directory
CFG.ROOT_DIR = require('path').normalize( __dirname + '/..' );

// Root directory for the webapp
CFG.APP_DIR = __dirname;

// Root directory for the served content
CFG.WEB_DIR = CFG.ROOT_DIR + '/editor';

// Expose configuration object
module.exports = CFG;
<commit_msg>Running a developer server now possible<commit_after>'use strict';

const CFG = {};

// Copy app configuration from config.json
Object.assign( CFG, require('../config.json') );

// App version is loaded from package.json
CFG.APP_VERSION = process.env.npm_package_version || (require('../package.json').version);

// Production run
CFG.DIST = (process.argv.indexOf("--dist") >= 0);

// Root directory
CFG.ROOT_DIR = require('path').normalize( __dirname + '/..' );

// Root directory for the webapp
CFG.APP_DIR = __dirname;

// Root directory for the served content
CFG.WEB_DIR = CFG.ROOT_DIR + '/editor';

// Production/development host/port setup
if (!CFG.DIST) {
  if (CFG.DEV_SERVER_HOST) CFG.SERVER_HOST = CFG.DEV_SERVER_HOST;
  if (CFG.DEV_SERVER_PORT) CFG.SERVER_PORT = CFG.DEV_SERVER_PORT;
}

// Expose configuration object
module.exports = CFG;
<|endoftext|>