<commit_before>// node modules
var Path = nodeRequire('path');
var fs = nodeRequire('fs');
var os = nodeRequire('os');
var chokidar = nodeRequire('chokidar');

// front-end modules
var Vue = require('vue');
var $ = require('jquery');
var _ = require('underscore');
var keybindings = require('./keybindings');
var Files = require('./files');
var menu = require('./menu');
var windowstate = require('./windowstate');
var updater = require('./updater');
var settings = require('./settings');
var modes = {
  p5: require('./modes/p5/p5-mode')
};

var appConfig = {

  el: '#app',

  mode: modes.p5,

  components: {
    editor: require('./editor/index'),
    sidebar: require('./sidebar/index'),
    settings: require('./settings/index'),
    debug: require('./debug/index')
  },

  data: {
    title: 'Untitled',
    projectPath: window.PATH,
    unsaved: window.UNSAVED ? true : false,
    windowURL: window.location.href,
    temp: true,
    running: false,
    focused: false,
    settings: {},
    showSettings: false,
    files: [],
    justSaved: false,
    askReload: false
  },

  computed: {
    projectName: function() {
      return Path.basename(this.projectPath);
    }
  },

  ready: function() {
    this.modeFunction('update');
    updater.check();
    keybindings.setup(this);
    menu.setup(this);

    this.setupFileListener();
    this.setupCloseHandler();
    this.setupDragListener();
    this.setupSettings();

    if (this.projectPath) {
      if (!this.unsaved) this.temp = false;
      var filename = null;

      if (fs.lstatSync(this.projectPath).isFile()) {
        // keep the name of the file to be opened
        filename = this.projectPath;

        // set the projectPath to the enclosing folder
        this.projectPath = Path.dirname(this.projectPath);
      }

      if (window.FILEPATH && fs.lstatSync(window.FILEPATH).isFile()) {
        filename = window.FILEPATH;
      }

      // load the project and open the selected file
      var self = this;
      this.loadProject(this.projectPath, function(){
        if (filename) {
          if (Path.dirname(filename) === this.projectPath) {
            self.openFile(filename);
          } else {
            self.$broadcast('open-nested-file', filename);
          }
        }
        gui.Window.get().show();
      });

      menu.updateRecentFiles(this, this.projectPath);
    } else {
      // if we don't have a project path global, create a new project
      this.modeFunction('newProject');
      menu.updateRecentFiles(this);
    }

  },

  methods: {
    modeFunction: function(func, args) {
      var mode = this.$options.mode;
      if (typeof mode[func] === 'function') {
        // make args an array if it isn't already
        // typeof args won't work because it returns 'object'
        if (Object.prototype.toString.call(args) !== '[object Array]') {
          args = [args];
        }
        mode[func].apply(this, args);
      }
    },

    setupSettings: function() {
      this.settings = settings.load();
      this.$watch('settings', function(value){
        this.$broadcast('settings-changed', value);
        settings.save(value);
      });
    },

    // use jquery to handle file changes
    // (I should move this over to vuejs but it wasn't dealing
    // with the html file element properly)
    setupFileListener: function() {
      $('#openFile').change(this.open.bind(this));
      $('#saveFile').change(this.saveAs.bind(this));
      $('#saveProject').change(this.saveProjectAs.bind(this));
    },

    setupCloseHandler: function() {
      var self = this;
      var win = gui.Window.get();
      win.on('close', function(closeEvent){
        // check to see if there are unsaved files
        var shouldClose = true;
        if (_.any(self.files, function(f) {return f.contents != f.originalContents})) {
          shouldClose = confirm('You have unsaved files. Quit and lose changes?');
        }
        if (shouldClose) {
          // clean up output window
          if (self.outputWindow) {
            self.outputWindow.close(true);
            self.outputWindow = null;
          }

          // save window state if the user quit the program
          if (closeEvent === 'quit') {
            windowstate.save(self, win);
          }

          // close this window
          this.close(true);
          win = null;
        }
      });

      win.on('focus', function(){
        self.focused = true;
        menu.resetMenu();
        if (self.askReload) {
          self.askReload = false;
          var shouldRefresh = confirm(self.currentFile.path + ' was edited somewhere else. Reload? You will lose any changes.');
          if (shouldRefresh) {
              //self.openProject(self.currentFile.path);
              //gui.Window.get().close(true);
            window.location = 'index.html';
          }
        }
      });

      win.on('blur', function(){
        self.focused = false;
      });
    },

    // todo: setup drag and drop
    setupDragListener: function() {
      var self = this;
      window.ondragover = function(e) { e.preventDefault(); return false };
      window.ondrop = function(e) {
        e.preventDefault();
        if (e.dataTransfer.files[0]) {
          var path = e.dataTransfer.files[0].path;
          self.openProject(path);
        }
        return false
      };
    },

    // create a new window 50px below current window
    newWindow: function(url, options) {
      var currentWindow = gui.Window.get();
      var win = gui.Window.open(url, _.extend({
        x: currentWindow.x + 50,
        y: currentWindow.y + 50,
        width: 1024,
        height: 700,
        toolbar: false,
        focus: true,
        show: false
      }, options));
      return win;
    },

    // open an existing project with a new window
    open: function(event) {
      var path = event.target.files[0].path;
      this.openProject(path);
      // reset value in case the user wants to open the same file more than once
      $('#openFile').val('');
    },

    openProject: function(path) {
      // create the new window
      var win = this.newWindow(this.windowURL);

      // set the project path of the new window
      win.on('document-start', function(){
        if (fs.lstatSync(path).isDirectory()) {
          var sketchPath = Path.join(path, 'sketch.js');
          if (fs.existsSync(sketchPath)) path = sketchPath;
        }
        win.window.PATH = path;
      });
      return win;
    },

    // load project files
    loadProject: function(path, callback) {
      var self = this;
      Files.list(path, function(files){
        self.files = files;
        self.watch(path);
        if (typeof callback === 'function') callback();
      });
    },

    // watch the project file tree for changes
    watch: function(path) {
      var self = this;

      // don't watch recursively
      var watcher = chokidar.watch(path, {
        ignoreInitial: true,
        ignored: function(filepath) {
          var regex = new RegExp(path + '\/.*\/.+');
          return regex.test(filepath);
        }
      });

      watcher.on('add', function(path) {
        var f = Files.setup(path);
        Files.addToTree(f, self.files, self.projectPath);
      }).on('addDir', function(path) {
        var f = Files.setup(path, {type: 'folder', children: []});
        Files.addToTree(f, self.files, self.projectPath);
      }).on('unlink', function(path) {
        Files.removeFromTree(path, self.files);
      }).on('unlinkDir', function(path) {
        Files.removeFromTree(path, self.files);
      }).on('change', function(path) {
        if (self.justSaved) {
          self.justSaved = false;
        } else {
          if (!self.temp) self.askReload = true;
        }
      });
    },

    // close the window, checking for unsaved file changes
    closeProject: function() {
      if (this.focused) {
        if (this.outputWindow) {
          this.outputWindow.close(true);
          this.outputWindow = null;
        }
        gui.Window.get().close();
      } else {
        if (this.outputWindow) {
          this.outputWindow.close(true);
          this.outputWindow = null;
        }
      }
    },

    // save all open files
    saveAll: function() {
      _.where(this.files, {type: 'file', open: true}).forEach(function(file) {
        if (file.originalContents != file.contents) {
          fs.writeFileSync(file.path, file.contents, "utf8");
          file.originalContents = file.contents;
        }
      });
      menu.updateRecentFiles(this, this.projectPath);
    },

    saveAs: function(event) {
      // capture the filename selected by the user
      var file = event.target.files[0].path;

      if (this.temp) {
        // mode specific action
        this.modeFunction('saveAs', file);
        menu.updateRecentFiles(this, this.projectPath);
      } else {
        // save a file
        // if the we are saving inside the project path just open the new file
        // otherwise open a new window
        fs.writeFileSync(file, this.currentFile.contents, "utf8");
        if ((Path.dirname(file) + '/').indexOf(this.projectPath + '/') > -1) {
          var f = Files.setup(file);
          Files.addToTree(f, this.files, this.projectPath);
          this.openFile(file);
        } else {
          this.openProject(file);
        }
      }

      // reset value in case the user wants to save the same filename more than once
      $('#saveFile').val('');
    },

    saveProjectAs: function(event) {
      var path = event.target.files[0].path;
      this.modeFunction('saveAs', path);
    },

    saveFile: function() {
      // if this is a new project then trigger a save-as
      if (this.temp) {
        $('#saveFile').trigger('click');
      } else {
        // otherwise just write the current file
        this.writeFile();
      }
    },

    writeFile: function() {
      var self = this;

      self.justSaved = true;

      fs.writeFileSync(this.currentFile.path, this.currentFile.contents, "utf8");
      this.currentFile.originalContents = this.currentFile.contents;

    },

    // open up a file - read its contents if it's not already opened
    openFile: function(path, callback) {
      var self = this;

      var file = Files.find(this.files, path);
      if (!file) return false;

      if (file.open) {
        this.title = file.name;
        this.currentFile = file;
        this.$broadcast('open-file', this.currentFile);
      } else {
        fs.readFile(path, 'utf8', function(err, fileContents) {
          if (err) throw err;
          file.contents = file.originalContents = fileContents;
          file.open = true;
          self.title = file.name;
          self.currentFile = file;
          self.$broadcast('open-file', self.currentFile);
          if (typeof callback === 'function') callback(file);
        });
      }
    },

    // create a new file and save it in the project path
    newFile: function(basepath) {
      var title = prompt('File name:');
      if (!title) return false;

      if (typeof basepath === 'undefined') {
        basepath = this.projectPath;
      }

      var filename = Path.join(basepath, title);

      var self = this;
      fs.writeFile(filename, '', 'utf8', function(err){
        var f = Files.setup(filename);
        Files.addToTree(f, self.files, self.projectPath);
        self.openFile(filename);
      });
    },

    newFolder: function(basepath) {
      var title = prompt('Folder name:');
      if (!title) return false;

      if (typeof basepath === 'undefined') {
        basepath = this.projectPath;
      }

      var filename = Path.join(basepath, title);

      var self = this;
      fs.mkdir(filename);
    },

    renameFile: function(path) {
      var originalName = Path.basename(path);
      var newName = prompt('Rename ' + originalName + ' to:', originalName);
      if (!newName) return false;

      fs.rename(path, Path.join(Path.dirname(path), newName));
    },

    debugOut: function(msg, line, type) {
      if (typeof msg === 'object') msg = JSON.stringify(msg);
      $('#debug').append('
' + (line ? line + ': ' : '') + msg + '
');
      $('#debug').scrollTop($('#debug')[0].scrollHeight);
    },

    run: function() {
      $('#debug').html('');
      this.modeFunction('run');
    },

    toggleRun: function() {
      if (this.running) {
        this.modeFunction('stop');
      } else {
        $('#debug').html('');
        this.modeFunction('run');
      }
    },

    changeFontSize: function(sz) {
      this.settings.fontSize = parseInt(this.settings.fontSize) + sz;
    },

    toggleSettingsPane: function() {
      this.showSettings = !this.showSettings;
    },

    showHelp: function() {
      gui.Shell.openExternal(this.$options.mode.referenceURL);
    }

  }

};

windowstate.load(function(createNewProject){
  if (createNewProject) {
    var app = new Vue(appConfig);
  } else {
    gui.Window.get().close(true);
  }
});
<commit_msg>really hopefuly fixed recent file bug<commit_after>// node modules
var Path = nodeRequire('path');
var fs = nodeRequire('fs');
var os = nodeRequire('os');
var chokidar = nodeRequire('chokidar');

// front-end modules
var Vue = require('vue');
var $ = require('jquery');
var _ = require('underscore');
var keybindings = require('./keybindings');
var Files = require('./files');
var menu = require('./menu');
var windowstate = require('./windowstate');
var updater = require('./updater');
var settings = require('./settings');
var modes = {
  p5: require('./modes/p5/p5-mode')
};

var appConfig = {

  el: '#app',

  mode: modes.p5,

  components: {
    editor: require('./editor/index'),
    sidebar: require('./sidebar/index'),
    settings: require('./settings/index'),
    debug: require('./debug/index')
  },

  data: {
    title: 'Untitled',
    projectPath: window.PATH,
    unsaved: window.UNSAVED ? true : false,
    windowURL: window.location.href,
    temp: true,
    running: false,
    focused: false,
    settings: {},
    showSettings: false,
    files: [],
    justSaved: false,
    askReload: false
  },

  computed: {
    projectName: function() {
      return Path.basename(this.projectPath);
    }
  },

  ready: function() {
    this.modeFunction('update');
    updater.check();
    keybindings.setup(this);
    menu.setup(this);

    this.setupFileListener();
    this.setupCloseHandler();
    this.setupDragListener();
    this.setupSettings();

    if (this.projectPath) {
      if (!this.unsaved) this.temp = false;
      var filename = null;

      if (fs.lstatSync(this.projectPath).isFile()) {
        // keep the name of the file to be opened
        filename = this.projectPath;

        // set the projectPath to the enclosing folder
        this.projectPath = Path.dirname(this.projectPath);
      }

      if (window.FILEPATH && fs.lstatSync(window.FILEPATH).isFile()) {
        filename = window.FILEPATH;
      }

      // load the project and open the selected file
      var self = this;
      this.loadProject(this.projectPath, function(){
        if (filename) {
          if (Path.dirname(filename) === self.projectPath) {
            self.openFile(filename);
          } else {
            self.$broadcast('open-nested-file', filename);
          }
        }
        gui.Window.get().show();
      });

      menu.updateRecentFiles(this, this.projectPath);
    } else {
      // if we don't have a project path global, create a new project
      this.modeFunction('newProject');
      menu.updateRecentFiles(this);
    }

  },

  methods: {
    modeFunction: function(func, args) {
      var mode = this.$options.mode;
      if (typeof mode[func] === 'function') {
        // make args an array if it isn't already
        // typeof args won't work because it returns 'object'
        if (Object.prototype.toString.call(args) !== '[object Array]') {
          args = [args];
        }
        mode[func].apply(this, args);
      }
    },

    setupSettings: function() {
      this.settings = settings.load();
      this.$watch('settings', function(value){
        this.$broadcast('settings-changed', value);
        settings.save(value);
      });
    },

    // use jquery to handle file changes
    // (I should move this over to vuejs but it wasn't dealing
    // with the html file element properly)
    setupFileListener: function() {
      $('#openFile').change(this.open.bind(this));
      $('#saveFile').change(this.saveAs.bind(this));
      $('#saveProject').change(this.saveProjectAs.bind(this));
    },

    setupCloseHandler: function() {
      var self = this;
      var win = gui.Window.get();
      win.on('close', function(closeEvent){
        // check to see if there are unsaved files
        var shouldClose = true;
        if (_.any(self.files, function(f) {return f.contents != f.originalContents})) {
          shouldClose = confirm('You have unsaved files. Quit and lose changes?');
        }
        if (shouldClose) {
          // clean up output window
          if (self.outputWindow) {
            self.outputWindow.close(true);
            self.outputWindow = null;
          }

          // save window state if the user quit the program
          if (closeEvent === 'quit') {
            windowstate.save(self, win);
          }

          // close this window
          this.close(true);
          win = null;
        }
      });

      win.on('focus', function(){
        self.focused = true;
        menu.resetMenu();
        if (self.askReload) {
          self.askReload = false;
          var shouldRefresh = confirm(self.currentFile.path + ' was edited somewhere else. Reload? You will lose any changes.');
          if (shouldRefresh) {
              //self.openProject(self.currentFile.path);
              //gui.Window.get().close(true);
            window.location = 'index.html';
          }
        }
      });

      win.on('blur', function(){
        self.focused = false;
      });
    },

    // todo: setup drag and drop
    setupDragListener: function() {
      var self = this;
      window.ondragover = function(e) { e.preventDefault(); return false };
      window.ondrop = function(e) {
        e.preventDefault();
        if (e.dataTransfer.files[0]) {
          var path = e.dataTransfer.files[0].path;
          self.openProject(path);
        }
        return false
      };
    },

    // create a new window 50px below current window
    newWindow: function(url, options) {
      var currentWindow = gui.Window.get();
      var win = gui.Window.open(url, _.extend({
        x: currentWindow.x + 50,
        y: currentWindow.y + 50,
        width: 1024,
        height: 700,
        toolbar: false,
        focus: true,
        show: false
      }, options));
      return win;
    },

    // open an existing project with a new window
    open: function(event) {
      var path = event.target.files[0].path;
      this.openProject(path);
      // reset value in case the user wants to open the same file more than once
      $('#openFile').val('');
    },

    openProject: function(path) {
      // create the new window
      var win = this.newWindow(this.windowURL);

      // set the project path of the new window
      win.on('document-start', function(){
        if (fs.lstatSync(path).isDirectory()) {
          var sketchPath = Path.join(path, 'sketch.js');
          if (fs.existsSync(sketchPath)) path = sketchPath;
        }
        win.window.PATH = path;
      });
      return win;
    },

    // load project files
    loadProject: function(path, callback) {
      var self = this;
      Files.list(path, function(files){
        self.files = files;
        self.watch(path);
        if (typeof callback === 'function') callback();
      });
    },

    // watch the project file tree for changes
    watch: function(path) {
      var self = this;

      // don't watch recursively
      var watcher = chokidar.watch(path, {
        ignoreInitial: true,
        ignored: function(filepath) {
          var regex = new RegExp(path + '\/.*\/.+');
          return regex.test(filepath);
        }
      });

      watcher.on('add', function(path) {
        var f = Files.setup(path);
        Files.addToTree(f, self.files, self.projectPath);
      }).on('addDir', function(path) {
        var f = Files.setup(path, {type: 'folder', children: []});
        Files.addToTree(f, self.files, self.projectPath);
      }).on('unlink', function(path) {
        Files.removeFromTree(path, self.files);
      }).on('unlinkDir', function(path) {
        Files.removeFromTree(path, self.files);
      }).on('change', function(path) {
        if (self.justSaved) {
          self.justSaved = false;
        } else {
          if (!self.temp) self.askReload = true;
        }
      });
    },

    // close the window, checking for unsaved file changes
    closeProject: function() {
      if (this.focused) {
        if (this.outputWindow) {
          this.outputWindow.close(true);
          this.outputWindow = null;
        }
        gui.Window.get().close();
      } else {
        if (this.outputWindow) {
          this.outputWindow.close(true);
          this.outputWindow = null;
        }
      }
    },

    // save all open files
    saveAll: function() {
      _.where(this.files, {type: 'file', open: true}).forEach(function(file) {
        if (file.originalContents != file.contents) {
          fs.writeFileSync(file.path, file.contents, "utf8");
          file.originalContents = file.contents;
        }
      });
      menu.updateRecentFiles(this, this.projectPath);
    },

    saveAs: function(event) {
      // capture the filename selected by the user
      var file = event.target.files[0].path;

      if (this.temp) {
        // mode specific action
        this.modeFunction('saveAs', file);
        menu.updateRecentFiles(this, this.projectPath);
      } else {
        // save a file
        // if the we are saving inside the project path just open the new file
        // otherwise open a new window
        fs.writeFileSync(file, this.currentFile.contents, "utf8");
        if ((Path.dirname(file) + '/').indexOf(this.projectPath + '/') > -1) {
          var f = Files.setup(file);
          Files.addToTree(f, this.files, this.projectPath);
          this.openFile(file);
        } else {
          this.openProject(file);
        }
      }

      // reset value in case the user wants to save the same filename more than once
      $('#saveFile').val('');
    },

    saveProjectAs: function(event) {
      var path = event.target.files[0].path;
      this.modeFunction('saveAs', path);
    },

    saveFile: function() {
      // if this is a new project then trigger a save-as
      if (this.temp) {
        $('#saveFile').trigger('click');
      } else {
        // otherwise just write the current file
        this.writeFile();
      }
    },

    writeFile: function() {
      var self = this;

      self.justSaved = true;

      fs.writeFileSync(this.currentFile.path, this.currentFile.contents, "utf8");
      this.currentFile.originalContents = this.currentFile.contents;

    },

    // open up a file - read its contents if it's not already opened
    openFile: function(path, callback) {
      var self = this;

      var file = Files.find(this.files, path);
      if (!file) return false;

      if (file.open) {
        this.title = file.name;
        this.currentFile = file;
        this.$broadcast('open-file', this.currentFile);
      } else {
        fs.readFile(path, 'utf8', function(err, fileContents) {
          if (err) throw err;
          file.contents = file.originalContents = fileContents;
          file.open = true;
          self.title = file.name;
          self.currentFile = file;
          self.$broadcast('open-file', self.currentFile);
          if (typeof callback === 'function') callback(file);
        });
      }
    },

    // create a new file and save it in the project path
    newFile: function(basepath) {
      var title = prompt('File name:');
      if (!title) return false;

      if (typeof basepath === 'undefined') {
        basepath = this.projectPath;
      }

      var filename = Path.join(basepath, title);

      var self = this;
      fs.writeFile(filename, '', 'utf8', function(err){
        var f = Files.setup(filename);
        Files.addToTree(f, self.files, self.projectPath);
        self.openFile(filename);
      });
    },

    newFolder: function(basepath) {
      var title = prompt('Folder name:');
      if (!title) return false;

      if (typeof basepath === 'undefined') {
        basepath = this.projectPath;
      }

      var filename = Path.join(basepath, title);

      var self = this;
      fs.mkdir(filename);
    },

    renameFile: function(path) {
      var originalName = Path.basename(path);
      var newName = prompt('Rename ' + originalName + ' to:', originalName);
      if (!newName) return false;

      fs.rename(path, Path.join(Path.dirname(path), newName));
    },

    debugOut: function(msg, line, type) {
      if (typeof msg === 'object') msg = JSON.stringify(msg);
      $('#debug').append('
' + (line ? line + ': ' : '') + msg + '
');
      $('#debug').scrollTop($('#debug')[0].scrollHeight);
    },

    run: function() {
      $('#debug').html('');
      this.modeFunction('run');
    },

    toggleRun: function() {
      if (this.running) {
        this.modeFunction('stop');
      } else {
        $('#debug').html('');
        this.modeFunction('run');
      }
    },

    changeFontSize: function(sz) {
      this.settings.fontSize = parseInt(this.settings.fontSize) + sz;
    },

    toggleSettingsPane: function() {
      this.showSettings = !this.showSettings;
    },

    showHelp: function() {
      gui.Shell.openExternal(this.$options.mode.referenceURL);
    }

  }

};

windowstate.load(function(createNewProject){
  if (createNewProject) {
    var app = new Vue(appConfig);
  } else {
    gui.Window.get().close(true);
  }
});
<|endoftext|>


<commit_before>var myApp = angular.module('myApp', ['ui.router'])
    .config(function ($stateProvider, $urlRouterProvider) {
        $urlRouterProvider.otherwise('/plans/focus/0');

        $stateProvider
            .state('plans', {
                url: '/plans',
                templateUrl: 'partials/plans.html',
                controller: function ($scope, $location) {
                    $scope.plans = [
                        'Plan 1',
                        'Plan 2',
                        'Plan 3',
                        'Plan 4',
                        'Plan 5'
                    ];

                    $scope.createPlan = function (planName) {
                        $scope.plans.push(planName);
                        $scope.setFocusPlan($scope.plans.length - 1);
                        $location.path('/');
                    };
                }
            })
            .state('plans.focus', {
                url: '/focus/:planId',
                templateUrl: 'partials/plans.focus.html',
                controller: function ($scope, $stateParams) {
                    $scope.focusPlan = $scope.plans[$stateParams.planId];
                }
            })
            .state('plans.create', {
                url: '/create',
                templateUrl: 'partials/plans.create.html',
                controller: function ($timeout) {
                    $timeout(function () {
                        document.getElementById('plan-name').focus();
                    }, 0);
                }
            });
    });
<commit_msg>Quick fix for stupidity<commit_after>var myApp = angular.module('myApp', ['ui.router'])
    .config(function ($stateProvider, $urlRouterProvider) {
        $urlRouterProvider.otherwise('/plans/focus/0');

        $stateProvider
            .state('plans', {
                url: '/plans',
                templateUrl: 'partials/plans.html',
                controller: function ($scope, $state, $location) {
                    $scope.plans = [
                        'Plan 1',
                        'Plan 2',
                        'Plan 3',
                        'Plan 4',
                        'Plan 5'
                    ];

                    $scope.createPlan = function (planName) {
                        $scope.plans.push(planName);
                        $state.go('plans.focus', {planId: $scope.plans.length - 1});
                    };
                }
            })
            .state('plans.focus', {
                url: '/focus/:planId',
                templateUrl: 'partials/plans.focus.html',
                controller: function ($scope, $stateParams) {
                    $scope.focusPlan = $scope.plans[$stateParams.planId];
                }
            })
            .state('plans.create', {
                url: '/create',
                templateUrl: 'partials/plans.create.html',
                controller: function ($timeout) {
                    $timeout(function () {
                        document.getElementById('plan-name').focus();
                    }, 0);
                }
            });
    });
<|endoftext|>


<commit_before>const electron = require('electron');

const app = electron.app;
const Shell = electron.shell;
const Menu = electron.Menu;
const auto_updater = require('./auto_update.js');
const is = require('electron-is');
const open = require('open');

var checkForUpdates = {
  label: 'Check for Updates…',
  id: 'updateCheck',
  click: function (item, focusedWindow) {
    auto_updater.check();
  }
};
var sep = {
  type: 'separator'
};
var prefs = {
  label: 'Preferences…',
  accelerator: 'CmdOrCtrl+,',
  click: function (item, focusedWindow, event) {
    if (focusedWindow) {
      focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.openSettings(); }', true);
    }
  }
};
var show_config = {
  label: 'Reveal Config File…',
  click: function (item, focusedWindow, event) {
    Shell.showItemInFolder(app.config.path);
  }
};

module.exports = {
  setup: function () {
    var app_menu = {
      label: app.getName(),
      id: 'app',
      submenu: [
        {
          role: 'about'
        },
        checkForUpdates,
        sep,
        prefs,
        sep,
        show_config,
        sep,
        {
          role: 'services',
          submenu: []
        },
        sep,
        {
          role: 'hide'
        }, {
          role: 'hideothers'
        }, {
          role: 'unhide'
        },
        sep,
        {
          role: 'quit'
        }
      ]
    };
    var file_menu = {
      label: 'File',
      submenu: [
        {
          role: 'close'
        },
        sep,
        {
          label: 'Open in Browser',
          click: function(item, focusedWindow, event) {
            var url = focusedWindow ?
              focusedWindow.webContents.getURL() :
              app.config.get('host');
            require('electron').shell.openExternal(url);
          }
        }, {
          label: 'Open Browser Tab…',
          accelerator: 'CmdOrCtrl+T',
          click: function(item, focusedWindow, event) {
            open('http://');
          }
        },
        sep,
        {
          label: 'Add a Network…',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.addNetwork(); }', true);
            }
          }
        },
        sep,
        {
          label: 'Jump to…',
          accelerator: 'CmdOrCtrl+K',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.channelSwitcher.toggle(); }', true);
            }
          }
        }, {
          label: 'Select Next in List',
          accelerator: 'Alt+Down',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.sidebar.bufferList.selectNextBuffer(); }', true);
            }
          }
        }, {
          label: 'Select Previous in List',
          accelerator: 'Alt+Up',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.sidebar.bufferList.selectPreviousBuffer(); }', true);
            }
          }
        }, {
          label: 'Select Next Unread in List',
          accelerator: 'Alt+Shift+Down',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.sidebar.bufferList.selectNextUnreadBuffer(); }', true);
            }
          }
        }, {
          label: 'Select Previous Unread in List',
          accelerator: 'Alt+Shift+Up',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.sidebar.bufferList.selectPreviousUnreadBuffer(); }', true);
            }
          }
        },
        sep,
        {
          label: 'Mark Current as Read',
          accelerator: 'Esc',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSION && SESSION.currentBuffer) { SESSION.currentBuffer.read(); }', true);
            }
          }
        }, {
          label: 'Mark All as Read',
          accelerator: 'Shift+Esc',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSION) { SESSION.markAllAsRead(); }', true);
            }
          }
        },
        sep,
        {
          label: 'Upload a File…',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSION && SESSION.currentBuffer) { SESSION.currentBuffer.trigger("uploadPrompt"); }', true);
            }
          }
        }, {
          label: 'Start a Pastebin…',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSION && SESSION.currentBuffer) { SESSION.currentBuffer.trigger("pastePrompt"); }', true);
            }
          }
        }
      ]
    };
    if (!is.macOS()) {
      file_menu.submenu.push(sep);
      file_menu.submenu.push(prefs);
      file_menu.submenu.push(show_config);
      file_menu.submenu.push(sep);
      file_menu.submenu.push({
        label: 'Show in Tray',
        type:  'checkbox',
        checked: Boolean(app.config.get('tray')),
        click: function(item, focusedWindow, event) {
          app.config.set('tray', item.checked);
          app.toggleTray();
        }
      });
      file_menu.submenu.push({
        role: 'quit'
      });
    }

    var spellingItem;
    var spellingSubItem = {
      type: 'checkbox',
      id: 'spellingItem',
      checked: app.config.get('spellcheck'),
      click: function(item, focusedWindow, event) {
        app.config.set('spellcheck', item.checked);
        app.toggleSpellcheck();
      }
    };
    if (is.macOS()) {
      spellingSubItem.label = 'Check Spelling While Typing';
      spellingItem = {
        label: 'Spelling and Grammar',
        submenu: [spellingSubItem]
      };
    } else {
      spellingSubItem.label = 'Check spelling as you type';
      spellingItem = spellingSubItem;
    }
    var edit_menu = {
      label: 'Edit',
      id: 'edit',
      submenu: [
        {
          role: 'undo'
        }, {
          role: 'redo'
        },
        sep,
        {
          role: 'cut'
        }, {
          role: 'copy'
        }, {
          role: 'delete'
        }, {
          role: 'paste'
        }, {
          role: 'pasteandmatchstyle'
        }, {
          role: 'selectall'
        },
        sep,
        spellingItem
      ]
    };

    var view_menu = {
      label: 'View',
      id: 'view',
      submenu: [
        {
          label: 'Reload',
          accelerator: 'CmdOrCtrl+R',
          click: function(item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.reloadIgnoringCache();
            } else {
              app.emit('activate', {
                reload: true
              });
            }
          }
        },
        sep,
        {
          role: 'togglefullscreen'
        }, {
          label: 'Actual Size',
          id: 'zoomReset',
          enabled: false,
          accelerator: 'CmdOrCtrl+0',
          click: function(item, focusedWindow, event) {
            app.resetZoom();
          }
        }, {
          label: 'Zoom In',
          id: 'zoomIn',
          enabled: false,
          accelerator: 'CmdOrCtrl+=',
          click: function(item, focusedWindow, event) {
            app.zoomIn();
          }
        }, {
          label: 'Zoom Out',
          id: 'zoomOut',
          enabled: false,
          accelerator: 'CmdOrCtrl+-',
          click: function(item, focusedWindow, event) {
            app.zoomOut();
          }
        },
        sep,
        {
          label: 'Developer Tools',
          accelerator: (function() {
            if (is.macOS()) {
              return 'Cmd+Alt+I';
            } else {
              return 'Ctrl+Shift+I';
            }
          })(),
          click: function(item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.openDevTools();
            }
          }
        }
      ]
    };
    if (!is.macOS()) {
      view_menu.submenu.splice(2, 0, {
        label: 'Toggle Menu Bar',
        accelerator: 'Ctrl+Shift+M',
        click: function(item, focusedWindow, event) {
          if (focusedWindow.isMenuBarAutoHide()) {
            app.config.set('menu-bar', true);
            app.toggleMenuBar(focusedWindow);
          } else {
            app.config.set('menu-bar', false);
            app.toggleMenuBar(focusedWindow);
          }
        }
      });
    }

    var go_menu = {
      label: 'Go',
      id: 'history',
      submenu: [
        {
          label: 'Back',
          accelerator: 'CmdOrCtrl+[',
          enabled: false,
          id: 'backMenu',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.goBack();
            }
          }
        }, {
          label: 'Forward',
          accelerator: 'CmdOrCtrl+]',
          enabled: false,
          id: 'fwdMenu',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.goForward();
            }
          }
        },
        sep,
        {
          label: 'File Uploads',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.files.show(); }', true);
            }
          }
        }, {
          label: 'Pastebins',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.pastebins.show(); }', true);
            }
          }
        }
      ]
    };

    var window_menu = {
      label: 'Window',
      role: 'window',
      submenu: [
        {
          role: 'minimize'
        },
        sep,
        {
          role: 'front'
        },
        sep,
        {
          label: 'Main Window',
          accelerator: 'CmdOrCtrl+1',
          click: function (item, focusedWindow, event) {
            app.emit('activate');
          }
        }
      ]
    };

    var help_menu = {
      role: 'help',
      submenu: [
        {
          label: 'Keyboard Shortcuts',
          accelerator: 'CmdOrCtrl+/',
          click: function (item, focusedWindow, event) {
            focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.navigate("?/shortcuts", {trigger: true}); }', true);
          }
        },
        sep,
        {
          label: 'Known Issues',
          click: function(item, focusedWindow, event) {
            require('electron').shell.openExternal('https://github.com/irccloud/irccloud-desktop/issues');
          }
        }
      ]
    };
    if (!is.macOS()) {
      help_menu.submenu.push(checkForUpdates);
    }

    var menu;
    if (is.macOS()) {
      menu = Menu.buildFromTemplate([app_menu, file_menu, edit_menu, view_menu, go_menu, window_menu, help_menu]);
    } else {
      menu = Menu.buildFromTemplate([file_menu, edit_menu, view_menu, go_menu, help_menu]);
    }
    Menu.setApplicationMenu(menu);
    return menu;
  },
  setup_tray: function(app){
    var menu;
    menu = Menu.buildFromTemplate([
      {
        role: 'quit'
      }
    ]);
    return menu;
  }
};
<commit_msg>Add a show log file menu item<commit_after>const electron = require('electron');

