<commit_before>/**
 * @module gulpfile
 * @license MIT
 * @version 2018/03/26
 */

'use strict';

const util = require('util');
const gulp = require('gulp');
const rimraf = require('del');
const cssnano = require('cssnano');
const uglify = require('uglify-es');
const chokidar = require('chokidar');
const concat = require('gulp-concat');
const plumber = require('gulp-plumber');
const css = require('@nuintun/gulp-css');
const cmd = require('@nuintun/gulp-cmd');
const cmdAddons = require('@nuintun/gulp-cmd-plugins');
const cssAddons = require('@nuintun/gulp-css-plugins');
const switchStream = require('@nuintun/switch-stream');
const { join, relative, dirname, extname, resolve } = require('path');

const { chalk, logger } = cmd;
const { through } = switchStream;

const ROOT = process.cwd();
const RUNTIME = ['static/develop/loader/sea.js'];
const CSS_LOADER = '/static/develop/loader/css-loader.js';
const IGNORE = new Set(['static/develop/js/base/jquery/**/*', CSS_LOADER.slice(1)]);

// Plumber configure
const plumberOpts = {
  errorHandler(error) {
    return logger.error(inspectError(error));
  }
};

/**
 * @function unixify
 * @param {string} path
 */
function unixify(path) {
  return path.replace(/\\/g, '/');
}

/**
 * @function progress
 * @description Show progress logger
 */
function progress() {
  return through(function(vinyl, encoding, next) {
    const file = chalk.reset.green(unixify(join(vinyl.base, vinyl.relative)));
    const info = chalk.reset.reset('Building ') + file;

    logger.info(info);

    next(null, vinyl);
  });
}

/**
 * @function inspectError
 * @param {Error} error
 * @returns {string}
 */
function inspectError(error) {
  error = util.inspect(error, { colors: true });
  error = error.replace(/^\{\s*|\}\s*$/g, '');

  return `${error}\x07`;
}

/**
 * @function toBuffer
 * @param {string} string
 * @returns {Buffer}
 */
const toBuffer = Buffer.from ? Buffer.from : string => new Buffer(string);

/**
 * @function compress
 * @description Compress javascript file
 */
function compress() {
  return switchStream(
    vinyl => {
      return extname(vinyl.path)
        .slice(1)
        .toLowerCase();
    },
    {
      js: through(function(vinyl, encoding, next) {
        const path = vinyl.path;
        const contents = vinyl.contents.toString();
        const options = { ecma: 5, ie8: true, mangle: { eval: true } };
        const result = uglify.minify({ [path]: contents }, options);

        if (result.error) {
          logger.error(inspectError(result.error));
        } else {
          vinyl.contents = toBuffer(result.code);
        }

        next(null, vinyl);
      }),
      css: through(async function(vinyl, encoding, next) {
        try {
          const result = await cssnano.process(vinyl.contents.toString(), { safe: true });

          vinyl.contents = toBuffer(result.css);
        } catch (error) {
          logger.error(inspectError(error));
        }

        next(null, vinyl);
      })
    }
  );
}

/**
 * @function watch
 * @description Files watch
 * @param {string|Array<string>} glob
 * @param {Object} options
 * @param {Function} callabck
 */
function watch(glob, options, callabck) {
  if (typeof options === 'function') {
    callabck = options;
    options = {};
  }

  // Ignore initial add event
  options.ignoreInitial = true;
  // Ignore permission errors
  options.ignorePermissionErrors = true;

  // Get watcher
  const watcher = chokidar.watch(glob, options);

  // Bind event
  if (callabck) {
    watcher.on('all', callabck);
  }

  // Return watcher
  return watcher;
}

/**
 * @function getAlias
 */
function getAlias() {
  delete require.cache[require.resolve('./alias.json')];

  return require('./alias.json');
}

/**
 * @function onpath
 * @description Resolve css path
 * @param {string} prop
 * @param {string} path
 * @param {string} referer
 * @returns {string}
 */
function onpath(prop, path, referer) {
  if (/^(?:[a-z0-9.+-]+:)?\/\/|^data:\w+?\/\w+?[,;]/i.test(path)) {
    return path;
  }

  if (!path.startsWith('/')) {
    path = join(dirname(referer), path);
    path = '/' + unixify(relative(ROOT, path));
  }

  return path.replace('/static/develop/', '/static/product/');
}

/**
 * @function resolveMap
 * @description Resolve map path
 * @param {string} path
 * @returns {string}
 */
function resolveMap(path) {
  return path.replace('/static/develop/', '/static/product/');
}

/**
 * @function clean
 */
function clean() {
  return rimraf('static/product');
}

/**
 * @function runtime
 * @param {boolean} product
 */
function runtime(product) {
  return function runtime() {
    // Loader file
    return gulp
      .src(RUNTIME, { base: 'static/develop/loader', nodir: true })
      .pipe(plumber(plumberOpts))
      .pipe(progress())
      .pipe(concat('sea.js'))
      .pipe(product ? compress() : through())
      .pipe(gulp.dest('static/product/loader'));
  };
}

/**
 * @function images
 * @param {boolean} product
 */
function images(product) {
  return function images() {
    return gulp
      .src('static/develop/images/**/*', { base: 'static/develop/images', nodir: true })
      .pipe(plumber(plumberOpts))
      .pipe(progress())
      .pipe(gulp.dest('static/product/images'));
  };
}

/**
 * @function script
 * @param {boolean} product
 */
function script(product) {
  let uid = 0;
  const manifest = new Map();
  const skipCache = new Map();

  function skipMinifyId(path) {
    if (skipCache.has(path)) return skipCache.get(path);

    const src = unixify(path);
    const skipped = src.includes('/jquery.js') || src.includes('/css-loader.js');

    skipCache.set(path, skipped);

    return skipped;
  }

  function map(path, resolved) {
    if (product && !skipMinifyId(resolved)) {
      if (manifest.has(resolved)) return manifest.get(resolved);

      const id = String(uid++);

      manifest.set(resolved, id);

      return id;
    }

    return resolveMap(path);
  }

  function common() {
    return gulp
      .src('static/develop/js/view/common.js', { base: 'static/develop/js', nodir: true, allowEmpty: true })
      .pipe(plumber(plumberOpts))
      .pipe(progress())
      .pipe(
        cmd({
          map: (path, resolved) => {
            if (product) {
              IGNORE.add(resolved);
            }

            return map(path, resolved);
          },
          combine: product,
          alias: getAlias(),
          indent: product ? 0 : 2,
          base: 'static/develop/js',
          ignore: product ? [...IGNORE] : [],
          css: { onpath, loader: CSS_LOADER },
          plugins: [cmdAddons({ minify: product, sourceMaps: !product })]
        })
      )
      .pipe(
        through((vinyl, encoding, next) => {
          const path = vinyl.path;
          const id = manifest.has(path) ? manifest.get(path) : '/static/product/js/view/common.js';
          const entry = Buffer.from(`${product ? '' : '\n\n'}seajs.use(${JSON.stringify(id)});`);

          vinyl.contents = Buffer.concat([vinyl.contents, entry]);

          return next(null, vinyl);
        })
      )
      .pipe(gulp.dest('static/product/js'));
  }

  function script() {
    return gulp
      .src(['static/develop/js/**/*', '!static/develop/js/view/common.js'], {
        base: 'static/develop/js',
        nodir: true
      })
      .pipe(plumber(plumberOpts))
      .pipe(progress())
      .pipe(
        cmd({
          map,
          alias: getAlias(),
          indent: product ? 0 : 2,
          base: 'static/develop/js',
          ignore: product ? [...IGNORE] : [],
          css: { onpath, loader: CSS_LOADER },
          plugins: [cmdAddons({ minify: product, sourceMaps: !product })],
          combine: module => product && unixify(module).includes('/js/view/')
        })
      )
      .pipe(
        through((vinyl, encoding, next) => {
          let id;
          const path = vinyl.path;

          if (extname(path).toLowerCase() === '.js' && /[\\/]view[\\/]/.test(path)) {
            const id = manifest.has(path)
              ? manifest.get(path)
              : ('/' + unixify(relative(ROOT, path))).replace('/static/develop/', '/static/product/');

            const entry = Buffer.from(`${product ? '' : '\n\n'}seajs.use(${JSON.stringify(id)});`);

            vinyl.contents = Buffer.concat([vinyl.contents, entry]);
          }

          return next(null, vinyl);
        })
      )
      .pipe(gulp.dest('static/product/js'));
  }

  return gulp.series(common, script);
}

/**
 * @function style
 * @param {boolean} product
 */
function style(product) {
  return function style() {
    return gulp
      .src(product ? 'static/develop/css/?(base|view)/**/*' : 'static/develop/css/**/*', {
        base: 'static/develop/css',
        nodir: true
      })
      .pipe(plumber(plumberOpts))
      .pipe(progress())
      .pipe(
        css({
          onpath,
          map: resolveMap,
          combine: product,
          plugins: [cssAddons({ minify: product })]
        })
      )
      .pipe(gulp.dest('static/product/css'));
  };
}

/**
 * @function watching
 */
function watching() {
  let bookmark = new Date();
  const base = join(process.cwd(), 'static/develop');

  /**
   * @function finish
   * @description Build finish function
   */
  function finish() {
    const now = new Date();

    logger.info(
      '%s build complete... %s',
      chalk.reset.green.bold.inverse(' √ DONE '),
      chalk.reset.green('+' + (now - bookmark) + 'ms')
    );
  }

  /**
   * @function debugWatcher
   * @param {string} event
   * @param {string} path
   */
  function debugWatcher(event, path) {
    const now = new Date();

    logger.info(
      '%s %s: %s',
      chalk.reset.green.bold.inverse(' • READ '),
      event,
      chalk.reset.green(join('static/develop', path).replace(/\\/g, '/'))
    );
  }

  // Watch js file
  watch('static/develop/js', (event, path) => {
    const rpath = relative(base, path);

    bookmark = new Date();
    event = event.toLowerCase();

    debugWatcher(event, rpath);

    if (event === 'unlink' || event === 'unlinkdir') {
      rimraf(resolve('static/product', rpath)).then(finish);
    } else {
      gulp
        .src(path, { base: 'static/develop/js' })
        .pipe(plumber(plumberOpts))
        .pipe(
          cmd({
            map: resolveMap,
            alias: getAlias(),
            plugins: [cmdAddons()],
            base: 'static/develop/js',
            css: { onpath, loader: CSS_LOADER }
          })
        )
        .pipe(gulp.dest('static/product/js'))
        .on('finish', finish);
    }
  });

  // Watch css file
  watch('static/develop/css', (event, path) => {
    const rpath = relative(base, path);

    bookmark = new Date();
    event = event.toLowerCase();

    debugWatcher(event, rpath);

    if (event === 'unlink' || event === 'unlinkdir') {
      rimraf(resolve('static/product', rpath)).then(finish);
    } else {
      gulp
        .src(path, { base: 'static/develop/css' })
        .pipe(plumber(plumberOpts))
        .pipe(
          css({
            onpath,
            map: resolveMap,
            plugins: [cssAddons()]
          })
        )
        .pipe(gulp.dest('static/product/css'))
        .on('finish', finish);
    }
  });

  // Watch image files
  watch('static/develop/images', (event, path) => {
    const rpath = relative(base, path);

    bookmark = Date.now();
    event = event.toLowerCase();

    debugWatcher(event, rpath);

    if (event === 'unlink' || event === 'unlinkdir') {
      rimraf(resolve('static/product', relative(base, path))).then(finish);
    } else {
      gulp
        .src(path, { base: 'static/develop/images' })
        .pipe(plumber(plumberOpts))
        .pipe(gulp.dest('static/product/images'))
        .on('finish', finish);
    }
  });
}

// Task default
gulp.task('default', gulp.series(clean, gulp.parallel(runtime(), images(), script(), style())));

// Task product
gulp.task('product', gulp.series(clean, gulp.parallel(runtime(true), images(true), script(true), style(true))));

// Task watch
gulp.task('watch', gulp.series('default', watching));
<commit_msg>:art: Rewrite<commit_after>/**
 * @module gulpfile
 * @license MIT
 * @version 2018/03/26
 */

'use strict';

const util = require('util');
const gulp = require('gulp');
const rimraf = require('del');
const cssnano = require('cssnano');
const uglify = require('uglify-es');
const chokidar = require('chokidar');
const concat = require('gulp-concat');
const plumber = require('gulp-plumber');
const css = require('@nuintun/gulp-css');
const cmd = require('@nuintun/gulp-cmd');
const cmdAddons = require('@nuintun/gulp-cmd-plugins');
const cssAddons = require('@nuintun/gulp-css-plugins');
const switchStream = require('@nuintun/switch-stream');
const { join, relative, dirname, extname, resolve } = require('path');

const { chalk, logger } = cmd;
const { through } = switchStream;

const ROOT = process.cwd();
const RUNTIME = ['static/develop/loader/sea.js'];
const CSS_LOADER = '/static/develop/loader/css-loader.js';
const IGNORE = new Set(['static/develop/js/base/jquery/**/*', CSS_LOADER.slice(1)]);

// Plumber configure
const plumberOpts = {
  errorHandler(error) {
    return logger.error(inspectError(error));
  }
};

/**
 * @function unixify
 * @param {string} path
 */
function unixify(path) {
  return path.replace(/\\/g, '/');
}

/**
 * @function progress
 * @description Show progress logger
 */
function progress() {
  return through(function(vinyl, encoding, next) {
    const file = chalk.reset.green(unixify(join(vinyl.base, vinyl.relative)));
    const info = chalk.reset.reset('Building ') + file;

    logger.info(info);

    next(null, vinyl);
  });
}

/**
 * @function inspectError
 * @param {Error} error
 * @returns {string}
 */
function inspectError(error) {
  error = util.inspect(error, { colors: true });
  error = error.replace(/^\{\s*|\}\s*$/g, '');

  return `${error}\x07`;
}

/**
 * @function toBuffer
 * @param {string} string
 * @returns {Buffer}
 */
const toBuffer = Buffer.from ? Buffer.from : string => new Buffer(string);

/**
 * @function compress
 * @description Compress javascript file
 */
function compress() {
  return switchStream(
    vinyl => {
      return extname(vinyl.path)
        .slice(1)
        .toLowerCase();
    },
    {
      js: through(function(vinyl, encoding, next) {
        const path = vinyl.path;
        const contents = vinyl.contents.toString();
        const options = { ecma: 5, ie8: true, mangle: { eval: true } };
        const result = uglify.minify({ [path]: contents }, options);

        if (result.error) {
          logger.error(inspectError(result.error));
        } else {
          vinyl.contents = toBuffer(result.code);
        }

        next(null, vinyl);
      }),
      css: through(async function(vinyl, encoding, next) {
        try {
          const result = await cssnano.process(vinyl.contents.toString(), { safe: true });

          vinyl.contents = toBuffer(result.css);
        } catch (error) {
          logger.error(inspectError(error));
        }

        next(null, vinyl);
      })
    }
  );
}

/**
 * @function watch
 * @description Files watch
 * @param {string|Array<string>} glob
 * @param {Object} options
 * @param {Function} callabck
 */
function watch(glob, options, callabck) {
  if (typeof options === 'function') {
    callabck = options;
    options = {};
  }

  // Ignore initial add event
  options.ignoreInitial = true;
  // Ignore permission errors
  options.ignorePermissionErrors = true;

  // Get watcher
  const watcher = chokidar.watch(glob, options);

  // Bind event
  if (callabck) {
    watcher.on('all', callabck);
  }

  // Return watcher
  return watcher;
}

/**
 * @function getAlias
 */
function getAlias() {
  delete require.cache[require.resolve('./alias.json')];

  return require('./alias.json');
}

/**
 * @function onpath
 * @description Resolve css path
 * @param {string} prop
 * @param {string} path
 * @param {string} referer
 * @returns {string}
 */
function onpath(prop, path, referer) {
  if (/^(?:[a-z0-9.+-]+:)?\/\/|^data:\w+?\/\w+?[,;]/i.test(path)) {
    return path;
  }

  if (!path.startsWith('/')) {
    path = join(dirname(referer), path);
    path = '/' + unixify(relative(ROOT, path));
  }

  return path.replace('/static/develop/', '/static/product/');
}

/**
 * @function resolveMap
 * @description Resolve map path
 * @param {string} path
 * @returns {string}
 */
function resolveMap(path) {
  return path.replace('/static/develop/', '/static/product/');
}

/**
 * @function clean
 */
function clean() {
  return rimraf('static/product');
}

/**
 * @function runtime
 * @param {boolean} product
 */
function runtime(product) {
  return function runtime() {
    // Loader file
    return gulp
      .src(RUNTIME, { base: 'static/develop/loader', nodir: true })
      .pipe(plumber(plumberOpts))
      .pipe(progress())
      .pipe(concat('sea.js'))
      .pipe(product ? compress() : through())
      .pipe(gulp.dest('static/product/loader'));
  };
}

/**
 * @function images
 * @param {boolean} product
 */
function images(product) {
  return function images() {
    return gulp
      .src('static/develop/images/**/*', { base: 'static/develop/images', nodir: true })
      .pipe(plumber(plumberOpts))
      .pipe(progress())
      .pipe(gulp.dest('static/product/images'));
  };
}

/**
 * @function script
 * @param {boolean} product
 */
function script(product) {
  let uid = 0;
  const manifest = new Map();
  const skipCache = new Map();

  function skipMinifyId(path) {
    if (skipCache.has(path)) return skipCache.get(path);

    const src = unixify(path);
    const skipped = src.includes('/jquery.js') || src.includes('/css-loader.js');

    skipCache.set(path, skipped);

    return skipped;
  }

  function map(path, resolved) {
    if (product && !skipMinifyId(resolved)) {
      if (manifest.has(resolved)) return manifest.get(resolved);

      const id = String(uid++);

      manifest.set(resolved, id);

      return id;
    }

    return resolveMap(path);
  }

  function common() {
    return gulp
      .src('static/develop/js/view/common.js', { base: 'static/develop/js', nodir: true, allowEmpty: true })
      .pipe(plumber(plumberOpts))
      .pipe(progress())
      .pipe(
        cmd({
          map: (path, resolved) => {
            if (product) {
              IGNORE.add(resolved);
            }

            return map(path, resolved);
          },
          combine: product,
          alias: getAlias(),
          indent: product ? 0 : 2,
          base: 'static/develop/js',
          ignore: product ? [...IGNORE] : [],
          css: { onpath, loader: CSS_LOADER },
          plugins: [cmdAddons({ minify: product, sourceMaps: !product })]
        })
      )
      .pipe(
        through((vinyl, encoding, next) => {
          const path = vinyl.path;
          const id = manifest.has(path) ? manifest.get(path) : '/static/product/js/view/common.js';
          const entry = Buffer.from(`${product ? '' : '\n\n'}seajs.use(${JSON.stringify(id)});`);

          vinyl.contents = Buffer.concat([vinyl.contents, entry]);

          return next(null, vinyl);
        })
      )
      .pipe(gulp.dest('static/product/js'));
  }

  function script() {
    return gulp
      .src(['static/develop/js/**/*', '!static/develop/js/view/common.js'], {
        base: 'static/develop/js',
        nodir: true
      })
      .pipe(plumber(plumberOpts))
      .pipe(progress())
      .pipe(
        cmd({
          map,
          alias: getAlias(),
          indent: product ? 0 : 2,
          base: 'static/develop/js',
          ignore: product ? [...IGNORE] : [],
          css: { onpath, loader: CSS_LOADER },
          plugins: [cmdAddons({ minify: product, sourceMaps: !product })],
          combine: module => product && unixify(module).includes('/js/view/')
        })
      )
      .pipe(
        through((vinyl, encoding, next) => {
          let id;
          const path = vinyl.path;

          if (extname(path).toLowerCase() === '.js' && /[\\/]view[\\/]/.test(path)) {
            const id = manifest.has(path)
              ? manifest.get(path)
              : ('/' + unixify(relative(ROOT, path))).replace('/static/develop/', '/static/product/');

            const entry = Buffer.from(`${product ? '' : '\n\n'}seajs.use(${JSON.stringify(id)});`);

            vinyl.contents = Buffer.concat([vinyl.contents, entry]);
          }

          return next(null, vinyl);
        })
      )
      .pipe(gulp.dest('static/product/js'));
  }

  return gulp.series(common, script);
}

/**
 * @function style
 * @param {boolean} product
 */
function style(product) {
  return function style() {
    return gulp
      .src(product ? 'static/develop/css/?(base|view)/**/*' : 'static/develop/css/**/*', {
        base: 'static/develop/css',
        nodir: true
      })
      .pipe(plumber(plumberOpts))
      .pipe(progress())
      .pipe(
        css({
          onpath,
          map: resolveMap,
          combine: product,
          plugins: [cssAddons({ minify: product })]
        })
      )
      .pipe(gulp.dest('static/product/css'));
  };
}