const app = electron.app;
const Shell = electron.shell;
const Menu = electron.Menu;
const auto_updater = require('./auto_update.js');
const is = require('electron-is');
const open = require('open');

var checkForUpdates = {
  label: 'Check for Updates…',
  id: 'updateCheck',
  click: function (item, focusedWindow) {
    auto_updater.check();
  }
};
var sep = {
  type: 'separator'
};
var prefs = {
  label: 'Preferences…',
  accelerator: 'CmdOrCtrl+,',
  click: function (item, focusedWindow, event) {
    if (focusedWindow) {
      focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.openSettings(); }', true);
    }
  }
};
var show_config = {
  label: 'Reveal Config File…',
  click: function (item, focusedWindow, event) {
    Shell.showItemInFolder(app.config.path);
  }
};
var show_log = {
  label: 'Reveal Log File…',
  click: function (item, focusedWindow, event) {
    Shell.showItemInFolder(log.findLogPath());
  }
};

module.exports = {
  setup: function () {
    var app_menu = {
      label: app.getName(),
      id: 'app',
      submenu: [
        {
          role: 'about'
        },
        checkForUpdates,
        sep,
        prefs,
        sep,
        show_config,
        show_log,
        sep,
        {
          role: 'services',
          submenu: []
        },
        sep,
        {
          role: 'hide'
        }, {
          role: 'hideothers'
        }, {
          role: 'unhide'
        },
        sep,
        {
          role: 'quit'
        }
      ]
    };
    var file_menu = {
      label: 'File',
      submenu: [
        {
          role: 'close'
        },
        sep,
        {
          label: 'Open in Browser',
          click: function(item, focusedWindow, event) {
            var url = focusedWindow ?
              focusedWindow.webContents.getURL() :
              app.config.get('host');
            require('electron').shell.openExternal(url);
          }
        }, {
          label: 'Open Browser Tab…',
          accelerator: 'CmdOrCtrl+T',
          click: function(item, focusedWindow, event) {
            open('http://');
          }
        },
        sep,
        {
          label: 'Add a Network…',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.addNetwork(); }', true);
            }
          }
        },
        sep,
        {
          label: 'Jump to…',
          accelerator: 'CmdOrCtrl+K',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.channelSwitcher.toggle(); }', true);
            }
          }
        }, {
          label: 'Select Next in List',
          accelerator: 'Alt+Down',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.sidebar.bufferList.selectNextBuffer(); }', true);
            }
          }
        }, {
          label: 'Select Previous in List',
          accelerator: 'Alt+Up',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.sidebar.bufferList.selectPreviousBuffer(); }', true);
            }
          }
        }, {
          label: 'Select Next Unread in List',
          accelerator: 'Alt+Shift+Down',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.sidebar.bufferList.selectNextUnreadBuffer(); }', true);
            }
          }
        }, {
          label: 'Select Previous Unread in List',
          accelerator: 'Alt+Shift+Up',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.sidebar.bufferList.selectPreviousUnreadBuffer(); }', true);
            }
          }
        },
        sep,
        {
          label: 'Mark Current as Read',
          accelerator: 'Esc',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSION && SESSION.currentBuffer) { SESSION.currentBuffer.read(); }', true);
            }
          }
        }, {
          label: 'Mark All as Read',
          accelerator: 'Shift+Esc',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSION) { SESSION.markAllAsRead(); }', true);
            }
          }
        },
        sep,
        {
          label: 'Upload a File…',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSION && SESSION.currentBuffer) { SESSION.currentBuffer.trigger("uploadPrompt"); }', true);
            }
          }
        }, {
          label: 'Start a Pastebin…',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSION && SESSION.currentBuffer) { SESSION.currentBuffer.trigger("pastePrompt"); }', true);
            }
          }
        }
      ]
    };
    if (!is.macOS()) {
      file_menu.submenu.push(sep);
      file_menu.submenu.push(prefs);
      file_menu.submenu.push(show_config);
      file_menu.submenu.push(show_log);
      file_menu.submenu.push(sep);
      file_menu.submenu.push({
        label: 'Show in Tray',
        type:  'checkbox',
        checked: Boolean(app.config.get('tray')),
        click: function(item, focusedWindow, event) {
          app.config.set('tray', item.checked);
          app.toggleTray();
        }
      });
      file_menu.submenu.push({
        role: 'quit'
      });
    }

    var spellingItem;
    var spellingSubItem = {
      type: 'checkbox',
      id: 'spellingItem',
      checked: app.config.get('spellcheck'),
      click: function(item, focusedWindow, event) {
        app.config.set('spellcheck', item.checked);
        app.toggleSpellcheck();
      }
    };
    if (is.macOS()) {
      spellingSubItem.label = 'Check Spelling While Typing';
      spellingItem = {
        label: 'Spelling and Grammar',
        submenu: [spellingSubItem]
      };
    } else {
      spellingSubItem.label = 'Check spelling as you type';
      spellingItem = spellingSubItem;
    }
    var edit_menu = {
      label: 'Edit',
      id: 'edit',
      submenu: [
        {
          role: 'undo'
        }, {
          role: 'redo'
        },
        sep,
        {
          role: 'cut'
        }, {
          role: 'copy'
        }, {
          role: 'delete'
        }, {
          role: 'paste'
        }, {
          role: 'pasteandmatchstyle'
        }, {
          role: 'selectall'
        },
        sep,
        spellingItem
      ]
    };

    var view_menu = {
      label: 'View',
      id: 'view',
      submenu: [
        {
          label: 'Reload',
          accelerator: 'CmdOrCtrl+R',
          click: function(item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.reloadIgnoringCache();
            } else {
              app.emit('activate', {
                reload: true
              });
            }
          }
        },
        sep,
        {
          role: 'togglefullscreen'
        }, {
          label: 'Actual Size',
          id: 'zoomReset',
          enabled: false,
          accelerator: 'CmdOrCtrl+0',
          click: function(item, focusedWindow, event) {
            app.resetZoom();
          }
        }, {
          label: 'Zoom In',
          id: 'zoomIn',
          enabled: false,
          accelerator: 'CmdOrCtrl+=',
          click: function(item, focusedWindow, event) {
            app.zoomIn();
          }
        }, {
          label: 'Zoom Out',
          id: 'zoomOut',
          enabled: false,
          accelerator: 'CmdOrCtrl+-',
          click: function(item, focusedWindow, event) {
            app.zoomOut();
          }
        },
        sep,
        {
          label: 'Developer Tools',
          accelerator: (function() {
            if (is.macOS()) {
              return 'Cmd+Alt+I';
            } else {
              return 'Ctrl+Shift+I';
            }
          })(),
          click: function(item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.openDevTools();
            }
          }
        }
      ]
    };
    if (!is.macOS()) {
      view_menu.submenu.splice(2, 0, {
        label: 'Toggle Menu Bar',
        accelerator: 'Ctrl+Shift+M',
        click: function(item, focusedWindow, event) {
          if (focusedWindow.isMenuBarAutoHide()) {
            app.config.set('menu-bar', true);
            app.toggleMenuBar(focusedWindow);
          } else {
            app.config.set('menu-bar', false);
            app.toggleMenuBar(focusedWindow);
          }
        }
      });
    }

    var go_menu = {
      label: 'Go',
      id: 'history',
      submenu: [
        {
          label: 'Back',
          accelerator: 'CmdOrCtrl+[',
          enabled: false,
          id: 'backMenu',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.goBack();
            }
          }
        }, {
          label: 'Forward',
          accelerator: 'CmdOrCtrl+]',
          enabled: false,
          id: 'fwdMenu',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.goForward();
            }
          }
        },
        sep,
        {
          label: 'File Uploads',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.files.show(); }', true);
            }
          }
        }, {
          label: 'Pastebins',
          click: function (item, focusedWindow, event) {
            if (focusedWindow) {
              focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.pastebins.show(); }', true);
            }
          }
        }
      ]
    };

    var window_menu = {
      label: 'Window',
      role: 'window',
      submenu: [
        {
          role: 'minimize'
        },
        sep,
        {
          role: 'front'
        },
        sep,
        {
          label: 'Main Window',
          accelerator: 'CmdOrCtrl+1',
          click: function (item, focusedWindow, event) {
            app.emit('activate');
          }
        }
      ]
    };

    var help_menu = {
      role: 'help',
      submenu: [
        {
          label: 'Keyboard Shortcuts',
          accelerator: 'CmdOrCtrl+/',
          click: function (item, focusedWindow, event) {
            focusedWindow.webContents.executeJavaScript('if (SESSIONVIEW) { SESSIONVIEW.navigate("?/shortcuts", {trigger: true}); }', true);
          }
        },
        sep,
        {
          label: 'Known Issues',
          click: function(item, focusedWindow, event) {
            require('electron').shell.openExternal('https://github.com/irccloud/irccloud-desktop/issues');
          }
        }
      ]
    };
    if (!is.macOS()) {
      help_menu.submenu.push(checkForUpdates);
    }

    var menu;
    if (is.macOS()) {
      menu = Menu.buildFromTemplate([app_menu, file_menu, edit_menu, view_menu, go_menu, window_menu, help_menu]);
    } else {
      menu = Menu.buildFromTemplate([file_menu, edit_menu, view_menu, go_menu, help_menu]);
    }
    Menu.setApplicationMenu(menu);
    return menu;
  },
  setup_tray: function(app){
    var menu;
    menu = Menu.buildFromTemplate([
      {
        role: 'quit'
      }
    ]);
    return menu;
  }
};
<|endoftext|>