/**
 * @function watching
 */
function watching() {
  let bookmark = new Date();
  const base = join(process.cwd(), 'static/develop');

  /**
   * @function finish
   * @description Build finish function
   */
  function finish() {
    const now = new Date();

    logger.info(
      '%s build complete... %s',
      chalk.reset.green.bold.inverse(' √ DONE '),
      chalk.reset.green('+' + (now - bookmark) + 'ms')
    );
  }

  /**
   * @function debugWatcher
   * @param {string} event
   * @param {string} path
   */
  function debugWatcher(event, path) {
    const now = new Date();

    logger.info(
      '%s %s: %s',
      chalk.reset.green.bold.inverse(' • READ '),
      event,
      chalk.reset.green(join('static/develop', path).replace(/\\/g, '/'))
    );
  }

  // Watch js file
  watch('static/develop/js', (event, path) => {
    const rpath = relative(base, path);

    bookmark = new Date();
    event = event.toLowerCase();

    debugWatcher(event, rpath);

    if (event === 'unlink' || event === 'unlinkdir') {
      rimraf(resolve('static/product', rpath)).then(finish);
    } else {
      gulp
        .src(path, { base: 'static/develop/js' })
        .pipe(plumber(plumberOpts))
        .pipe(
          cmd({
            map: resolveMap,
            alias: getAlias(),
            plugins: [cmdAddons()],
            base: 'static/develop/js',
            css: { onpath, loader: CSS_LOADER }
          })
        )
        .pipe(
          through((vinyl, encoding, next) => {
            let id;
            const path = vinyl.path;

            if (extname(path).toLowerCase() === '.js' && /[\\/]view[\\/]/.test(path)) {
              const id = ('/' + unixify(relative(ROOT, path))).replace('/static/develop/', '/static/product/');
              const entry = Buffer.from(`\n\nseajs.use(${JSON.stringify(id)});`);

              vinyl.contents = Buffer.concat([vinyl.contents, entry]);
            }

            return next(null, vinyl);
          })
        )
        .pipe(gulp.dest('static/product/js'))
        .on('finish', finish);
    }
  });

  // Watch css file
  watch('static/develop/css', (event, path) => {
    const rpath = relative(base, path);

    bookmark = new Date();
    event = event.toLowerCase();

    debugWatcher(event, rpath);

    if (event === 'unlink' || event === 'unlinkdir') {
      rimraf(resolve('static/product', rpath)).then(finish);
    } else {
      gulp
        .src(path, { base: 'static/develop/css' })
        .pipe(plumber(plumberOpts))
        .pipe(
          css({
            onpath,
            map: resolveMap,
            plugins: [cssAddons()]
          })
        )
        .pipe(gulp.dest('static/product/css'))
        .on('finish', finish);
    }
  });

  // Watch image files
  watch('static/develop/images', (event, path) => {
    const rpath = relative(base, path);

    bookmark = Date.now();
    event = event.toLowerCase();

    debugWatcher(event, rpath);

    if (event === 'unlink' || event === 'unlinkdir') {
      rimraf(resolve('static/product', relative(base, path))).then(finish);
    } else {
      gulp
        .src(path, { base: 'static/develop/images' })
        .pipe(plumber(plumberOpts))
        .pipe(gulp.dest('static/product/images'))
        .on('finish', finish);
    }
  });
}

// Task default
gulp.task('default', gulp.series(clean, gulp.parallel(runtime(), images(), script(), style())));

// Task product
gulp.task('product', gulp.series(clean, gulp.parallel(runtime(true), images(true), script(true), style(true))));

// Task watch
gulp.task('watch', gulp.series('default', watching));
<|endoftext|>


<commit_before>import { Applications } from '../../applications/applications.js';
import { Bundles } from '../bundles.js';
import { BUNDLE_DIR, SYNC_EXEC_OPTIONS, ASYNC_EXEC_OPTIONS } from '../utils.js';

// NPM PACKAGES
import { cd, rm, mkdir, exec, test } from 'shelljs';

Bundles.on('stored', Meteor.bindEnvironment((file, storeName) => {
  const APPLICATION_DIR  = `${BUNDLE_DIR}/${file._id}`;

  // REMOVE OLD APPLICATION
  rm('-rf', APPLICATION_DIR);

  // CREATE NEW APPLICATION DIR
  mkdir(APPLICATION_DIR);

  // GO TO BUNDLE DIR
  cd(BUNDLE_DIR);

  // EXTRACT
  exec(`tar -xvzf ${file._id}.tar.gz -C ${file._id} --strip 1`, SYNC_EXEC_OPTIONS);

  // CD SERVER PACKAGES
  cd(`${file._id}/programs/server`);

  // NPM CORE PACKAGES INSTALL
  const npm = exec('npm install', ASYNC_EXEC_OPTIONS);

  npm.stdout.on('end', Meteor.bindEnvironment(() => {

    // FIX BCRYPT
    if (test('-e', 'npm/npm-bcrypt')) {
      exec('npm install bcrypt', SYNC_EXEC_OPTIONS);
      rm('-rf', 'npm/npm-bcrypt');
    }

    // FIX BSON
    if (test('-e', 'npm/cfs_gridfs')) {
      cd('npm/cfs_gridfs/node_modules/mongodb/node_modules/bson');
      exec('make', SYNC_EXEC_OPTIONS);
    }

    const application = Applications.findOne({
      bundleId: file._id
    });

   /*
    * IMPORTANT!!!!
    * After installation is completed it will be updated before
    * the start if the application fix begin.
    */
    application.setStatus(3);
  }));
}));
<commit_msg>fixes bundle upload completed<commit_after>import { Applications } from '../../applications/applications.js';
import { Bundles } from '../bundles.js';
import { BUNDLE_DIR, SYNC_EXEC_OPTIONS, ASYNC_EXEC_OPTIONS } from '../utils.js';

// NPM PACKAGES
import { cd, rm, mkdir, exec, test } from 'shelljs';

Bundles.on('stored', Meteor.bindEnvironment((file, storeName) => {
  const APPLICATION_DIR  = `${BUNDLE_DIR}/${file._id}`;

  // REMOVE OLD APPLICATION
  rm('-rf', APPLICATION_DIR);

  // CREATE NEW APPLICATION DIR
  mkdir(APPLICATION_DIR);

  // GO TO BUNDLE DIR
  cd(BUNDLE_DIR);

  // EXTRACT
  exec(`tar -xvzf ${file._id}.tar.gz -C ${file._id} --strip 1`, SYNC_EXEC_OPTIONS);

  // CD SERVER PACKAGES
  cd(`${file._id}/programs/server`);

  // NPM CORE PACKAGES INSTALL
  const npm = exec('npm install', ASYNC_EXEC_OPTIONS);

  npm.stdout.on('end', Meteor.bindEnvironment(() => {

    // FIX BCRYPT
    if (test('-e', 'npm/npm-bcrypt')) {
      rm('-rf', 'npm/npm-bcrypt');
      exec('npm install bcrypt', SYNC_EXEC_OPTIONS);
    }

    // FIX BSON
    if (test('-e', 'npm/cfs_gridfs')) {
      rm('-rf', 'npm/cfs_gridfs/node_modules/mongodb/node_modules/bson');
      exec('npm install bson', SYNC_EXEC_OPTIONS);
    }

    const application = Applications.findOne({
      bundleId: file._id
    });

   /*
    * IMPORTANT!!!!
    * After installation is completed it will be updated before
    * the start if the application fix begin.
    */
    application.setStatus(3);
  }));
}));
<|endoftext|>


<commit_before>'use strict';

var _ = require('underscore');
var async = require('async');
var utils = require('../utils');

var Resource = require('./Resource');
var InstanceResource = require('./InstanceResource');

// ==============================================
// Collection Resource
// ==============================================
function wrapAsyncCallToAllPages(coll, func, args, callbackWrapper){
  var page = _.pick(coll, [
    'href', 'query', 'offset', 'limit', 'items',
    'dataStore', 'instanceConstructor']);

  var callback = args.pop();

  function getNextPage(page, callback) {
    // there are no next page
    if (page.items.length < page.limit) {
      return callback();
    }

    //we've fully exhausted the current page.  There could be another one on the server, so
    //we have to execute another query to continue to the next page if one exists:
    var nextQuery = utils.shallowCopy(page.query, {});
    nextQuery.offset = page.offset + page.items.length;
    nextQuery.limit = 100;

    page.dataStore.getResource(page.href, nextQuery, page.instanceConstructor,
      function onNextPage(err, collectionResource) {
        if (err) {
          return callback(err);
        }
        (typeof setImmediate !== 'undefined' ?
          setImmediate : process.nextTick)(function(){
          callback(null, collectionResource);
        });
      });
  }

  function worker(task, cb){
    if (!task.collection.items || !task.collection.items.length){
      return cb();
    }

    async.parallel([
      function(parallel_cb){
        if (callbackWrapper.isDone){
          return parallel_cb();
        }

        var callArgs = Array.prototype
          .concat(
            [task.collection.items],
            !!callbackWrapper.wrapPageArgs ? callbackWrapper.wrapPageArgs(args) : args,
            callbackWrapper.wrapPageCallback(parallel_cb));
        func.apply(this, callArgs);
      },
      function(parallel_cb){
        if (callbackWrapper.isDone){
          return parallel_cb();
        }

        getNextPage(task.collection, function(err, nextPage){
          if (err || !nextPage){
            return parallel_cb(err);
          }

          q.push({collection: nextPage});
          parallel_cb();
        });
      }
    ], cb);

  }

  var q = async.queue(worker, 1);
  q.drain = callbackWrapper.wrapCallback(callback);
  q.push({ collection: page });
}

function ensureInstanceResources(items, InstanceConstructor, dataStore) {

  var InstanceCtor = utils.valueOf(InstanceConstructor, InstanceResource);

  if (!items || items.length === 0 || items[0] instanceof InstanceCtor /* already converted */) {
    return items;
  }

  var convertedItems = [];

  for (var i = 0; i < items.length; i++) {
    var obj = items[i];
    //we have to call instantiate via a require statement to avoid a circular dependency
    //(instantiate references CollectionResource):
    var converted = require('./ResourceFactory').instantiate(InstanceCtor, obj, null, dataStore);
    convertedItems.push(converted);
  }

  return convertedItems;
}