<commit_before>/*
 * Memcing
 * Copyright (c) 2014 Fatih Cetinkaya (http://github.com/cmfatih/memcing)
 * For the full copyright and license information, please view the LICENSE.txt file.
 */

// repl module implements REPL.

// Init reqs
/* jslint node: true */
'use strict';

var readline = require('readline');

// Init the module
exports = module.exports = function(options, cacheInstance) {

  // Init vars
  var config      = {isDebug: false},
      start,      // start - function
      completer   // auto complete - function
  ;

  // Check params
  if(typeof cacheInstance !== 'object') throw new Error('Invalid cache instance!');

  if(options) {
    if(options.isDebug === true) config.isDebug = true;
  }

  // Starts repl
  start = function start() {

    // Init vars
    var rl = readline.createInterface({
      input:      process.stdin,
      output:     process.stdout,
      completer:  completer,
      terminal:   true
    });

    rl.setPrompt('> '); // set prompt
    rl.prompt();

    // line event
    rl.on('line', function(line) {

      // Check the input
      if(!line.trim()) { rl.prompt(); return; }

      // Execute the command
      var cp = cacheInstance.execCmd(line);

      // for debug
      if(config.isDebug === true) {
        if(cp.cmd) {
          console.log({cmd: cp.cmd, cmdArgs: cp.cmdArgs});

          if(cp.cmd == 'stats') {
            console.log(JSON.stringify(cp.cmdRes, null, 2));
          } else {
            console.log(cp.cmdRes);
          }

          // NOTE: Do not vacuum here for dump command.
        }
        if(cp.cmdRes) {
          if(cp.cmdRes.error) console.log('ERROR: ' + cp.cmdRes.error);
          if(cp.cmdRes.exit && cp.cmdRes.exit === true) process.exit(0);
        }
        rl.prompt();
        return;
      }

      switch(cp.cmd) {
        case 'get':
          console.log((cp.cmdRes && cp.cmdRes.val) ? cp.cmdRes.val : '');
          break;
        case 'set':
        case 'add':
          console.log((cp.cmdRes.error) ? 'ERROR' : 'STORED');
          break;
        case 'delete':
          console.log((cp.cmdRes) ? 'DELETED' : 'ERROR');
          break;
        case 'drop':
          console.log((cp.cmdRes) ? 'DROPPED' : 'ERROR');
          break;
        case 'increment':
        case 'decrement':
          console.log((cp.cmdRes.error) ? 'ERROR' : cp.cmdRes.val);
          break;
        case 'dump':

          // Cleanup expired entries
          cacheInstance.vacuum({exp: true});

          if(cacheInstance.numOfEntry() > 0) {
            var cData     = cp.cmdRes,
                cDataLen  = cacheInstance.numOfEntry(),
                cDataCnt  = 0,
                cChar     = ''
            ;
            console.log('[');
            for(var key in cData) {
              cDataCnt++;
              cChar = (cDataCnt < cDataLen) ? ',' : '';
              console.log(JSON.stringify(cData[key]) + cChar);
            }
            console.log(']');
          } else {
            console.log('[]');
          }
          break;
        case 'stats':
          console.log(JSON.stringify(cp.cmdRes, null, 2));
          break;
        case 'vacuum':
          console.log(cp.cmdRes);
          break;
        case 'exit':
          if(cp.cmdRes.exit && cp.cmdRes.exit === true) process.exit(0);
          break;
        default:
          if(cp.cmdRes && cp.cmdRes.error) {
            console.log('ERROR: ' + cp.cmdRes.error);
          } else {
            console.log('ERROR: Unexpected command!' + cp);
          }
      }

      rl.prompt();
    });

    // close event
    rl.on('close', function() {
      process.exit(0);
    });

    // SIGINT (^C) event
    rl.on('SIGINT', function() {
      rl.clearLine(process.stdin, 0); // clear prompt
      rl.question('All the cached data will be gone. Are you sure? (y/N) ', function(answer) {
        if(answer.match(/^(y|yes)$/i)) {
          rl.close();
        } else {
          rl.prompt();
        }
      });
    });
  };

  // Auto complete function for readline.
  completer = function completer(line) {

    // Init vars
    var lineF         = line.trim(),
        cmdList,      // cache command list
        lineCmds,     // commands on the line
        lastCmd,      // last command on the line
        fltrdCmds,    // filtered commands
        matchingCmds  // matching commands
    ;

    if(!lineF) {
      matchingCmds = cacheInstance.cmdList;
    } else {
      lineCmds  = lineF.split(' ');
      lastCmd   = lineCmds.pop();

      if(lineCmds.length > 0) {
        cmdList = cacheInstance.cmdList.map(function(value) { return lineCmds.join(' ') + ' ' + value; });
      } else {
        cmdList = cacheInstance.cmdList;
      }

      fltrdCmds = cmdList.filter(function(element) { return element.indexOf(lineF) === 0; });

      if(!fltrdCmds.length) {
        matchingCmds  = null;
      } else if(fltrdCmds.length === 1) {
        matchingCmds  = [fltrdCmds[0] + ' '];
      } else {
        if(lineCmds.length > 0) {
          fltrdCmds   = fltrdCmds.map(function(value) { return value.split(' ').pop(); });
        }

        matchingCmds  = fltrdCmds;
      }
    }

    return [matchingCmds, line];
  };

  // Return
  return {
    start: start
  };
};<commit_msg>Add notes<commit_after>/*
 * Memcing
 * Copyright (c) 2014 Fatih Cetinkaya (http://github.com/cmfatih/memcing)
 * For the full copyright and license information, please view the LICENSE.txt file.
 */