function CollectionResource(/*data, query, InstanceCtor, dataStore*/) {

  var args = Array.prototype.slice.call(arguments);

  var data = args[0];
  var dataStore = args[args.length - 1];
  var query = null;
  var InstanceCtor = InstanceResource; //default for generic resource instances

  //check if query params supplied:
  if (args[1] instanceof Object && !(args[1] instanceof Function)) {
    query = args[1];
  }

  //check if a type-specific resource constructor function was supplied:
  var secondToLastArg = args[args.length - 2];
  if (secondToLastArg instanceof Function && utils.isAssignableFrom(Resource, secondToLastArg)) {
    InstanceCtor = secondToLastArg;
  }

  //convert raw items array (array of objects) to an array of Instance Resources:
  if (data && data.hasOwnProperty('items') && data.items.length > 0) {
    data.items = ensureInstanceResources(data.items, InstanceCtor, dataStore);
  }

  CollectionResource.super_.apply(this, [data, dataStore]);

  Object.defineProperty(this, 'instanceConstructor', {
    get: function getInstanceConstructor() {
      return InstanceCtor;
    },
    set: function setInstanceConstructor(TheInstanceCtor) {
      InstanceCtor = TheInstanceCtor;
    }
  });
  this.instanceConstructor = InstanceCtor;

  Object.defineProperty(this, 'query', {
    get: function getQuery() {
      return query;
    },
    set: function setQuery(aQuery) {
      query = aQuery;
    }
  });
  this.query = query;
}
utils.inherits(CollectionResource, Resource);

(function extendCollectionResourceWithAsyncMethods(){

  function CallbackWrapper(argsLength){
    var res = [];

    this.wrapPageCallback = function wrapPageCallback(cb){
      return function funcCallback(err, result){
        if (argsLength === 1){
          result = err;
          err = null;
        }

        res = Array.prototype.concat.call(res, result);

        cb(err, result);
      };
    };

    this.wrapCallback = function(callback){
      return function(err){
        if (argsLength === 1){
          return callback(res);
        }
        callback(err, res);
      };
    };
  }

  function Every(){
    var res = true;
    this.wrapPageCallback = function wrapPageCallback(cb){
      return function funcCallback(result){
        res = res && result;
        cb(result);
      };
    };

    this.wrapCallback = function(callback ){
      return function(){
        callback(res);
      };
    };
  }

  function Some (){
    var res = false;
    this.isDone = false;
    var that = this;
    this.wrapPageCallback = function wrapPageCallback(cb){
      return function funcCallback(result){
        that.isDone = !!result;
        res = res || result;
        cb(result);
      };
    };

    this.wrapCallback = function(callback ){
      return function(){
        callback(res);
      };
    };
  }

  function Detect(){
    var res = null;
    var that = this;
    this.isDone = false;

    this.wrapPageCallback = function wrapPageCallback(cb){
      return function funcCallback(result){
        that.isDone = !!result;
        res = res || result;
        cb(res);
      };
    };

    this.wrapCallback = function(callback ){
      return function(){
        callback(res);
      };
    };
  }

  function Reduce(){
    var res = null;
    this.wrapPageCallback = function wrapPageCallback(cb){
      return function funcCallback(err, result){
        res = result;
        cb(err, result);
      };
    };

    this.wrapPageArgs = function(args){
      var memo = args[0];
      var iter = args[1];
      res = res || memo;
      // should be memo
      return [res, iter];
    };

    this.wrapCallback = function(callback ){
      return function(err, result){
        res = res || result;
        callback(err, res);
      };
    };
  }

  function ReduceRight(){
    var memo = null;
    var items = [];
    var iterator, callback;

    this.wrapPageCallback = function wrapPageCallback(cb){
      return cb;
    };

    this.wrapArgs = function(args){
      memo = args[0];
      iterator = args[1];
      callback = args[2];
      return [
        function(item, cb){
          items.push(item);cb();
        },
        function(){
          console.log(arguments);
        }
      ];
    };

    this.wrapCallback = function(){
      return function(err){
        if (err) {
          return callback(err);
        }

        async.reduceRight(items, memo, iterator, callback);
      };
    };
  }

  function SortBy(){
    var items = [];
    var iterator, callback;

    this.wrapPageCallback = function wrapPageCallback(cb){
      return cb;
    };

    this.wrapArgs = function(args){
      iterator = args[0];
      callback = args[1];
      return [
        function(item, cb){
          items.push(item);cb();
        },
        function(){
        }
      ];
    };

    this.wrapCallback = function(){
      return function(err){
        if (err) {
          return callback(err);
        }

        async.sortBy(items, iterator, callback);
      };
    };
  }

  var W1 = function(){ return new CallbackWrapper(1);};
  var W2 = function(){ return new CallbackWrapper(2);};

  var methods = {
    each: {wrapper: W2}, eachSeries: {wrapper: W2}, eachLimit: {wrapper: W2},
    forEach: {wrapper: W2}, forEachSeries: {wrapper: W2}, forEachLimit: {wrapper: W2},
    map: {wrapper: W2}, mapSeries: {wrapper: W2}, mapLimit:{wrapper: W2},
    filter: {wrapper: W1}, filterSeries: {wrapper: W1},
    select: {wrapper: W1}, selectSeries: {wrapper: W1},
    reject: {wrapper: W1}, rejectSeries: {wrapper: W1},
    reduce: {wrapper: Reduce}, inject: {wrapper: Reduce}, foldl: {wrapper: Reduce},
    reduceRight: {wrapper: ReduceRight, method: 'eachSeries'},
    foldr: {wrapper: ReduceRight, method: 'eachSeries'},
    detect: {wrapper: Detect},detectSeries: {wrapper: Detect},
    sortBy: {wrapper: SortBy, method: 'eachSeries'},
    some: {wrapper: Some}, any: {wrapper: Some},
    every: {wrapper: Every}, all: {wrapper: Every},
    concat: {wrapper: W2},concatSeries: {wrapper: W2}
  };

  function wrap(func, Wrapper){
    return function(){
      var args = Array.prototype.slice.call(arguments);
      var wrapper = new Wrapper();
      if (wrapper.wrapArgs){
        args = wrapper.wrapArgs(args);
      }
      wrapAsyncCallToAllPages(this, func, args, wrapper);
    };
  }

  _.each(methods, function(opts, method){
    CollectionResource.prototype[method] = wrap(async[opts.method || method], opts.wrapper);
  });
})();

module.exports = CollectionResource;<commit_msg>update iterator and callback function made optional<commit_after>'use strict';

var _ = require('underscore');
var async = require('async');
var utils = require('../utils');

var Resource = require('./Resource');
var InstanceResource = require('./InstanceResource');

// ==============================================
// Collection Resource
// ==============================================
function wrapAsyncCallToAllPages(coll, func, args, callbackWrapper){
  var page = _.pick(coll, [
    'href', 'query', 'offset', 'limit', 'items',
    'dataStore', 'instanceConstructor']);

  var callback = args.pop();

  function getNextPage(page, callback) {
    // there are no next page
    if (page.items.length < page.limit) {
      return callback();
    }

    //we've fully exhausted the current page.  There could be another one on the server, so
    //we have to execute another query to continue to the next page if one exists:
    var nextQuery = utils.shallowCopy(page.query, {});
    nextQuery.offset = page.offset + page.items.length;
    nextQuery.limit = 100;

    page.dataStore.getResource(page.href, nextQuery, page.instanceConstructor,
      function onNextPage(err, collectionResource) {
        if (err) {
          return callback(err);
        }
        (typeof setImmediate !== 'undefined' ?
          setImmediate : process.nextTick)(function(){
          callback(null, collectionResource);
        });
      });
  }

  function worker(task, cb){
    if (!task.collection.items || !task.collection.items.length){
      return cb();
    }

    async.parallel([
      function(parallel_cb){
        if (callbackWrapper.isDone){
          return parallel_cb();
        }

        var callArgs = Array.prototype
          .concat(
            [task.collection.items],
            !!callbackWrapper.wrapPageArgs ? callbackWrapper.wrapPageArgs(args) : args,
            callbackWrapper.wrapPageCallback(parallel_cb));
        func.apply(this, callArgs);
      },
      function(parallel_cb){
        if (callbackWrapper.isDone){
          return parallel_cb();
        }

        getNextPage(task.collection, function(err, nextPage){
          if (err || !nextPage){
            return parallel_cb(err);
          }

          q.push({collection: nextPage});
          parallel_cb();
        });
      }
    ], cb);

  }

  var q = async.queue(worker, 1);
  q.drain = callbackWrapper.wrapCallback(callback);
  q.push({ collection: page });
}

function ensureInstanceResources(items, InstanceConstructor, dataStore) {

  var InstanceCtor = utils.valueOf(InstanceConstructor, InstanceResource);

  if (!items || items.length === 0 || items[0] instanceof InstanceCtor /* already converted */) {
    return items;
  }

  var convertedItems = [];

  for (var i = 0; i < items.length; i++) {
    var obj = items[i];
    //we have to call instantiate via a require statement to avoid a circular dependency
    //(instantiate references CollectionResource):
    var converted = require('./ResourceFactory').instantiate(InstanceCtor, obj, null, dataStore);
    convertedItems.push(converted);
  }

  return convertedItems;
}

function CollectionResource(/*data, query, InstanceCtor, dataStore*/) {

  var args = Array.prototype.slice.call(arguments);

  var data = args[0];
  var dataStore = args[args.length - 1];
  var query = null;
  var InstanceCtor = InstanceResource; //default for generic resource instances

  //check if query params supplied:
  if (args[1] instanceof Object && !(args[1] instanceof Function)) {
    query = args[1];
  }

  //check if a type-specific resource constructor function was supplied:
  var secondToLastArg = args[args.length - 2];
  if (secondToLastArg instanceof Function && utils.isAssignableFrom(Resource, secondToLastArg)) {
    InstanceCtor = secondToLastArg;
  }

  //convert raw items array (array of objects) to an array of Instance Resources:
  if (data && data.hasOwnProperty('items') && data.items.length > 0) {
    data.items = ensureInstanceResources(data.items, InstanceCtor, dataStore);
  }

  CollectionResource.super_.apply(this, [data, dataStore]);

  Object.defineProperty(this, 'instanceConstructor', {
    get: function getInstanceConstructor() {
      return InstanceCtor;
    },
    set: function setInstanceConstructor(TheInstanceCtor) {
      InstanceCtor = TheInstanceCtor;
    }
  });
  this.instanceConstructor = InstanceCtor;

  Object.defineProperty(this, 'query', {
    get: function getQuery() {
      return query;
    },
    set: function setQuery(aQuery) {
      query = aQuery;
    }
  });
  this.query = query;
}
utils.inherits(CollectionResource, Resource);