// repl module implements Read-Eval-Print-Loop (REPL).
//
// TODO: Command result messages should be change.

// Init reqs
/* jslint node: true */
'use strict';

var readline = require('readline');

// Init the module
exports = module.exports = function(options, cacheInstance) {

  // Init vars
  var config    = {isDebug: false},
      start,    // start - function
      completer // auto complete - function
  ;

  // Check params
  if(typeof cacheInstance !== 'object') throw new Error('Invalid cache instance!');

  if(options) {
    if(options.isDebug === true) config.isDebug = true;
  }

  // Starts repl
  start = function start() {

    // Init vars
    var rl = readline.createInterface({
      input:      process.stdin,
      output:     process.stdout,
      completer:  completer,
      terminal:   true
    });

    rl.setPrompt('> '); // set prompt
    rl.prompt();

    // line event
    rl.on('line', function(line) {

      // Check the input
      if(!line.trim()) { rl.prompt(); return; }

      // Execute the command
      var cp = cacheInstance.execCmd(line);

      // for debug
      if(config.isDebug === true) {
        if(cp.cmd) {
          console.log({cmd: cp.cmd, cmdArgs: cp.cmdArgs});

          if(cp.cmd == 'stats') {
            console.log(JSON.stringify(cp.cmdRes, null, 2));
          } else {
            console.log(cp.cmdRes);
          }

          // NOTE: Do not vacuum here for dump command. It is good for debugging.
        }

        if(cp.cmdRes) {
          if(cp.cmdRes.error) console.log('ERROR: ' + cp.cmdRes.error);
          if(cp.cmdRes.exit && cp.cmdRes.exit === true) process.exit(0);
        }

        rl.prompt();
        return;
      }

      switch(cp.cmd) {
        case 'get':
          console.log((cp.cmdRes && cp.cmdRes.val) ? cp.cmdRes.val : '');
          break;
        case 'set':
        case 'add':
          console.log((cp.cmdRes.error) ? 'ERROR' : 'STORED');
          break;
        case 'delete':
          console.log((cp.cmdRes) ? 'DELETED' : 'ERROR');
          break;
        case 'drop':
          console.log((cp.cmdRes) ? 'DROPPED' : 'ERROR');
          break;
        case 'increment':
        case 'decrement':
          console.log((cp.cmdRes.error) ? 'ERROR' : cp.cmdRes.val);
          break;
        case 'dump':
          // Cleanup expired entries
          cacheInstance.vacuum({exp: true});

          if(cacheInstance.numOfEntry() > 0) {
            var cData     = cp.cmdRes,
                cDataLen  = cacheInstance.numOfEntry(),
                cDataCnt  = 0,
                cChar     = ''
            ;
            console.log('[');
            for(var key in cData) {
              cDataCnt++;
              cChar = (cDataCnt < cDataLen) ? ',' : '';
              console.log(JSON.stringify(cData[key]) + cChar);
            }
            console.log(']');
          } else {
            console.log('[]');
          }
          break;
        case 'stats':
          console.log(JSON.stringify(cp.cmdRes, null, 2));
          break;
        case 'vacuum':
          console.log(cp.cmdRes);
          break;
        case 'exit':
          if(cp.cmdRes.exit && cp.cmdRes.exit === true) process.exit(0);
          break;
        default:
          if(cp.cmdRes && cp.cmdRes.error) {
            console.log('ERROR: ' + cp.cmdRes.error);
          } else {
            console.log('ERROR: Unexpected command!' + cp);
          }
      }

      rl.prompt();
    });

    // close event
    rl.on('close', function() {
      process.exit(0);
    });

    // SIGINT (^C) event
    rl.on('SIGINT', function() {
      rl.clearLine(process.stdin, 0); // clear prompt
      rl.question('All the cached data will be gone. Are you sure? (y/N) ', function(answer) {
        if(answer.match(/^(y|yes)$/i)) {
          rl.close();
        } else {
          rl.prompt();
        }
      });
    });
  };

  // Auto complete function for readline.
  completer = function completer(line) {

    // Init vars
    var lineF         = line.trim(),
        cmdList,      // cache command list
        lineCmds,     // commands on the line
        lastCmd,      // last command on the line
        fltrdCmds,    // filtered commands
        matchingCmds  // matching commands
    ;

    if(!lineF) {
      matchingCmds  = cacheInstance.cmdList;
    } else {
      lineCmds      = lineF.split(' ');
      lastCmd       = lineCmds.pop();

      if(lineCmds.length > 0) {
        cmdList     = cacheInstance.cmdList.map(function(value) { return lineCmds.join(' ') + ' ' + value; });
      } else {
        cmdList     = cacheInstance.cmdList;
      }

      fltrdCmds = cmdList.filter(function(element) { return element.indexOf(lineF) === 0; });

      if(!fltrdCmds.length) {
        matchingCmds  = null;
      } else if(fltrdCmds.length === 1) {
        matchingCmds  = [fltrdCmds[0] + ' '];
      } else {
        if(lineCmds.length > 0) {
          fltrdCmds   = fltrdCmds.map(function(value) { return value.split(' ').pop(); });
        }

        matchingCmds  = fltrdCmds;
      }
    }

    return [matchingCmds, line];
  };

  // Return
  return {
    start: start
  };
};<|endoftext|>