(function extendCollectionResourceWithAsyncMethods(){

  function CallbackWrapper(argsLength){
    var res = [];

    this.wrapPageCallback = function wrapPageCallback(cb){
      return function funcCallback(err, result){
        if (argsLength === 1){
          result = err;
          err = null;
        }

        res = Array.prototype.concat.call(res, result);

        cb(err, result);
      };
    };

    this.wrapCallback = function(callback){
      return function(err){
        if (argsLength === 1){
          return callback(res);
        }
        callback(err, res);
      };
    };
  }

  function Every(){
    var res = true;
    this.wrapPageCallback = function wrapPageCallback(cb){
      return function funcCallback(result){
        res = res && result;
        cb(result);
      };
    };

    this.wrapCallback = function(callback ){
      return function(){
        callback(res);
      };
    };
  }

  function Some (){
    var res = false;
    this.isDone = false;
    var that = this;
    this.wrapPageCallback = function wrapPageCallback(cb){
      return function funcCallback(result){
        that.isDone = !!result;
        res = res || result;
        cb(result);
      };
    };

    this.wrapCallback = function(callback ){
      return function(){
        callback(res);
      };
    };
  }

  function Detect(){
    var res = null;
    var that = this;
    this.isDone = false;

    this.wrapPageCallback = function wrapPageCallback(cb){
      return function funcCallback(result){
        that.isDone = !!result;
        res = res || result;
        cb(res);
      };
    };

    this.wrapCallback = function(callback ){
      return function(){
        callback(res);
      };
    };
  }

  function Reduce(){
    var res = null;
    this.wrapPageCallback = function wrapPageCallback(cb){
      return function funcCallback(err, result){
        res = result;
        cb(err, result);
      };
    };

    this.wrapPageArgs = function(args){
      var memo = args[0];
      var iter = args[1];
      res = res || memo;
      // should be memo
      return [res, iter];
    };

    this.wrapCallback = function(callback ){
      return function(err, result){
        res = res || result;
        callback(err, res);
      };
    };
  }

  function ReduceRight(){
    var memo = null;
    var items = [];
    var iterator, callback;

    this.wrapPageCallback = function wrapPageCallback(cb){
      return cb;
    };

    this.wrapArgs = function(args){
      memo = args[0];
      iterator = args[1];
      callback = args[2];
      return [
        function(item, cb){
          items.push(item);cb();
        },
        function(){
          console.log(arguments);
        }
      ];
    };

    this.wrapCallback = function(){
      return function(err){
        if (err) {
          return callback(err);
        }

        async.reduceRight(items, memo, iterator, callback);
      };
    };
  }

  function SortBy(){
    var items = [];
    var iterator, callback;

    this.wrapPageCallback = function wrapPageCallback(cb){
      return cb;
    };

    this.wrapArgs = function(args){
      iterator = args[0];
      callback = args[1];
      return [
        function(item, cb){
          items.push(item);cb();
        },
        function(){
        }
      ];
    };

    this.wrapCallback = function(){
      return function(err){
        if (err) {
          return callback(err);
        }

        async.sortBy(items, iterator, callback);
      };
    };
  }

  var W1 = function(){ return new CallbackWrapper(1);};
  var W2 = function(){ return new CallbackWrapper(2);};

  var methods = {
    each: {wrapper: W2}, eachSeries: {wrapper: W2}, eachLimit: {wrapper: W2},
    forEach: {wrapper: W2}, forEachSeries: {wrapper: W2}, forEachLimit: {wrapper: W2},
    map: {wrapper: W2}, mapSeries: {wrapper: W2}, mapLimit:{wrapper: W2},
    filter: {wrapper: W1}, filterSeries: {wrapper: W1},
    select: {wrapper: W1}, selectSeries: {wrapper: W1},
    reject: {wrapper: W1}, rejectSeries: {wrapper: W1},
    reduce: {wrapper: Reduce}, inject: {wrapper: Reduce}, foldl: {wrapper: Reduce},
    reduceRight: {wrapper: ReduceRight, method: 'eachSeries'},
    foldr: {wrapper: ReduceRight, method: 'eachSeries'},
    detect: {wrapper: Detect},detectSeries: {wrapper: Detect},
    sortBy: {wrapper: SortBy, method: 'eachSeries'},
    some: {wrapper: Some}, any: {wrapper: Some},
    every: {wrapper: Every}, all: {wrapper: Every},
    concat: {wrapper: W2},concatSeries: {wrapper: W2}
  };

  function wrap(func, Wrapper){
    return function(){
      var args = Array.prototype.slice.call(arguments);

      if (typeof args[args.length - 1] !== 'function' && typeof args[args.length - 2] !== 'function'){
        // no iterator function, no callback - ignore call
        return;
      }

      if (typeof args[args.length - 2] !== 'function'){
        args.push(function(){});
      }

      var wrapper = new Wrapper();
      if (wrapper.wrapArgs){
        args = wrapper.wrapArgs(args);
      }
      wrapAsyncCallToAllPages(this, func, args, wrapper);
    };
  }

  _.each(methods, function(opts, method){
    CollectionResource.prototype[method] = wrap(async[opts.method || method], opts.wrapper);
  });
})();

module.exports = CollectionResource;<|endoftext|>


<commit_before>define([
    'underscore'
],
function(_){
    var CronUtil = function() {};

    _.extend(CronUtil, {

      //TODO this just checks that the characters are in the valid
      //set but does not assert the syntax of cron
      minuteRegex : RegExp(/^[0-9\*\-,\/]+$/),
      hourRegex : RegExp(/^[0-9\*\-,\/]+$/),
      dayRegex : RegExp(/^[0-9\*\-,\/,LW]+$/i),

      parsleyValidator : function(cb) {
        var validator = function() {};
        _.extend(validator, {
          validationMinlength: 1,
          validators : {
            cronfield : function (val,param) {
              var valid = null;
              switch(param) {
                case 'day':
                  valid = val.match(this.dayRegex);
                break;
                case 'hour':
                  valid = val.match(this.hourRegex);
                break;
                case 'minute':
                  valid = val.match(this.minuteRegex);
                break;
              }
              if(_.isFunction(cb)) {
                valid = cb(val,param,valid);
              }
              return valid!=null;
            }.bind(this)
          },
          messages : {
            cronfield : "Not a valid value for cron field '%s'"
          }
        });
        return validator;
      }

    });

    return CronUtil;
});

<commit_msg>Fix UI cron validation regex for days<commit_after>define([
    'underscore'
],
function(_){
    var CronUtil = function() {};

    _.extend(CronUtil, {

      //TODO this just checks that the characters are in the valid
      //set but does not assert the syntax of cron
      minuteRegex : RegExp(/^[0-9\*\-,\/]+$/),
      hourRegex : RegExp(/^[0-9\*\-,\/]+$/),
      dayRegex : RegExp(/^[\?0-9\*\-,\/,LW]+$/i),

      parsleyValidator : function(cb) {
        var validator = function() {};
        _.extend(validator, {
          validationMinlength: 1,
          validators : {
            cronfield : function (val,param) {
              var valid = null;
              switch(param) {
                case 'day':
                  valid = val.match(this.dayRegex);
                break;
                case 'hour':
                  valid = val.match(this.hourRegex);
                break;
                case 'minute':
                  valid = val.match(this.minuteRegex);
                break;
              }
              if(_.isFunction(cb)) {
                valid = cb(val,param,valid);
              }
              return valid!=null;
            }.bind(this)
          },
          messages : {
            cronfield : "Not a valid value for cron field '%s'"
          }
        });
        return validator;
      }

    });

    return CronUtil;
});

<|endoftext|>


<commit_before>"use strict";
var $ = require('jquery'),
    config = require('./config'),
    i18n = require('i18next-client'),
    Backbone = require('backbone')
;

var views = {
    "register": require('./views/provider-form'),
    "register-confirm": require('./views/provider-form-confirm'),
    "account-activate": require('./views/account-activate'),
    "service": require('./views/service-form'),
    "feedback": require('./views/feedback'),
    "map": require('./views/map'),
    "service-list": require('./views/service-list'),
    "login": require('./views/login'),
    "password-reset": require('./views/password-reset'),
    "password-reset-form": require('./views/password-reset-form'),
};

function loadPage(name, params) {
    var params = params || [];
    return function() {
        config.ready(function(){
            var $el = $(document.querySelector('#page'));
            var opts = {
                el: $el
            };
            for (var i=0; i < params.length; i++) {
                opts[params[i]] = arguments[i];
            }
            var view = new views[name](opts);
            i18n.init(function(){
                view.render.apply(view, arguments);
                view.$el.i18n({
                    lng: config.get('lang'),
                });
            });
            $('#menu-container').addClass("menu-closed");
            $('#menu-container').removeClass("menu-open");
        })
    }
}

module.exports = Backbone.Router.extend({
    routes: {
        "": function() {
            if (config.get('forever.authToken')) {

            } else {

            }
        },
        "register": loadPage("register"),
        "register/confirm": loadPage("register-confirm"),
        "register/verify/:key": loadPage("account-activate", ['key']),
        "service": loadPage("service"),
        "feedback": loadPage("feedback"),
        "map": loadPage("map"),
        "service-list": loadPage("service-list"),
        "login": loadPage("login"),
        "password-reset": loadPage("password-reset"),
        "password-reset-form": loadPage("password-reset-form"),
        "logout": function() {
            config.remove('forever.authToken');
            window.location.hash = '';
            window.location.reload();
        },
    },
})
<commit_msg>Fix closure-related arguments passing problems in hte account activation view<commit_after>"use strict";
var $ = require('jquery'),
    config = require('./config'),
    i18n = require('i18next-client'),
    Backbone = require('backbone')
;

var views = {
    "register": require('./views/provider-form'),
    "register-confirm": require('./views/provider-form-confirm'),
    "account-activate": require('./views/account-activate'),
    "service": require('./views/service-form'),
    "feedback": require('./views/feedback'),
    "map": require('./views/map'),
    "service-list": require('./views/service-list'),
    "login": require('./views/login'),
    "password-reset": require('./views/password-reset'),
    "password-reset-form": require('./views/password-reset-form'),
};

function loadPage(name, params) {
    var params = params || [];
    return function() {
        var viewArguments = Array.prototype.slice.apply(arguments);
        config.ready(function(){
            var $el = $(document.querySelector('#page'));
            var opts = {
                el: $el
            };
            for (var i=0; i < params.length; i++) {
                opts[params[i]] = viewArguments[i];
            };
            var view = new views[name](opts);
            i18n.init(function(){
                view.render.apply(view, viewArguments);
                view.$el.i18n({
                    lng: config.get('lang'),
                });
            });
            $('#menu-container').addClass("menu-closed");
            $('#menu-container').removeClass("menu-open");
        })
    }
}

module.exports = Backbone.Router.extend({
    routes: {
        "": function() {
            if (config.get('forever.authToken')) {

            } else {

            }
        },
        "register": loadPage("register"),
        "register/confirm": loadPage("register-confirm"),
        "register/verify/:key": loadPage("account-activate", ['key']),
        "service": loadPage("service"),
        "feedback": loadPage("feedback"),
        "map": loadPage("map"),
        "service-list": loadPage("service-list"),
        "login": loadPage("login"),
        "password-reset": loadPage("password-reset"),
        "password-reset-form": loadPage("password-reset-form"),
        "logout": function() {
            config.remove('forever.authToken');
            window.location.hash = '';
            window.location.reload();
        },
    },
})
<|endoftext|>


<commit_before>import React, {PropTypes, Component} from 'react'
import _ from 'lodash'

import FieldListItem from 'src/data_explorer/components/FieldListItem'
import GroupByTimeDropdown from 'src/data_explorer/components/GroupByTimeDropdown'
import FillQuery from 'shared/components/FillQuery'
import FancyScrollbar from 'shared/components/FancyScrollbar'

import {showFieldKeys} from 'shared/apis/metaQuery'
import showFieldKeysParser from 'shared/parsing/showFieldKeys'
import {
  functionNames,
  numFunctions,
  getFieldsWithName,
  getFuncsByFieldName,
} from 'shared/reducers/helpers/fields'

class FieldList extends Component {
  constructor(props) {
    super(props)
    this.state = {
      fields: [],
    }
  }

  componentDidMount() {
    const {database, measurement} = this.props.query
    if (!database || !measurement) {
      return
    }

    this._getFields()
  }

  componentDidUpdate(prevProps) {
    const {querySource, query} = this.props
    const {database, measurement, retentionPolicy} = query
    const {
      database: prevDB,
      measurement: prevMeas,
      retentionPolicy: prevRP,
    } = prevProps.query
    if (!database || !measurement) {
      return
    }

    if (
      database === prevDB &&
      measurement === prevMeas &&
      retentionPolicy === prevRP &&
      _.isEqual(prevProps.querySource, querySource)
    ) {
      return
    }

    this._getFields()
  }

  handleGroupByTime = groupBy => {
    this.props.onGroupByTime(groupBy.menuOption)
  }

  handleFill = fill => {
    this.props.onFill(fill)
  }

  handleToggleField = field => {
    const {
      query,
      onToggleField,
      addInitialField,
      initialGroupByTime: time,
      isKapacitorRule,
    } = this.props
    const {fields, groupBy} = query
    const initialGroupBy = {...groupBy, time}

    if (!_.size(fields)) {
      return isKapacitorRule
        ? onToggleField(field)
        : addInitialField(field, initialGroupBy)
    }

    onToggleField(field)
  }

  handleApplyFuncs = fieldFunc => {
    const {
      query,
      removeFuncs,
      applyFuncsToField,
      initialGroupByTime: time,
    } = this.props
    const {groupBy, fields} = query
    const {funcs} = fieldFunc

    // If one field has no funcs, all fields must have no funcs
    if (!_.size(funcs)) {
      return removeFuncs(fields)
    }

    // If there is no groupBy time set apple one
    if (!groupBy.time) {
      return applyFuncsToField(fieldFunc, {...groupBy, time})
    }

    applyFuncsToField(fieldFunc, groupBy)
  }

  _getFields = () => {
    const {database, measurement, retentionPolicy} = this.props.query
    const {source} = this.context
    const {querySource} = this.props

    const proxy =
      _.get(querySource, ['links', 'proxy'], null) || source.links.proxy

    showFieldKeys(proxy, database, measurement, retentionPolicy).then(resp => {
      const {errors, fieldSets} = showFieldKeysParser(resp.data)
      if (errors.length) {
        console.error('Error parsing fields keys: ', errors)
      }

      this.setState({
        fields: fieldSets[measurement].map(f => ({value: f, type: 'field'})),
      })
    })
  }

  render() {
    const {
      query: {database, measurement, fields = [], groupBy, fill},
      isKapacitorRule,
      isInDataExplorer,
    } = this.props

    const hasAggregates = numFunctions(fields) > 0
    const hasGroupByTime = groupBy.time
    const noDBorMeas = !database || !measurement

    return (

          Fields
          {hasAggregates
            ?

                <GroupByTimeDropdown
                  isOpen={!hasGroupByTime}
                  selected={groupBy.time}
                  onChooseGroupByTime={this.handleGroupByTime}
                  isInRuleBuilder={isKapacitorRule}
                  isInDataExplorer={isInDataExplorer}
                />
                {isKapacitorRule
                  ? null
                  : <FillQuery value={fill} onChooseFill={this.handleFill} />}

            : null}

        {noDBorMeas
          ?

                No Measurement selected

          :

              <FancyScrollbar>
                {this.state.fields.map((fieldFunc, i) => {
                  const selectedFields = getFieldsWithName(
                    fieldFunc.value,
                    fields
                  )

                  const funcs = getFuncsByFieldName(fieldFunc.value, fields)
                  const fieldFuncs = selectedFields.length
                    ? selectedFields
                    : [fieldFunc]

                  return (
                    <FieldListItem
                      key={i}
                      onToggleField={this.handleToggleField}
                      onApplyFuncsToField={this.handleApplyFuncs}
                      isSelected={!!selectedFields.length}
                      fieldFuncs={fieldFuncs}
                      funcs={functionNames(funcs)}
                      isKapacitorRule={isKapacitorRule}
                    />
                  )
                })}
              </FancyScrollbar>

}

    )
  }
}

const {bool, func, shape, string} = PropTypes

FieldList.defaultProps = {
  isKapacitorRule: false,
  initialGroupByTime: null,
}

FieldList.contextTypes = {
  source: shape({
    links: shape({
      proxy: string.isRequired,
    }).isRequired,
  }).isRequired,
}

FieldList.propTypes = {
  query: shape({
    database: string,
    retentionPolicy: string,
    measurement: string,
  }).isRequired,
  onToggleField: func.isRequired,
  onGroupByTime: func.isRequired,
  onFill: func,
  applyFuncsToField: func.isRequired,
  isKapacitorRule: bool,
  isInDataExplorer: bool,
  querySource: shape({
    links: shape({
      proxy: string.isRequired,
    }).isRequired,
  }),
  removeFuncs: func.isRequired,
  addInitialField: func,
  initialGroupByTime: string,
}

export default FieldList
<commit_msg>Fix comment<commit_after>import React, {PropTypes, Component} from 'react'
import _ from 'lodash'

import FieldListItem from 'src/data_explorer/components/FieldListItem'
import GroupByTimeDropdown from 'src/data_explorer/components/GroupByTimeDropdown'
import FillQuery from 'shared/components/FillQuery'
import FancyScrollbar from 'shared/components/FancyScrollbar'

import {showFieldKeys} from 'shared/apis/metaQuery'
import showFieldKeysParser from 'shared/parsing/showFieldKeys'
import {
  functionNames,
  numFunctions,
  getFieldsWithName,
  getFuncsByFieldName,
} from 'shared/reducers/helpers/fields'

class FieldList extends Component {
  constructor(props) {
    super(props)
    this.state = {
      fields: [],
    }
  }

  componentDidMount() {
    const {database, measurement} = this.props.query
    if (!database || !measurement) {
      return
    }

    this._getFields()
  }

  componentDidUpdate(prevProps) {
    const {querySource, query} = this.props
    const {database, measurement, retentionPolicy} = query
    const {
      database: prevDB,
      measurement: prevMeas,
      retentionPolicy: prevRP,
    } = prevProps.query
    if (!database || !measurement) {
      return
    }

    if (
      database === prevDB &&
      measurement === prevMeas &&
      retentionPolicy === prevRP &&
      _.isEqual(prevProps.querySource, querySource)
    ) {
      return
    }

    this._getFields()
  }

  handleGroupByTime = groupBy => {
    this.props.onGroupByTime(groupBy.menuOption)
  }

  handleFill = fill => {
    this.props.onFill(fill)
  }

  handleToggleField = field => {
    const {
      query,
      onToggleField,
      addInitialField,
      initialGroupByTime: time,
      isKapacitorRule,
    } = this.props
    const {fields, groupBy} = query
    const initialGroupBy = {...groupBy, time}

    if (!_.size(fields)) {
      return isKapacitorRule
        ? onToggleField(field)
        : addInitialField(field, initialGroupBy)
    }

    onToggleField(field)
  }

  handleApplyFuncs = fieldFunc => {
    const {
      query,
      removeFuncs,
      applyFuncsToField,
      initialGroupByTime: time,
    } = this.props
    const {groupBy, fields} = query
    const {funcs} = fieldFunc

    // If one field has no funcs, all fields must have no funcs
    if (!_.size(funcs)) {
      return removeFuncs(fields)
    }

    // If there is no groupBy time, set one
    if (!groupBy.time) {
      return applyFuncsToField(fieldFunc, {...groupBy, time})
    }

    applyFuncsToField(fieldFunc, groupBy)
  }

  _getFields = () => {
    const {database, measurement, retentionPolicy} = this.props.query
    const {source} = this.context
    const {querySource} = this.props

    const proxy =
      _.get(querySource, ['links', 'proxy'], null) || source.links.proxy

    showFieldKeys(proxy, database, measurement, retentionPolicy).then(resp => {
      const {errors, fieldSets} = showFieldKeysParser(resp.data)
      if (errors.length) {
        console.error('Error parsing fields keys: ', errors)
      }

      this.setState({
        fields: fieldSets[measurement].map(f => ({value: f, type: 'field'})),
      })
    })
  }