<commit_before>var read = require('./read');
var chalk = require('chalk');
var inquirer = require('inquirer');
var getGitName = require('./get-git-name');
var log = require('./log');
var fs = require('fs-extra');

var sign = module.exports = {
  isLogged: () => {
    return !!sign.env || !!(sign.env = read('./.env.json', true));
  },
  login: (cb) => {
    var logged = sign.isLogged();
    var message = logged ?
      'You\'re signed as ' + chalk.green(sign.env.username) + '. Press enter to skip or enter a new username:' :
      'Not signed. Press enter to use the default username or enter a new one:';
    inquirer.prompt([{
      name: 'username',
      type: 'input',
      message: message,
      default: logged ? sign.env.username : getGitName(),
      validate: x => /^[0-9a-zA-Z._\-]+$/.test(x) || 'Only 0-9, a-z, A-Z and . _ - allowed.'
    }], answers => {
      if (logged && sign.env.username === answers.username) {
        cb();
        return;
      }
      // TODO: check if duplicate.
      sign.env = answers;
      fs.writeJsonSync('./.env.json', answers);
      cb();
    });
  }
};
<commit_msg>Create the participant's directory<commit_after>var read = require('./read');
var chalk = require('chalk');
var inquirer = require('inquirer');
var getGitName = require('./get-git-name');
var log = require('./log');
var fs = require('fs-extra');