  render() {
    const {
      query: {database, measurement, fields = [], groupBy, fill},
      isKapacitorRule,
      isInDataExplorer,
    } = this.props

    const hasAggregates = numFunctions(fields) > 0
    const hasGroupByTime = groupBy.time
    const noDBorMeas = !database || !measurement

    return (

          Fields
          {hasAggregates
            ?

                <GroupByTimeDropdown
                  isOpen={!hasGroupByTime}
                  selected={groupBy.time}
                  onChooseGroupByTime={this.handleGroupByTime}
                  isInRuleBuilder={isKapacitorRule}
                  isInDataExplorer={isInDataExplorer}
                />
                {isKapacitorRule
                  ? null
                  : <FillQuery value={fill} onChooseFill={this.handleFill} />}

            : null}

        {noDBorMeas
          ?

                No Measurement selected

          :

              <FancyScrollbar>
                {this.state.fields.map((fieldFunc, i) => {
                  const selectedFields = getFieldsWithName(
                    fieldFunc.value,
                    fields
                  )

                  const funcs = getFuncsByFieldName(fieldFunc.value, fields)
                  const fieldFuncs = selectedFields.length
                    ? selectedFields
                    : [fieldFunc]

                  return (
                    <FieldListItem
                      key={i}
                      onToggleField={this.handleToggleField}
                      onApplyFuncsToField={this.handleApplyFuncs}
                      isSelected={!!selectedFields.length}
                      fieldFuncs={fieldFuncs}
                      funcs={functionNames(funcs)}
                      isKapacitorRule={isKapacitorRule}
                    />
                  )
                })}
              </FancyScrollbar>

}

    )
  }
}

const {bool, func, shape, string} = PropTypes

FieldList.defaultProps = {
  isKapacitorRule: false,
  initialGroupByTime: null,
}

FieldList.contextTypes = {
  source: shape({
    links: shape({
      proxy: string.isRequired,
    }).isRequired,
  }).isRequired,
}

FieldList.propTypes = {
  query: shape({
    database: string,
    retentionPolicy: string,
    measurement: string,
  }).isRequired,
  onToggleField: func.isRequired,
  onGroupByTime: func.isRequired,
  onFill: func,
  applyFuncsToField: func.isRequired,
  isKapacitorRule: bool,
  isInDataExplorer: bool,
  querySource: shape({
    links: shape({
      proxy: string.isRequired,
    }).isRequired,
  }),
  removeFuncs: func.isRequired,
  addInitialField: func,
  initialGroupByTime: string,
}

export default FieldList
<|endoftext|>


<commit_before>/**
 * Current weather widget.
 * Displayed in the main menu.
 */

(function(){

    var curweather = {

        //current : {},
        dom_obj : {},

        init : function(){

            this.dom_obj = create_block_element('curweather_block', main_menu.dom_obj);
        },

        set : function(weather){
            _debug('curweather.set', weather);
            this.current = weather;

            if (main_menu){
                this.render();
            }
        },

        render : function(){
            _debug('curweather.render');

            var cur = '

';
            cur += '
' + this.current.t +'° C
';
            cur += this.current.cloud_str + '
';
            cur += '' + word['weather_comfort'] + ': ' + this.current.t_flik +'° C
';
            cur += '' + word['weather_pressure'] + ': ' + this.current.p + ' ' + word['weather_mmhg'] +'
';
            cur += '' + word['weather_wind'] + ': '+ this.current.w_rumb_str + ', ' + this.current.w + ' ' + word['weather_speed'] + '
';
            cur += '' + word['weather_humidity'] + ': '+ this.current.h + '%
';
            cur += '
';

            this.dom_obj.innerHTML = cur;
        }

    }

    curweather.init();

    module.curweather = curweather;

    loader.next();

})();<commit_msg>"Modify render"<commit_after>/**
 * Current weather widget.
 * Displayed in the main menu.
 */

(function(){

    var curweather = {

        //current : {},
        dom_obj : {},

        init : function(){

            this.dom_obj = create_block_element('curweather_block', main_menu.dom_obj);
        },

        set : function(weather){
            _debug('curweather.set', weather);
            this.current = weather;

            if (main_menu){
                this.render();
            }
        },

        render : function(){
            _debug('curweather.render');

            var cur = '

';
            cur += '
' + this.current.t +'° C
';
            cur += this.current.cloud_str + '
';
            cur += '' + word['weather_comfort'] + ': ' + this.current.t_flik +'° C
';
            cur += '' + word['weather_pressure'] + ': ' + this.current.p + ' ' + word['weather_mmhg'] +'
';
            cur += '' + word['weather_wind'] + ': '+ this.current.w_rumb_str + ', ' + this.current.w + ' ' + word['weather_speed'] + '
';
            cur += '' + word['weather_humidity'] + ': '+ this.current.h + '%
';
            cur += '
';

            this.dom_obj.innerHTML = cur;
        }

    }

    curweather.init();

    module.curweather = curweather;

    loader.next();

})();<|endoftext|>


<commit_before>var r = require('express').Router(),
	ObjectId = require('mongodb').ObjectId,
	db = require('../libs/db-connector.js')

r.get('/all', function (req, res) {
	db().collection('profiles').find({hidden: {$ne: true}}).toArray(function (err, profiles) {
		if (!err && profiles) {
			res.json(profiles)
		}
		else if (!!err) {
			res.status(500).json('')
		}
	})
})

r.get('/all-from-institution', function (req, res) {
	if (req.query.id && req.query.id.length === 24) {
		var _id = ObjectId(req.query.id)
		db().collection('profiles').find({institution: _id}).toArray(function (err, profiles) {
			if (!err && profiles.length > 0) {
				res.json(profiles)
			}
			else if (!!err) {
				console.log(err)
				res.status(500).json('')
			}
			else {
				res.status(404).json('No institution profile found')
			}
		})
	}
	else {
		res.status(412).json('Missing parameter')
	}
})

r.get('/single', function (req, res) {
	if (req.query.id && req.query.id.length === 24) {
		var _id = ObjectId(req.query.id)
		db().collection('profiles').find({_id: _id}).toArray(function (err, profile) {
			if (!err && profile[0]) {
				res.json(profile[0])
			}
			else if (!!err) {
				console.log(err)
				res.status(500).json('Contains malformed data; please removed any copy-pasted images and re insert them with the editor')
			}
			else {
				res.status(404).json('Profile not found')
			}
		})
	}
	else {
		res.status(412).json('Missing parameter')
	}
})

r.get('/meta', function (req, res) {
	db().collection('meta_profiles').find({}).sort({required: -1, _id:1}).toArray(function (err, metaProfiles) {
		res.json(metaProfiles)
	})
})

r.post('/save', function (req, res) {

	if (!!req.body && !!req.body.data && !!req.body.data.institution) {
		var data = req.body.data
		delete data._id
		req.body.data.institution = ObjectId(req.body.data.institution)
		db().collection('profiles').update({'year': (new Date()).getFullYear(), institution: req.body.data.institution}, {$set: data}, {upsert: true, new: true, doc:true}, function (err, doc) {
			db().collection('profiles').update({'year': (new Date()).getFullYear() - 1, institution: req.body.data.institution}, {$set: {hidden: true}})
			if (err) {
				console.log(err)
				res.status(500).json('Contains malformed data; please removed any copy-pasted images and re insert them with the editor')
			}
			else res.status(200).json('OK')
		})
	}
	else {
		res.status(412).json('Missing parameter')
	}
})

module.exports = r
<commit_msg>trying to sort year issue<commit_after>var r = require('express').Router(),
	ObjectId = require('mongodb').ObjectId,
	db = require('../libs/db-connector.js')

r.get('/all', function (req, res) {
	var t = {hidden: {$ne: true}}
	if (req.query.year) t.year: req.query.year
	db().collection('profiles').find(t).toArray(function (err, profiles) {
		if (!err && profiles) {
			res.json(profiles)
		}
		else if (!!err) {
			res.status(500).json('')
		}
	})
})

r.get('/all-from-institution', function (req, res) {
	if (req.query.id && req.query.id.length === 24) {
		var _id = ObjectId(req.query.id)

		var t = {institution: _id}
		if (req.query.year) t.year: req.query.year

		db().collection('profiles').find(t).toArray(function (err, profiles) {
			if (!err && profiles.length > 0) {
				res.json(profiles)
			}
			else if (!!err) {
				console.log(err)
				res.status(500).json('')
			}
			else {
				res.status(404).json('No institution profile found')
			}
		})
	}
	else {
		res.status(412).json('Missing parameter')
	}
})

r.get('/single', function (req, res) {
	if (req.query.id && req.query.id.length === 24) {
		var _id = ObjectId(req.query.id)

		var t = {_id: _id}
		if (req.query.year) t.year: req.query.year

		db().collection('profiles').find(t).toArray(function (err, profile) {
			if (!err && profile[0]) {
				res.json(profile[0])
			}
			else if (!!err) {
				console.log(err)
				res.status(500).json('Contains malformed data; please removed any copy-pasted images and re insert them with the editor')
			}
			else {
				res.status(404).json('Profile not found')
			}
		})
	}
	else {
		res.status(412).json('Missing parameter')
	}
})

r.get('/meta', function (req, res) {
	db().collection('meta_profiles').find({}).sort({required: -1, _id:1}).toArray(function (err, metaProfiles) {
		res.json(metaProfiles)
	})
})

r.post('/save', function (req, res) {

	if (!!req.body && !!req.body.data && !!req.body.data.institution) {
		var data = req.body.data
		delete data._id
		req.body.data.institution = ObjectId(req.body.data.institution)
		db().collection('profiles').update({'year': (new Date()).getFullYear(), institution: req.body.data.institution}, {$set: data}, {upsert: true, new: true, doc:true}, function (err, doc) {
			db().collection('profiles').update({'year': (new Date()).getFullYear() - 1, institution: req.body.data.institution}, {$set: {hidden: true}})
			if (err) {
				console.log(err)
				res.status(500).json('Contains malformed data; please removed any copy-pasted images and re insert them with the editor')
			}
			else res.status(200).json('OK')
		})
	}
	else {
		res.status(412).json('Missing parameter')
	}
})

module.exports = r
<|endoftext|>


<commit_before>'use strict';