function isDuplicate(username) {
  var userpath = './participants/' + username;
  try {
    fs.statSync(userpath);
    return true;
  } catch (e) {
    fs.mkdirSync(userpath);
    return false;
  }
}

var sign = module.exports = {
  isLogged: () => {
    return !!sign.env || !!(sign.env = read('./.env.json', true));
  },
  login: (cb) => {
    var logged = sign.isLogged();
    var message = logged ?
      'You\'re signed as ' + chalk.green(sign.env.username) + '. Press enter to skip or enter a new username:' :
      'Not signed. Press enter to use the default username or enter a new one:';
    inquirer.prompt([{
      name: 'username',
      type: 'input',
      message: message,
      default: logged ? sign.env.username : getGitName(),
      validate: x => /^[0-9a-zA-Z._\-]+$/.test(x) || 'Only 0-9, a-z, A-Z and . _ - allowed.'
    }], answers => {
      if (logged && sign.env.username === answers.username) {
        cb();
        return;
      }
      log.info(
        isDuplicate(answers.username) ? 'Login as existing user %s.' : 'Create new user %s.',
        chalk.green(answers.username)
      );
      fs.writeJsonSync('./.env.json', sign.env = answers);
      cb();
    });
  }
};
<|endoftext|>


<commit_before>// ==UserScript==
// @name         15 macro's for Agar.io :)
// @version      0.3
// @description  15 macro's for feeding, linesplits, tricksplits, etc. And enables show mass and skip stats by default :)
// @author       Megabyte918
// @match        http://agar.io/*
// @match        http://old.ogarul.io/*
// ==/UserScript==
window.addEventListener('keydown', keydown);
window.addEventListener('keyup', keyup);
document.getElementById("nick").maxLength = "100";