app.core.router = function () {
	var hooks = {};
	var self = this;
	var errorHandler = false;

	this.active = false;

	/**
	 * Click listener for links
	 * @param Event event
	 */
	var handleClick = function (event) {
		// Get the URL
		var link = $(this).attr('href');

		if (link && link !== 'javascript:void(0)') {
			// Load the page
			self.routeTo(link);

			// Send it to the browser history
			history.pushState('', '', link);

			// Prevent site from refreshing
			event.preventDefault();
		}
	};

	/**
	 * Assign click listeners to all internal links
	 */
	this.assignEvents = function () {
		if (history.pushState) {
			// Assign AJAX loading behavior
			$('a').each(function () {
				var element = $(this);

				// Make sure it has not been assigned already and is not an external link
				if (element.attr('data-hasevents') != '1'
				&& element.attr('target') != '_blank'
				&& !/http(s)?:\/\//.test(element.attr('href'))
				&& element.attr('data-direct') != '1') {
					element.attr('data-hasevents', '1');

					element.on('click', handleClick);
				}
			});
		}
	};

	/**
	 * Listen for 404 errors
	 * @param Function callback
	 */
	this.error = function (callback) {
		errorHandler = callback;
	};

	/**
	 * Attach a controller to an URL
	 * @param String call
	 * @param Function object
	 */
	this.get = function (call, object) {
		hooks[call] = object;
	};

	/**
	 * Load an URL from the hooked controllers
	 * @param String url
	 */
	this.routeTo = function (url) {
		// Remove the base path from the URL
		url = url.replace(app.config.path, '');

		// Rewrite ./ to /
		if (/^\.\/$/.test(url)) {
			url = '/';
		}

		// Force / in the beginning of URL
		if (!/^\//.test(url)) {
			url = '/' + url;
		}

		// Remove / from the end
		if (url != '/' && /\/$/.test(url)) {
			url = url.substr(0, url.length - 1);
		}

		self.active = url;

		// Try to find a controller in the hooks
		if (typeof hooks[url] != 'undefined') {
			app.core.log.debug('Routed to controller [' + url + ']');
			window.app.controller = new hooks[url]();
		} else {
			app.core.log.warning('Controller [' + url + '] not found');

			if (errorHandler) {
				window.app.controller = new errorHandler();
			}
		}

		$(window).trigger('ZeusRoute', self.active);
	};

	/**
	 * Load the default controller
	 */
	$(window).on('ZeusReady', function() {
		// Check for HTML5 pushState support
		if (history.pushState) {
			app.core.log.debug('Initialized router');

			$(window).bind('popstate', function() {
				window.app.core.router.routeTo(window.location.pathname);
			});

			self.assignEvents();

			if (app.config.preRouteHook) {
				app.config.preRouteHook(function() {
					self.routeTo(window.location.pathname);
				});

				return;
			}

			self.routeTo(window.location.pathname);
		}
	});
};<commit_msg>Note to self: javascript is different from PHP.<commit_after>'use strict';

app.core.router = function () {
	var hooks = {};
	var self = this;
	var errorHandler = false;

	this.active = false;

	/**
	 * Click listener for links
	 * @param Event event
	 */
	var handleClick = function (event) {
		// Get the URL
		var link = $(this).attr('href');

		if (link && link !== 'javascript:void(0)') {
			// Load the page
			self.routeTo(link);

			// Send it to the browser history
			history.pushState('', '', link);

			// Prevent site from refreshing
			event.preventDefault();
		}
	};

	/**
	 * Assign click listeners to all internal links
	 */
	this.assignEvents = function () {
		if (history.pushState) {
			// Assign AJAX loading behavior
			$('a').each(function () {
				var element = $(this);

				// Make sure it has not been assigned already and is not an external link
				if (element.attr('data-hasevents') != '1'
				&& element.attr('target') != '_blank'
				&& !/http(s)?:\/\//.test(element.attr('href'))
				&& element.attr('data-direct') != '1') {
					element.attr('data-hasevents', '1');

					element.on('click', handleClick);
				}
			});
		}
	};

	/**
	 * Listen for 404 errors
	 * @param Function callback
	 */
	this.error = function (callback) {
		errorHandler = callback;
	};

	/**
	 * Attach a controller to an URL
	 * @param String call
	 * @param Function object
	 */
	this.get = function (call, object) {
		hooks[call] = object;
	};

	/**
	 * Load an URL from the hooked controllers
	 * @param String url
	 */
	this.routeTo = function (url) {
		// Remove the base path from the URL
		url = url.replace(app.config.path, '');

		// Rewrite ./ to /
		if (/^\.\/$/.test(url)) {
			url = '/';
		}

		// Force / in the beginning of URL
		if (!/^\//.test(url)) {
			url = '/' + url;
		}

		// Remove / from the end
		if (url != '/' && /\/$/.test(url)) {
			url = url.substr(0, url.length - 1);
		}

		self.active = url;

		// Try to find a controller in the hooks
		if (typeof hooks[url] != 'undefined') {
			app.core.log.debug('Routed to controller [' + url + ']');
			window.app.controller = new hooks[url]();
		} else {
			app.core.log.warning('Controller [' + url + '] not found');

			if (errorHandler) {
				window.app.controller = new errorHandler();
			}
		}

		$(window).trigger('ZeusRoute', self.active);
	};

	/**
	 * Load the default controller
	 */
	$(window).on('ZeusReady', function() {
		// Check for HTML5 pushState support
		if (history.pushState) {
			app.core.log.debug('Initialized router');

			$(window).bind('popstate', function() {
				window.app.core.router.routeTo(window.location.pathname);
			});

			self.assignEvents();

			if (app.config.preRouteHook) {
				(eval(app.config.preRouteHook))(function() {
					self.routeTo(window.location.pathname);
				});

				return;
			}

			self.routeTo(window.location.pathname);
		}
	});
};<|endoftext|>


<commit_before>// Licensed under the Apache License, Version 2.0 (the “License”); you may not
// use this file except in compliance with the License. You may obtain a copy of
// the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an “AS IS” BASIS, WITHOUT
// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
// License for the specific language governing permissions and limitations under
// the License.

export function platformToTarget(platform) {
  switch (platform) {
    case 'browser':
      return 'web'
    case 'node':
      return platform
  }
  throw new Error(`Unsupported platform “${platform}”.`)
}
<commit_msg>Remove dead code<commit_after><|endoftext|>


<commit_before>function QNode(front, vState, depth) {
  // "visited" flags
  this.vState = vState
  // current node
  this.front = front
  this.depth = depth
  this.next = null
}

/**
 * @param {number[][]} graph
 * @return {number}
 */
const shortestPathLength = graph => {
  const N = graph.length
  const vStateSet = (which, vState) => (vState | (1 << which))
  const vStateTest = (which, vState) => Boolean(vState & (1 << which))

  // memo[vState][front] = depth records the best path of <vState> and <front>
  const memo = new Array(1 << N)

  // dummy node for now
  let qHead = {next: null}
  let qTail = qHead
  let targetVState = 0
  for (let i = 0; i < N; ++i) {
    const vState = vStateSet(i, 0)
    const node = new QNode(i, vState, 0)
    qTail.next = node
    qTail = qTail.next

    memo[vState] = new Array(N)
    memo[vState][i] = node.depth

    // reusing this loop to set target v-state, which is 1 for all nodes
    targetVState = vStateSet(i, targetVState)
  }
  // get rid of dummy head
  qHead = qHead.next
  while (qHead) {
    const {vState, front, depth} = qHead
    if (vState === targetVState) {
      // current one is already a solution, no need of looking further.
      qHead = qHead.next
      continue
    }
    const newDep = depth+1
    // try to extend the front
    graph[front].forEach(nextNode => {
      const newVState = vStateSet(nextNode, vState)
      if (!(newVState in memo)) {
        memo[newVState] = new Array(N)
      }
      if (
        !(nextNode in memo[newVState]) ||
        memo[newVState][nextNode] > newDep
      ) {
        memo[newVState][nextNode] = newDep
      } else {
        return
      }
      qTail.next = new QNode(nextNode, newVState, newDep)
      qTail = qTail.next
    })
    qHead = qHead.next
  }
  let minDepth = +Infinity
  memo[targetVState].forEach(x => {
    if (minDepth > x) {
      minDepth = x
    }
  })
  return minDepth
}

const inp2 = [
  // 0
  [1,2,3],
  // 1
  [0,6],
  // 2
  [0,4,5],
  // 3
  [0,9,10],
  // 4
  [2],
  // 5
  [2,11],
  // 6
  [1,7],
  // 7
  [8,6],
  // 8
  [7],
  // 9
  [3],
  // 10
  [3],
  // 11
  [5]
]

console.assert(shortestPathLength(inp2) === 15)
console.assert(shortestPathLength([[1,2,3],[0],[0],[0]]) === 4)
console.assert(shortestPathLength([[1],[0,2,4],[1,3,4],[2],[1,2]]) === 4)
<commit_msg>new toys to play with<commit_after>function QNode(front, vState, depth) {
  // "visited" flags
  this.vState = vState
  // current node
  this.front = front
  this.depth = depth
  this.next = null
}

/**
 * @param {number[][]} graph
 * @return {number}
 */
const shortestPathLength = graph => {
  const N = graph.length
  const vStateSet = (which, vState) => (vState | (1 << which))
  const vStateTest = (which, vState) => Boolean(vState & (1 << which))

  // memo[vState][front] = depth records the best path of <vState> and <front>
  const memo = new Array(1 << N)

  // dummy node for now
  let qHead = {next: null}
  let qTail = qHead
  let targetVState = 0
  for (let i = 0; i < N; ++i) {
    const vState = vStateSet(i, 0)
    const node = new QNode(i, vState, 0)
    qTail.next = node
    qTail = qTail.next

    memo[vState] = new Array(N)
    memo[vState][i] = node.depth

    // reusing this loop to set target v-state, which is 1 for all nodes
    targetVState = vStateSet(i, targetVState)
  }
  // get rid of dummy head
  qHead = qHead.next
  while (qHead) {
    const {vState, front, depth} = qHead
    if (vState === targetVState) {
      // current one is already a solution, no need of looking further.
      qHead = qHead.next
      continue
    }
    const newDep = depth+1
    // try to extend the front
    graph[front].forEach(nextNode => {
      const newVState = vStateSet(nextNode, vState)
      if (!(newVState in memo)) {
        memo[newVState] = new Array(N)
      }
      if (
        !(nextNode in memo[newVState]) ||
        memo[newVState][nextNode] > newDep
      ) {
        memo[newVState][nextNode] = newDep
      } else {
        return
      }
      qTail.next = new QNode(nextNode, newVState, newDep)
      qTail = qTail.next
    })
    qHead = qHead.next
  }
  let minDepth = +Infinity
  memo[targetVState].forEach(x => {
    if (minDepth > x) {
      minDepth = x
    }
  })
  return minDepth
}

const inp2 = [
  // 0
  [1,2,3],
  // 1
  [0,6],
  // 2
  [0,4,5],
  // 3
  [0,9,10],
  // 4
  [2],
  // 5
  [2,11],
  // 6
  [1,7],
  // 7
  [8,6],
  // 8
  [7],
  // 9
  [3],
  // 10
  [3],
  // 11
  [5]
]

const {consoleTest} = require('leetcode-zwischenzug')

consoleTest(shortestPathLength)(inp2)(15)
consoleTest(shortestPathLength)([[1,2,3],[0],[0],[0]])(4)
consoleTest(shortestPathLength)([[1],[0,2,4],[1,3,4],[2],[1,2]])(4)
<|endoftext|>