//List instructions
var i = document.getElementById("instructions");
i.innerHTML += "Press & hold W for macro feed";
i.innerHTML += "Press Shift to split 4x";
i.innerHTML += "Press A or 3 to split 3x";
i.innerHTML += "Press D or 2 to split 2x";
i.innerHTML += "Press S or 1 to split 1x";
i.innerHTML += "Press H for horizontal linesplit position";
i.innerHTML += "Press V for vertical linesplit position";
i.innerHTML += "Press g and j to move left and right during a horizontal linesplit";
i.innerHTML += "Press y and n to move up and down during a vertical linesplit";

//Auto-enable show mass/skip stats
//IMPORTANT: You must uncheck showmass/skip stats first then recheck them for it to auto save every time
function autoSet() {
    var m = document.getElementById('showMass'), s = document.getElementById('skipStats');
    if (document.getElementById("overlays").style.display!= "none") {
        document.getElementById("settings").style.display = "block";
        if (m.checked) {m.click();} m.click(); //Show mass
        if (s.checked) {s.click();} s.click(); //Skip stats
    } else setTimeout(autoSet, 100);
}

//Load macros
var canFeed = false;
function keydown(event) {
    switch (event.keyCode) {
        case 87: //Feeding Macro (w)
            canFeed = true;
            feed();
            break;
        case 16: //Tricksplit Macro (shift)
            var e = 35;
            for (var e2 = 0; e2 < 4; e2++) {
                setTimeout(split, e);
                e *= 2;
            }
            break;
        case 52: //Tricksplit Macro (4)
            var four = 35;
            for (var four2 = 0; four2 < 4; four2++) {
                setTimeout(split, four);
                four *= 2;
            }
            break;
        case 65: //Triplesplit Macro (a)
            var a = 35;
            for (var a2 = 0; a2 < 3; a2++) {
                setTimeout(split, a);
                a *= 2;
            }
            break;
        case 51: //Triplesplit Macro (3)
            var three = 35;
            for (var three2 = 0; three2 < 3; three2++) {
                setTimeout(split, three);
                three *= 2;
            }
            break;
        case 68: //Doublesplit Macro (d)
            split();
            setTimeout(split, 50);
            break;
        case 50: //Doublesplit Macro (2)
            split();
            setTimeout(split, 50);
            break;
        case 83: //Space Macro (s)
            split();
            break;
        case 49: //Space Macro (1)
            split();
            break;
        case 72: //Horizontal linesplit (h)
            X = window.innerWidth / 2;
            Y = window.innerHeight / 2;
            $("canvas").trigger($.Event("mousemove", {clientX: X, clientY: Y}));
            break;
        case 86: //Vertical linesplit (v)
            X = window.innerWidth / 2;
            Y = window.innerHeight / 2.006;
            $("canvas").trigger($.Event("mousemove", {clientX: X, clientY: Y}));
            break;
        case 71: //Move left Horizontal (g)
            X = window.innerWidth / 2.4;
            Y = window.innerHeight / 2;
            $("canvas").trigger($.Event("mousemove", {clientX: X, clientY: Y}));
            break;
        case 74: //Move right Horizontal (j)
            X = window.innerWidth / 1.6;
            Y = window.innerHeight / 2;
            $("canvas").trigger($.Event("mousemove", {clientX: X, clientY: Y}));
            break;
        case 80: // Move up Veritcal (y)
            X = window.innerWidth / 2;
            Y = window.innerHeight / 2.4;
            $("canvas").trigger($.Event("mousemove", {clientX: X, clientY: Y}));
            break;
        case 78: // Move down Veritcal (n)
            X = window.innerWidth / 2;
            Y = window.innerHeight / 1.6;
            $("canvas").trigger($.Event("mousemove", {clientX: X, clientY: Y}));
            break;
    }
}

//When a player lets go of W stop feeding
function keyup(event) {
    if (event.keyCode == 87)
        canFeed = false;
}

//Alias for W key
function feed() {
    if (canFeed) {
        window.onkeydown({keyCode: 87});
        window.onkeyup({keyCode: 87});
        setTimeout(feed, 0);
    }
}

//Alias for space
function split() {
    $("body").trigger($.Event("keydown", { keyCode: 32}));
    $("body").trigger($.Event("keyup", { keyCode: 32}));
}
<commit_msg>Popsplit<commit_after>// ==UserScript==
// @name         15 macro's for Agar.io :)
// @version      0.3
// @description  15 macro's for feeding, linesplits, tricksplits, etc. And enables show mass and skip stats by default :)
// @author       Megabyte918
// @match        http://agar.io/*
// @match        http://old.ogarul.io/*
// ==/UserScript==
window.addEventListener('keydown', keydown);
window.addEventListener('keyup', keyup);
document.getElementById("nick").maxLength = "100";

//List instructions
var i = document.getElementById("instructions");
i.innerHTML += "Press & hold W for macro feed";
i.innerHTML += "Press Shift to split 4x";
i.innerHTML += "Press A or 3 to split 3x";
i.innerHTML += "Press D or 2 to split 2x";
i.innerHTML += "Press S or 1 to split 1x";
i.innerHTML += "Press H for horizontal linesplit position";
i.innerHTML += "Press V for vertical linesplit position";
i.innerHTML += "Press g and j to move left and right during a horizontal linesplit";
i.innerHTML += "Press y and n to move up and down during a vertical linesplit";

//Auto-enable show mass/skip stats
//IMPORTANT: You must uncheck showmass/skip stats first then recheck them for it to auto save every time
function autoSet() {
    var m = document.getElementById('showMass'), s = document.getElementById('skipStats');
    if (document.getElementById("overlays").style.display!= "none") {
        document.getElementById("settings").style.display = "block";
        if (m.checked) {m.click();} m.click(); //Show mass
        if (s.checked) {s.click();} s.click(); //Skip stats
    } else setTimeout(autoSet, 100);
}

//Load macros
var canFeed = false;
function keydown(event) {
    switch (event.keyCode) {
        case 87: //Feeding Macro (w)
            canFeed = true;
            feed();
            break;
        case 16: //Tricksplit Macro (shift)
            var e = 35;
            for (var e2 = 0; e2 < 4; e2++) {
                setTimeout(split, e);
                e *= 2;
            }
            break;
        case 52: //Tricksplit Macro (4)
            var four = 35;
            for (var four2 = 0; four2 < 4; four2++) {
                setTimeout(split, four);
                four *= 2;
            }
            break;
        case 65: //Triplesplit Macro (a)
            var a = 35;
            for (var a2 = 0; a2 < 3; a2++) {
                setTimeout(split, a);
                a *= 2;
            }
            break;
        case 51: //Triplesplit Macro (3)
            var three = 35;
            for (var three2 = 0; three2 < 3; three2++) {
                setTimeout(split, three);
                three *= 2;
            }
            break;
        case 68: //Doublesplit Macro (d)
            split();
            setTimeout(split, 50);
            break;
        case 50: //Doublesplit Macro (2)
            split();
            setTimeout(split, 50);
            break;
        case 83: //Popsplit Macro (s) For people that are too lazy to press space twice and instead use the double split macro and complain when they fail their popsplits. Don't worry your not alone :)
            var time1 = Math.random() * (350 - 200) + 200;
            split();
            setTimeout(split, time1);
            break;
        case 72: //Horizontal linesplit (h)
            X = window.innerWidth / 2;
            Y = window.innerHeight / 2;
            $("canvas").trigger($.Event("mousemove", {clientX: X, clientY: Y}));
            break;
        case 86: //Vertical linesplit (v)
            X = window.innerWidth / 2;
            Y = window.innerHeight / 2.006;
            $("canvas").trigger($.Event("mousemove", {clientX: X, clientY: Y}));
            break;
        case 71: //Move left Horizontal (g)
            X = window.innerWidth / 2.4;
            Y = window.innerHeight / 2;
            $("canvas").trigger($.Event("mousemove", {clientX: X, clientY: Y}));
            break;
        case 74: //Move right Horizontal (j)
            X = window.innerWidth / 1.6;
            Y = window.innerHeight / 2;
            $("canvas").trigger($.Event("mousemove", {clientX: X, clientY: Y}));
            break;
        case 80: // Move up Veritcal (y)
            X = window.innerWidth / 2;
            Y = window.innerHeight / 2.4;
            $("canvas").trigger($.Event("mousemove", {clientX: X, clientY: Y}));
            break;
        case 78: // Move down Veritcal (n)
            X = window.innerWidth / 2;
            Y = window.innerHeight / 1.6;
            $("canvas").trigger($.Event("mousemove", {clientX: X, clientY: Y}));
            break;
    }
}

//When a player lets go of W stop feeding
function keyup(event) {
    if (event.keyCode == 87)
        canFeed = false;
}

//Alias for W key
function feed() {
    if (canFeed) {
        window.onkeydown({keyCode: 87});
        window.onkeyup({keyCode: 87});
        setTimeout(feed, 0);
    }
}

//Alias for space
function split() {
    $("body").trigger($.Event("keydown", { keyCode: 32}));
    $("body").trigger($.Event("keyup", { keyCode: 32}));
}
<|endoftext|>


<commit_before>/**
 * @author evaisse
 */
var restoreConsole = require('jsonconsole')();
var dotenv = require('dotenv').config({ silent: true });
var nconf = require('nconf');
var os = require('os');
var util = require('util');

var defaultConfig = {

    "NODE_ENV": {
        alias: "env",
        description: 'Global node env',
        default: "production"
    },

    "OUTPUT_VERBOSE": {
        alias: "verbose",
        description: 'Enable debug level output',
        default: false,
        type: "boolean",
    },

    "h": {
        description: "Show this help usage",
        type: "boolean",
    },

    "V": {
        description: "Show current version",
        type: "boolean"
    },

};

/*
    Build environment regarding
        1) process.env
        2) dotenv() overrdie regarding .env file on root dir
        3) argv values
 */
var buildEnvironmentConfig = function () {

    /*
        Assign env keys to config only assign
        config that match a CONSTANT_FORM_PATTERN LIKE_THAT
     */
    nconf.env(Object.keys(process.args))
         .argv(process.args);

    /*
        Show help if needed
     */
    if (nconf.get('h')) {
        process.stdout.write(nconf.stores.argv.help());
        process.exit();
    }

    /*
        Stop command for some args
     */
    if (nconf.get('V')) {
        process.stdout.write(require(__dirname + '/package.json').version + os.EOL);
        process.exit();
    }

    /*
        rewrite only env keys
     */
    Object.keys(nconf.get())
          .filter((k) => k.match(/[A-Z0-9][A-Z0-9_]+[A-Z0-9]/))
          .forEach((key) => process.env[key] = nconf.get(key));

}

module.exports = function () {

    process.args = process.args || defaultConfig;

    process.once('ready', buildEnvironmentConfig);

    return function () {
        process.emit('boot');
        process.emit('ready');
        console.log('Start application with configuration ' + util.inspect(process.env));
        process.emit('start');
    };

};
<commit_msg>Remove debug<commit_after>/**
 * @author evaisse
 */
var restoreConsole = require('jsonconsole')();
var dotenv = require('dotenv').config({ silent: true });
var nconf = require('nconf');
var os = require('os');
var util = require('util');

var defaultConfig = {

    "NODE_ENV": {
        alias: "env",
        description: 'Global node env',
        default: "production"
    },

    "OUTPUT_VERBOSE": {
        alias: "verbose",
        description: 'Enable debug level output',
        default: false,
        type: "boolean",
    },

    "h": {
        description: "Show this help usage",
        type: "boolean",
    },

    "V": {
        description: "Show current version",
        type: "boolean"
    },

};

/*
    Build environment regarding
        1) process.env
        2) dotenv() overrdie regarding .env file on root dir
        3) argv values
 */
var buildEnvironmentConfig = function () {

    /*
        Assign env keys to config only assign
        config that match a CONSTANT_FORM_PATTERN LIKE_THAT
     */
    nconf.env(Object.keys(process.args))
         .argv(process.args);

    /*
        Show help if needed
     */
    if (nconf.get('h')) {
        process.stdout.write(nconf.stores.argv.help());
        process.exit();
    }

    /*
        Stop command for some args
     */
    if (nconf.get('V')) {
        process.stdout.write(require(__dirname + '/package.json').version + os.EOL);
        process.exit();
    }

    /*
        rewrite only env keys
     */
    Object.keys(nconf.get())
          .filter((k) => k.match(/[A-Z0-9][A-Z0-9_]+[A-Z0-9]/))
          .forEach((key) => process.env[key] = nconf.get(key));

}

module.exports = function () {

    process.args = process.args || defaultConfig;

    process.once('ready', buildEnvironmentConfig);

    return function () {
        process.emit('boot');
        process.emit('ready');
        process.emit('start');
    };

};
<|endoftext|>


<commit_before>// Hi Welcome to WFI by David Jones / RackFX, LLC
var fs = require('fs');
var wfi = {}

wfi.infoByFilename = function(filename, cb){
  var stats = fs.statSync(filename)
  var buffer = new Buffer(40);  // first 40 bytes are RIFF header
  fs.open(filename, 'r', function(err, fd) {
    if(err) return cb(err);  // error probably TODO:check this!

    // ex error -
    // { [Error: ENOENT: no such file or directory, open './test.wav'] errno: -2, code: 'ENOENT', syscall: 'open', path: './test.wav' }
    var read_result = {}

    // this a list of sequenced bytes in the 40 byte header. This builds the read_result object.
    //  Property name / Data type / Length
    var reads = [
      ['riff_head', 'string', 4],
      ['chunk_size','uinteger', 4],
      ['wave_identifier', 'string', 4],
      ['fmt_identifier', 'string', 4],
      ['subchunk_size','integer',4],
      ['audio_format','integer',2],
      ['num_channels','integer',2],
      ['sample_rate','integer',4],
      ['byte_rate','integer',4],
      ['block_align','integer',2],
      ['bits_per_sample','integer',2],
      //['uhm','integer',2],
      ['data_identifier','string', 4],
      //['sub_chunk2_size', 'integer', 4],

    ]
    fs.read(fd, buffer, 0, 40, 0, function(err, num) {

      var i=0;
      var pointer = 0;
      function read_wav(){
        var read = reads[i];

        i++;
        if(read[1]=='string'){
          read_result[read[0]] = buffer.toString('ascii', pointer , pointer + read[2]);
          pointer = pointer + read[2];   // pointer = pointer plus # bytes
        }
        else if(read[1]=='integer'){

          read_result[read[0]] = buffer.readUInt16LE(pointer, read[2])
          pointer = pointer + read[2];
        }
        else if(read[1]=='uinteger'){

          read_result[read[0]] = buffer.readInt32LE(pointer, read[2])
          pointer = pointer + read[2];
        }
        if(i < reads.length) { return read_wav()}
        else { return post_process(); }

      }
      //console.log(i)
      read_wav();
    }); // end fs.read

    function post_process(){
      var error = false;
      var invalid_reasons = []

      if (read_result.riff_head != "RIFF")  invalid_reasons.push("Expected \"RIFF\" string at 0" )
      if (read_result.wave_identifier != "WAVE") invalid_reasons.push("Expected \"WAVE\" string at 4")
      if (read_result.fmt_identifier != "fmt ") invalid_reasons.push("Expected \"fmt \" string at 8")
      if (read_result.audio_format != 1) invalid_reasons.push("Unknwon format: "+read_result.audio_format)
      if ((read_result.chunk_size + 8) !== stats.size) invalid_reasons.push("chunk_size does not match file size")
      //if ((read_result.data_identifier) != "data") invalid_reasons.push("Expected data identifier at the end of the header")

      if (invalid_reasons.length > 0) error = true;

      if (error) return cb({
        error : true,
        invalid_reasons: invalid_reasons,
        header: read_result,
        stats: stats
      });

      cb(null, {
        header: read_result,
        stats: stats,
        duration: ((stats.size - 8) / (read_result.sample_rate * read_result.num_channels * (read_result.bits_per_sample / 8)))
      });
    }
    function calculateDuration(o){
      //(1697504) / (44100 * 2 * (16/8))
    }
  });
}
module.exports = wfi;
<commit_msg>duraton git push<commit_after>// Hi Welcome to WFI by David Jones / RackFX, LLC
var fs = require('fs');
var wfi = {}

wfi.infoByFilename = function(filename, cb){
  var stats = fs.statSync(filename)
  var buffer = new Buffer(40);  // first 40 bytes are RIFF header
  fs.open(filename, 'r', function(err, fd) {
    if(err) return cb(err);  // error probably TODO:check this!

    // ex error -
    // { [Error: ENOENT: no such file or directory, open './test.wav'] errno: -2, code: 'ENOENT', syscall: 'open', path: './test.wav' }
    var read_result = {}

    // this a list of sequenced bytes in the 40 byte header. This builds the read_result object.
    //  Property name / Data type / Length
    var reads = [
      ['riff_head', 'string', 4],
      ['chunk_size','uinteger', 4],
      ['wave_identifier', 'string', 4],
      ['fmt_identifier', 'string', 4],
      ['subchunk_size','integer',4],
      ['audio_format','integer',2],
      ['num_channels','integer',2],
      ['sample_rate','integer',4],
      ['byte_rate','integer',4],
      ['block_align','integer',2],
      ['bits_per_sample','integer',2],
      //['uhm','integer',2],
      ['data_identifier','string', 4],
      //['sub_chunk2_size', 'integer', 4],

    ]
    fs.read(fd, buffer, 0, 40, 0, function(err, num) {

      var i=0;
      var pointer = 0;
      function read_wav(){
        var read = reads[i];

        i++;
        if(read[1]=='string'){
          read_result[read[0]] = buffer.toString('ascii', pointer , pointer + read[2]);
          pointer = pointer + read[2];   // pointer = pointer plus # bytes
        }
        else if(read[1]=='integer'){

          read_result[read[0]] = buffer.readUInt16LE(pointer, read[2])
          pointer = pointer + read[2];
        }
        else if(read[1]=='uinteger'){

          read_result[read[0]] = buffer.readInt32LE(pointer, read[2])
          pointer = pointer + read[2];
        }
        if(i < reads.length) { return read_wav()}
        else { return post_process(); }

      }
      //console.log(i)
      read_wav();
    }); // end fs.read

    function post_process(){
      var error = false;
      var invalid_reasons = []

      if (read_result.riff_head != "RIFF")  invalid_reasons.push("Expected \"RIFF\" string at 0" )
      if (read_result.wave_identifier != "WAVE") invalid_reasons.push("Expected \"WAVE\" string at 4")
      if (read_result.fmt_identifier != "fmt ") invalid_reasons.push("Expected \"fmt \" string at 8")
      if (read_result.audio_format != 1) invalid_reasons.push("Unknwon format: "+read_result.audio_format)
      if ((read_result.chunk_size + 8) !== stats.size) invalid_reasons.push("chunk_size does not match file size")
      //if ((read_result.data_identifier) != "data") invalid_reasons.push("Expected data identifier at the end of the header")

      if (invalid_reasons.length > 0) error = true;

      if (error) return cb({
        error : true,
        invalid_reasons: invalid_reasons,
        header: read_result,
        stats: stats
      });

      cb(null, {
        header: read_result,
        stats: stats,
        duration: ((stats.size - 8) / (read_result.sample_rate * read_result.num_channels * (read_result.bits_per_sample / 8)))
      });
    }
    function calculateDuration(o){
      //(1697504) / (44100 * 2 * (16/8))
    }
  });
}
module.exports = wfi;
<|endoftext|>