<commit_before>const Modifiers = {
  /* validators */

  integer: function(v) {
    var min = Modifiers.numberize(this.min, undefined);
    var max = Modifiers.numberize(this.max, undefined);
    var strict = !!this.strict;

    if (typeof v != 'number') {
      if (strict) {
        return Modifiers.error.call(this, {reason: 'not number', val: v});
      }
      else {
        var vI = parseInt(v);
      }
    }
    else {
      vI = v;
    }
    if (isNaN(vI)) return Modifiers.error.call(this, {reason: 'NaN', val: v});
    if (min != null && vI < min) return Modifiers.error({reason: 'min', val: v});
    if (max != null && vI > max) return Modifiers.error.call(this, {reason: 'max', val: v});
    return vI;
  },

  number: function(v) {
    var min = Modifiers.numberize(this.min, undefined);
    var max = Modifiers.numberize(this.max, undefined);
    var strict = !!this.strict;

    if (typeof v != 'number') {
      if (strict) {
        return Modifiers.error.call(this, {reason: 'not number', val: v});
      }
      else {
        var vI = Number(v);
      }
    }
    else {
      vI = v;
    }
    if (isNaN(vI)) return Modifiers.error.call(this, {reason: 'NaN', val: v});
    if (min != null && vI < min) return Modifiers.error.call(this, {reason: 'min', val: v});
    if (max != null && vI > max) return Modifiers.error.call(this, {reason: 'max', val: v});
    return vI;
  },

  string: function(v) {
    var min = Modifiers.numberize(this.min, undefined);
    var max = Modifiers.numberize(this.max, undefined);
    if (typeof v != 'string') {
      if (this.strict) {
        return Modifiers.error.call(this, {reason: 'not string', val: v});
      }
      else if (v != null) {
        v = v.toString();
      }
      else {
        v = '';
      }
    }
    var len = v.length;
    if (this.min != null && len < this.min) return Modifiers.error.call(this, {reason: 'min length', val: v});
    if (this.max != null && len > this.max) return Modifiers.error.call(this, {reason: 'max length', val: v});
    return v;
  },

  equal: function(v) {
    if (this.strict && this.value !== v) {
      throw Modifiers.error.call(this, {reason: 'not strict equal', val: v});
    }
    else if (!this.strict && this.value != v) {
      throw Modifiers.error.call(this, {reason: 'not equal', val: v});
    }
    return v;
  },

  isNull: function(v) {
    if ((this.strict && v === null) || (!this.strict && v == null)) return v;
    return Modifiers.error.call(this, {reason: 'not null', val : v});
  },

  isUndefined: function(v) {
    if ((this.strict && v === undefined) || (!this.strict && v == undefined)) return v;
    return Modifiers.error.call(this, {reason: 'not undefined', val : v});
  },

  regex: function(v) {
    if (! v.toString().match(this.pattern)) throw Modifiers.error.call(this, {reason: 'invalid pattern', val : v});
    return v;
  },

  func: function(fn) {
    if (typeof fn != 'function') return Modifiers.error.call(this, {reason: 'not a function', val: fn});
    return fn;
  },

  /* mapping arguments to the context */

  mappers: {
  // arg[0]        arg[1] arg[2] arg[3] ....
    integer     : ['min', 'max', 'strict'],
    number      : ['min', 'max', 'strict'],
    string      : ['min', 'max', 'strict'],
    equal       : ['value', 'strict'],
    isNull      : ['strict'],
    isUndefined : ['strict'],
    regex       : ['pattern']
  },

  /* filters */

  noerror : function(fn) {
    return function(v) {
      try {
        v = fn(v);
        return v;
      }
      catch (e) {
        return undefined;
      }
    }

  },

  every: function() {
    var args = arguments;
    return function(v) {
      Array.prototype.forEach.call(args, function(fn) {
        if (typeof fn == 'function') {
          v = fn(v);
        }
      });
      return v;
    };
  },

  some: function() {
    var args = arguments;
    return function(v) {
      Array.prototype.some.call(args, function(fn) {
        try {
          v = fn(v);
          return true;
        } catch (e) {}
      });
      return v;
    };
  },

  /* modifiers without raising errors */

  numberize: function(v, _default) {
    var vN = Number(v);
    return (isNaN(vN) || v == null || v === false || v == '') ? _default : vN;
  },

  /* methods to enable context chaining */

  bind: function() {
    var key = Array.prototype.shift.call(arguments);
    if (typeof Modifiers[key] != 'function') return Modifiers.error.call(this, {reason: 'no method', val: key});
    var ob = arguments[0];
    if (Modifiers.mappers[key] instanceof Array && (ob == null || (typeof ob != 'object') || (ob.constructor != Object))) {
      var context = {};
      Array.prototype.forEach.call(arguments, function(v, k) {
        var arg = Modifiers.mappers[key][k];
        if (arg) context[arg] = v;
      });
      return Modifiers[key].bind(context);
    }

    return Modifiers[key].bind(arguments[0] || {});
  },

  empty: function() {
  },

  /* utilities */

  error : function(info) {
    if (this.quiet) {
      return undefined;
    }
    throw new Error(JSON.stringify(info));
  }
};
Modifiers.set = Modifiers.bind;

// for Node.js
if (typeof exports == 'object' && exports === this) {
  const fs  = require('fs');
  const pth = require('path');

  Modifiers.mappers.file = ['normalize'];

  Modifiers.file = function(path) {
    path = Modifiers.string(path);
    if (!fs.statSync(path).isFile()) {
      return Modifiers.error({reason: 'not a file.', val : path});
    }
    return (this.normalize) ? pth.normalize(path) : path;
  };

  Modifiers.mappers.dir = ['normalize'];
  Modifiers.dir = function(path) {
    path = Modifiers.string(path);
    if (!fs.statSync(path).isDirectory()) {
      return Modifiers.error({reason: 'not a directory.', val : path});
    }
    return (this.normalize) ? pth.normalize(path) : path;
  };

  Modifiers.mappers.path = ['type', 'normalize'];
  Modifiers.path = function(path) {
    switch (this.type) {
    case 'path':
    default:
      path = Modifiers.string(path);
      if (!pth.existsSync(path)) {
        return Modifiers.error({reason: 'no such file or directory.', val : path});
      }
      return (this.normalize) ? pth.normalize(path) : path;
    case 'file':
      return Modifiers.file.call(this, path);
    case 'dir':
      return Modifiers.dir.call(this, path);
    }
  };
}

Modifiers.empty.prototype = Modifiers;

/* extension of each method */
const ModifierExtensions = Object.create(Object.prototype, {
  quiet: {
    get: function() {
      return this.bind({quiet: true});
    },
    set: function(){},
    enumerable: true
  },
  strict: {
    get: function() {
      return this.bind({strict: true});
    },
    set: function(){},
    enumerable: true
  }
});

/* ModifierExtensions inherits Function.prototype */
Object.getOwnPropertyNames(Function.prototype).forEach(function(k) {
  ModifierExtensions[k] = Function.prototype[k];
});

/* ModifierExtensions overrides Function.prototype.bind */
ModifierExtensions.bind = function(obj) {
  if (!this.bound) {
    var boundFunc = Function.prototype.bind.apply(this, arguments);
    Modifiers.extend(boundFunc);
    boundFunc.bound = obj;
    return boundFunc;
  }
  else {
    Object.keys(obj).forEach(function(k) {
      this.bound[k] = obj[k];
    }, this);
    return this;
  }
};
ModifierExtensions.set = ModifierExtensions.bind;

Object.freeze(ModifierExtensions);

Modifiers.extend = function(fn) {
  if (fn.__proto__) {
    fn.__proto__ = ModifierExtensions;
  }
  else {
    Object.getOwnPropertyNames(ModifierExtensions).forEach(function(p) {
      Object.defineProperty(fn, p, {
        value    : ModifierExtensions[p],
        writable : false
      });
    }, this);
  }
};

Object.keys(Modifiers).forEach(function(k) {
  if (typeof Modifiers[k] == 'function') {
    Modifiers.extend(Modifiers[k]);
  }
});

Object.freeze(Modifiers);

function ModifiersTest() {
  console.log(Modifiers.string.bind({min: 11}).quiet('eeeeeeeeeeeeee'));
  console.log('QUIET', Modifiers.bind('string', {min:8, max:14}).quiet);
  console.log('QUIET', Modifiers.bind('string', {min:8, max:14}).__proto__);
  console.log('QUIET', Modifiers.bind('string', {min:8, max:14}).__proto__);
  console.log(Modifiers.integer(33));
  console.log(Modifiers.bind('integer')(13));

  try {
    console.log(Modifiers.bind('integer', 14)(13));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.set('integer', {max: 11})(13));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.integer.set({max: 11, strict: true})("1"));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.integer.call({max: 11, strict: true}, 33));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.integer.bind({max: 11}).strict("3"));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.integer.bind({max: 11}).quiet.strict("3"));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.number.bind({max: 11.3, strict: true, quiet: true})(11.9));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.noerror(Modifiers.bind('number', null, 11.3))(11.9));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('string', {min:8, max:14})('shinout'));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('regex', /a/)('shinout'));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('regex', {pattern: /a/})('shinout'));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.equal.bind({value: 133})('133'));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.equal.bind({value: 133, strict: true})('133'));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('equal', 133, true)('133'));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('isNull')(undefined));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('isUndefined')(null));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('isUndefined', true)(null));
  } catch (e) { console.log(e.message); }

  console.log(Modifiers.regex.set({pattern: /^get[A-Za-z0-9]+$/}));

  console.log(
    Modifiers.every(
      Modifiers.string,
      Modifiers.bind('regex', {pattern: /^get[A-Za-z0-9]+$/})
    )('getConfig')
  );

  console.log(
    Modifiers.some(
      Modifiers.string,
      Modifiers.bind('regex', {pattern: /^get[A-Za-z0-9]+$/})
    )('getConfig##')
  );

  if (typeof exports === "object") {
    try {
      console.log(Modifiers.bind('path')('Modifiers.js'));
    } catch (e) { console.log(e.message); }

    try {
      console.log(Modifiers.bind('path')('Modifiers.css'));
    } catch (e) { console.log(e.message); }

    try {
      console.log(Modifiers.dir('Modifiers.js'));
    } catch (e) { console.log(e.message); }

    try {
      console.log(Modifiers.path('././Modifiers.js'));
    } catch (e) { console.log(e.message); }

    try {
      console.log(Modifiers.bind('path', null, true)('././Modifiers.js'));
    } catch (e) { console.log(e.message); }
  }
  else {
    console.log(module.exports);
  }
}

if (process.argv[1] === __filename) { ModifiersTest(); }
if (typeof exports === "object" && this === exports) module.exports = Modifiers;
<commit_msg>handled path errors<commit_after>const Modifiers = {
  /* validators */

  integer: function(v) {
    var min = Modifiers.numberize(this.min, undefined);
    var max = Modifiers.numberize(this.max, undefined);
    var strict = !!this.strict;

    if (typeof v != 'number') {
      if (strict) {
        return Modifiers.error.call(this, {reason: 'not number', val: v});
      }
      else {
        var vI = parseInt(v);
      }
    }
    else {
      vI = v;
    }
    if (isNaN(vI)) return Modifiers.error.call(this, {reason: 'NaN', val: v});
    if (min != null && vI < min) return Modifiers.error({reason: 'min', val: v});
    if (max != null && vI > max) return Modifiers.error.call(this, {reason: 'max', val: v});
    return vI;
  },

  number: function(v) {
    var min = Modifiers.numberize(this.min, undefined);
    var max = Modifiers.numberize(this.max, undefined);
    var strict = !!this.strict;

    if (typeof v != 'number') {
      if (strict) {
        return Modifiers.error.call(this, {reason: 'not number', val: v});
      }
      else {
        var vI = Number(v);
      }
    }
    else {
      vI = v;
    }
    if (isNaN(vI)) return Modifiers.error.call(this, {reason: 'NaN', val: v});
    if (min != null && vI < min) return Modifiers.error.call(this, {reason: 'min', val: v});
    if (max != null && vI > max) return Modifiers.error.call(this, {reason: 'max', val: v});
    return vI;
  },

  string: function(v) {
    var min = Modifiers.numberize(this.min, undefined);
    var max = Modifiers.numberize(this.max, undefined);
    if (typeof v != 'string') {
      if (this.strict) {
        return Modifiers.error.call(this, {reason: 'not string', val: v});
      }
      else if (v != null) {
        v = v.toString();
      }
      else {
        v = '';
      }
    }
    var len = v.length;
    if (this.min != null && len < this.min) return Modifiers.error.call(this, {reason: 'min length', val: v});
    if (this.max != null && len > this.max) return Modifiers.error.call(this, {reason: 'max length', val: v});
    return v;
  },

  equal: function(v) {
    if (this.strict && this.value !== v) {
      throw Modifiers.error.call(this, {reason: 'not strict equal', val: v});
    }
    else if (!this.strict && this.value != v) {
      throw Modifiers.error.call(this, {reason: 'not equal', val: v});
    }
    return v;
  },

  isNull: function(v) {
    if ((this.strict && v === null) || (!this.strict && v == null)) return v;
    return Modifiers.error.call(this, {reason: 'not null', val : v});
  },

  isUndefined: function(v) {
    if ((this.strict && v === undefined) || (!this.strict && v == undefined)) return v;
    return Modifiers.error.call(this, {reason: 'not undefined', val : v});
  },

  regex: function(v) {
    if (! v.toString().match(this.pattern)) throw Modifiers.error.call(this, {reason: 'invalid pattern', val : v});
    return v;
  },

  func: function(fn) {
    if (typeof fn != 'function') return Modifiers.error.call(this, {reason: 'not a function', val: fn});
    return fn;
  },

  /* mapping arguments to the context */

  mappers: {
  // arg[0]        arg[1] arg[2] arg[3] ....
    integer     : ['min', 'max', 'strict'],
    number      : ['min', 'max', 'strict'],
    string      : ['min', 'max', 'strict'],
    equal       : ['value', 'strict'],
    isNull      : ['strict'],
    isUndefined : ['strict'],
    regex       : ['pattern']
  },

  /* filters */

  noerror : function(fn) {
    return function(v) {
      try {
        v = fn(v);
        return v;
      }
      catch (e) {
        return undefined;
      }
    }

  },

  every: function() {
    var args = arguments;
    return function(v) {
      Array.prototype.forEach.call(args, function(fn) {
        if (typeof fn == 'function') {
          v = fn(v);
        }
      });
      return v;
    };
  },

  some: function() {
    var args = arguments;
    return function(v) {
      Array.prototype.some.call(args, function(fn) {
        try {
          v = fn(v);
          return true;
        } catch (e) {}
      });
      return v;
    };
  },

  /* modifiers without raising errors */

  numberize: function(v, _default) {
    var vN = Number(v);
    return (isNaN(vN) || v == null || v === false || v == '') ? _default : vN;
  },

  /* methods to enable context chaining */

  bind: function() {
    var key = Array.prototype.shift.call(arguments);
    if (typeof Modifiers[key] != 'function') return Modifiers.error.call(this, {reason: 'no method', val: key});
    var ob = arguments[0];
    if (Modifiers.mappers[key] instanceof Array && (ob == null || (typeof ob != 'object') || (ob.constructor != Object))) {
      var context = {};
      Array.prototype.forEach.call(arguments, function(v, k) {
        var arg = Modifiers.mappers[key][k];
        if (arg) context[arg] = v;
      });
      return Modifiers[key].bind(context);
    }

    return Modifiers[key].bind(arguments[0] || {});
  },

  empty: function() {
  },

  /* utilities */

  error : function(info) {
    if (this.quiet) {
      return undefined;
    }
    throw new Error(JSON.stringify(info));
  }
};
Modifiers.set = Modifiers.bind;

// for Node.js
if (typeof exports == 'object' && exports === this) {
  const fs  = require('fs');
  const pth = require('path');

  Modifiers.mappers.file = ['normalize'];

  Modifiers.file = function(path) {
    path = Modifiers.string(path);
    try {
      if (!fs.statSync(path).isFile()) {
        return Modifiers.error({reason: 'not a file.', val : path});
      }
      return (this.normalize) ? pth.normalize(path) : path;
    }
    catch (e) {
      return Modifiers.error({reason: 'no such file or directory.', val: path});
    }
  };

  Modifiers.mappers.dir = ['normalize'];
  Modifiers.dir = function(path) {
    path = Modifiers.string(path);
    try {
      if (!fs.statSync(path).isDirectory()) {
        return Modifiers.error({reason: 'not a directory.', val : path});
      }
      return (this.normalize) ? pth.normalize(path) : path;
    }
    catch (e) {
      return Modifiers.error.call(this, {reason: 'no such file or directory.', val: path});
    }
  };

  Modifiers.mappers.path = ['type', 'normalize'];
  Modifiers.path = function(path) {
    switch (this.type) {
    case 'path':
    default:
      path = Modifiers.string(path);
      if (!pth.existsSync(path)) {
        return Modifiers.error({reason: 'no such file or directory.', val : path});
      }
      return (this.normalize) ? pth.normalize(path) : path;
    case 'file':
      return Modifiers.file.call(this, path);
    case 'dir':
      return Modifiers.dir.call(this, path);
    }
  };
}

Modifiers.empty.prototype = Modifiers;

/* extension of each method */
const ModifierExtensions = Object.create(Object.prototype, {
  quiet: {
    get: function() {
      return this.bind({quiet: true});
    },
    set: function(){},
    enumerable: true
  },
  strict: {
    get: function() {
      return this.bind({strict: true});
    },
    set: function(){},
    enumerable: true
  }
});

/* ModifierExtensions inherits Function.prototype */
Object.getOwnPropertyNames(Function.prototype).forEach(function(k) {
  ModifierExtensions[k] = Function.prototype[k];
});

/* ModifierExtensions overrides Function.prototype.bind */
ModifierExtensions.bind = function(obj) {
  if (!this.bound) {
    var boundFunc = Function.prototype.bind.apply(this, arguments);
    Modifiers.extend(boundFunc);
    boundFunc.bound = obj;
    return boundFunc;
  }
  else {
    Object.keys(obj).forEach(function(k) {
      this.bound[k] = obj[k];
    }, this);
    return this;
  }
};
ModifierExtensions.set = ModifierExtensions.bind;

Object.freeze(ModifierExtensions);

Modifiers.extend = function(fn) {
  if (fn.__proto__) {
    fn.__proto__ = ModifierExtensions;
  }
  else {
    Object.getOwnPropertyNames(ModifierExtensions).forEach(function(p) {
      Object.defineProperty(fn, p, {
        value    : ModifierExtensions[p],
        writable : false
      });
    }, this);
  }
};

Object.keys(Modifiers).forEach(function(k) {
  if (typeof Modifiers[k] == 'function') {
    Modifiers.extend(Modifiers[k]);
  }
});

Object.freeze(Modifiers);

function ModifiersTest() {
  console.log(Modifiers.string.bind({min: 11}).quiet('eeeeeeeeeeeeee'));
  console.log('QUIET', Modifiers.bind('string', {min:8, max:14}).quiet);
  console.log('QUIET', Modifiers.bind('string', {min:8, max:14}).__proto__);
  console.log('QUIET', Modifiers.bind('string', {min:8, max:14}).__proto__);
  console.log(Modifiers.integer(33));
  console.log(Modifiers.bind('integer')(13));

  try {
    console.log(Modifiers.bind('integer', 14)(13));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.set('integer', {max: 11})(13));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.integer.set({max: 11, strict: true})("1"));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.integer.call({max: 11, strict: true}, 33));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.integer.bind({max: 11}).strict("3"));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.integer.bind({max: 11}).quiet.strict("3"));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.number.bind({max: 11.3, strict: true, quiet: true})(11.9));
  } catch (e) { console.log(e.message); }

  try {
  console.log(Modifiers.noerror(Modifiers.bind('number', null, 11.3))(11.9));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('string', {min:8, max:14})('shinout'));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('regex', /a/)('shinout'));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('regex', {pattern: /a/})('shinout'));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.equal.bind({value: 133})('133'));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.equal.bind({value: 133, strict: true})('133'));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('equal', 133, true)('133'));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('isNull')(undefined));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('isUndefined')(null));
  } catch (e) { console.log(e.message); }

  try {
    console.log(Modifiers.bind('isUndefined', true)(null));
  } catch (e) { console.log(e.message); }

  console.log(Modifiers.regex.set({pattern: /^get[A-Za-z0-9]+$/}));

  console.log(
    Modifiers.every(
      Modifiers.string,
      Modifiers.bind('regex', {pattern: /^get[A-Za-z0-9]+$/})
    )('getConfig')
  );

  console.log(
    Modifiers.some(
      Modifiers.string,
      Modifiers.bind('regex', {pattern: /^get[A-Za-z0-9]+$/})
    )('getConfig##')
  );

  if (typeof exports === "object") {
    try {
      console.log(Modifiers.bind('path')('Modifiers.js'));
    } catch (e) { console.log(e.message); }

    try {
      console.log(Modifiers.bind('path')('Modifiers.css'));
    } catch (e) { console.log(e.message); }

    try {
      console.log(Modifiers.dir('Modifiers.js'));
    } catch (e) { console.log(e.message); }

    try {
      console.log(Modifiers.path('././Modifiers.js'));
    } catch (e) { console.log(e.message); }

    try {
      console.log(Modifiers.bind('path', null, true)('././Modifiers.js'));
    } catch (e) { console.log(e.message); }
  }
  else {
    console.log(module.exports);
  }
}

if (process.argv[1] === __filename) { ModifiersTest(); }
if (typeof exports === "object" && this === exports) module.exports = Modifiers;
<|endoftext|>


<commit_before>// Test for Calendar
/*eslint-env node */
const getopt = require("node-getopt");
const Q = require("q");

const Utils = require("../common/Utils.js");
const Config = require("../common/Config.js");

const Calendar = require("./Calendar.js");

var cliopt = getopt.create([
    [ "h", "help", "Show this help" ],
    [ "c", "config=ARG", "Configuration file (default ./hotpot.cfg)" ]
])
    .bindHelp()
    .parseSystem()
    .options;

if (typeof cliopt.config === "undefined")
    cliopt.config = "./hotpot.cfg";

Q.longStackSupport = true;

Config.load(cliopt.config)
.done(function(config) {
   var cal = new Calendar("Crawford", config.controller.calendar.Crawford,
                         trigger, remove);

    cal
    .authorise()
    .then(function() {
        return cal.fillCache();
    })
    .then(function() {
        console.log("Active event:");
        console.log(Utils.dump(cal.get()));
    })
    .catch(function(e) {
        console.error(e.stack);
    });
});

<commit_msg>Add calendar listing<commit_after>// Test for Calendar. Supports listing of available calendars, useful
// for setting up initial config.
/*eslint-env node */
const Getopt = require("node-getopt");
const Q = require("q");

const Utils = require("../common/Utils.js");
const Config = require("../common/Config.js");

const Calendar = require("./Calendar.js");

var getopt = new Getopt([
    [ "h", "help", "Show this help" ],
    [ "l", "list", "List available calendars" ],
    [ "c", "calendar=ARG", "Name of calendar (default is first)" ],
    [ "f", "config=ARG", "Configuration file (default ./hotpot.cfg)" ]
])
    .bindHelp()
    .parseSystem();

var cliopt = getopt.options;

if (typeof cliopt.config === "undefined")
    cliopt.config = "./hotpot.cfg";

Q.longStackSupport = true;

//Utils.setTRACE("all");

function showCalendar(calendar, config) {
    config.controller.calendar[calendar].id = "primary";
    var cal = new Calendar(calendar, config.controller.calendar[calendar]);
    cal
        .authorise()
        .then(function() {
            return cal.fillCache();
        })
        .then(function() {
            console.log(Utils.dump(cal));
        })
        .catch(function(e) {
            console.error(e.stack);
        });
}

function listCalendars(calendar, config) {
    var cfg = config.controller.calendar[calendar];

    var cal = new Calendar(calendar, cfg);
    cal.authorise()
        .then(function() {
            return cal.listCalendars();
        })
        .then(function(data) {
            for (var i in data) {
                console.log(data[i].summary + " - '" + data[i].id + "'");
            }
        })
        .catch(function(e) {
            console.error(e.stack);
        });
}

Config.load(cliopt.config)
    .done(function(config) {
        if (!cliopt.calendar) {
            for (cliopt.calendar in config.controller.calendar)
                break;
            console.log("Using calendar '" + cliopt.calendar + "'");
        }
        if (cliopt.list)
            listCalendars(cliopt.calendar, config);
        else
            showCalendar(cliopt.calendar, config);
    });
<|endoftext|>


<commit_before>function setupFlorence() {
    window.templates = Handlebars.templates;
    Handlebars.registerPartial("browseNode", templates.browseNode);
    Handlebars.registerPartial("browseNodeDataVis", templates.browseNodeDataVis);
    Handlebars.registerPartial("editNav", templates.editNav);
    Handlebars.registerPartial("editNavChild", templates.editNavChild);
    Handlebars.registerPartial("selectorHour", templates.selectorHour);
    Handlebars.registerPartial("selectorMinute", templates.selectorMinute);
    Handlebars.registerPartial("tickAnimation", templates.tickAnimation);
    Handlebars.registerPartial("loadingAnimation", templates.loadingAnimation);
    Handlebars.registerHelper('select', function (value, options) {
        var $el = $('<select />').html(options.fn(this));
        $el.find('[value="' + value + '"]').attr({'selected': 'selected'});
        return $el.html();
    });
    Handlebars.registerHelper('ifCond', function (v1, operator, v2, options) {

        switch (operator) {
            case '==':
                return (v1 == v2) ? options.fn(this) : options.inverse(this);
            case '===':
                return (v1 === v2) ? options.fn(this) : options.inverse(this);
            case '<':
                return (v1 < v2) ? options.fn(this) : options.inverse(this);
            case '<=':
                return (v1 <= v2) ? options.fn(this) : options.inverse(this);
            case '>':
                return (v1 > v2) ? options.fn(this) : options.inverse(this);
            case '>=':
                return (v1 >= v2) ? options.fn(this) : options.inverse(this);
            case '&&':
                return (v1 && v2) ? options.fn(this) : options.inverse(this);
            case '||':
                return (v1 || v2) ? options.fn(this) : options.inverse(this);
            default:
                return options.inverse(this);
        }
    });
    //Check if array contains element
    Handlebars.registerHelper('ifContains', function (elem, list, options) {
        if (list.indexOf(elem) > -1) {
            return options.fn(this);
        }
        return options.inverse(this);
    });
    // Add two values together. Primary usage was '@index + 1' to create numbered lists
    Handlebars.registerHelper('plus', function (value1, value2) {
        return value1 + value2;
    });
    // Add two values together. Primary usage was '@index + 1' to create numbered lists
    Handlebars.registerHelper('lastEditedBy', function (array) {
        if (array) {
            var event = array[array.length - 1];
            if (event) {
                return 'Last edited ' + StringUtils.formatIsoDateString(new Date(event.date)) + " by " + event.email;
            }
        }
        return '';
    });
    Handlebars.registerHelper('createdBy', function (array) {
        if (array) {
            var event = getCollectionCreatedEvent(array);
            if (event) {
                return 'Created ' + StringUtils.formatIsoDateString(new Date(event.date)) + " by " + event.email + '';
            } else {
                return "";
            }
        }
        return "";
    });
    // If two strings match
    Handlebars.registerHelper('if_eq', function (a, b, opts) {
        if (a == b)
            return opts.fn(this);
        else
            return opts.inverse(this);
    });
    // If two strings don't match
    Handlebars.registerHelper('if_ne', function (a, b, opts) {
        if (a != b)
            return opts.fn(this);
        else
            return opts.inverse(this);
    });

    Handlebars.registerHelper('comma_separated_list', function (array) {
        var asString = "";

        if (array) {
            array.forEach(function (item) {
                asString = asString + item + ", ";
            });
            return asString.substring(0, asString.lastIndexOf(","));
        }
        return asString;
    });

    Florence.globalVars.activeTab = false;

    // load main florence template
    var florence = templates.florence;

    $('body').append(florence);
    Florence.refreshAdminMenu();

    var adminMenu = $('.admin-nav');
    // dirty checks on admin menu
    adminMenu.on('click', '.nav--admin__item', function () {
        if (Florence.Editor.isDirty) {
            swal({
                title: "Warning",
                text: "If you do not come back to this page, you will lose any unsaved changes",
                type: "warning",
                showCancelButton: true,
                confirmButtonText: "Continue",
                cancelButtonText: "Cancel"
            }, function (result) {
                if (result === true) {
                    Florence.Editor.isDirty = false;
                    processMenuClick(this);
                    return true;
                } else {
                    return false;
                }
            });
        } else {
            processMenuClick(this);
        }
    });

    window.onbeforeunload = function () {
        if (Florence.Editor.isDirty) {
            return 'You have unsaved changes.';
        }
    };
    viewController();

    function processMenuClick(clicked) {
        Florence.collection = {};

        $('.nav--admin__item--collection').hide();
        $('.nav--admin__item').removeClass('selected');
        var menuItem = $(clicked);

        menuItem.addClass('selected');

        if (menuItem.hasClass("nav--admin__item--collections")) {
            viewController('collections');
        } else if (menuItem.hasClass("nav--admin__item--collection")) {
            var thisCollection = CookieUtils.getCookieValue("collection");
            viewCollections(thisCollection);
            $(".nav--admin__item--collections").addClass('selected');
        } else if (menuItem.hasClass("nav--admin__item--users")) {
            viewController('users');
        } else if (menuItem.hasClass("nav--admin__item--teams")) {
            viewController('teams');
        } else if (menuItem.hasClass("nav--admin__item--publish")) {
            viewController('publish');
        } else if (menuItem.hasClass("nav--admin__item--reports")) {
            viewController('reports');
        } else if (menuItem.hasClass("nav--admin__item--login")) {
            viewController('login');
        } else if (menuItem.hasClass("nav--admin__item--logout")) {
            logout();
            viewController();
        }
    }

    var lastPingTime;
    var pingTimes = [];

    function doPing() {
        var start = new Date().getTime();
        $.ajax({
            url: "/zebedee/ping",
            dataType: 'json',
            contentType: 'application/json',
            type: 'POST',
            data: JSON.stringify({
                lastPingTime: lastPingTime
            }),
            success: function (response) {

                var end = new Date().getTime();
                var time = end - start;

                lastPingTime = time;
                pingTimes.push(time);
                if (pingTimes.length > 5)
                    pingTimes.shift();

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

                var averagePingTime = sum / pingTimes.length;

                networkStatus(lastPingTime);

                if (averagePingTime < 100) {
                    console.log("ping time: pretty good! " + time + " average: " + averagePingTime + " " + pingTimes);
                } else if (averagePingTime < 300) {
                    console.log("ping time: not so good! " + time + " average: " + averagePingTime + " " + pingTimes);
                } else {
                    console.log("ping time: really bad! " + time);
                }

                pingTimer = setTimeout(function () {
                    doPing();
                }, 10000);
            }
        });
    }

    var pingTimer = setTimeout(function () {
        doPing();
    }, 10000);

    // Reset default functions from certain elements - eg form submits
    resetPage();

}

<commit_msg>Add click event logging for easier debugging on production<commit_after>function setupFlorence() {
    window.templates = Handlebars.templates;
    Handlebars.registerPartial("browseNode", templates.browseNode);
    Handlebars.registerPartial("browseNodeDataVis", templates.browseNodeDataVis);
    Handlebars.registerPartial("editNav", templates.editNav);
    Handlebars.registerPartial("editNavChild", templates.editNavChild);
    Handlebars.registerPartial("selectorHour", templates.selectorHour);
    Handlebars.registerPartial("selectorMinute", templates.selectorMinute);
    Handlebars.registerPartial("tickAnimation", templates.tickAnimation);
    Handlebars.registerPartial("loadingAnimation", templates.loadingAnimation);
    Handlebars.registerHelper('select', function (value, options) {
        var $el = $('<select />').html(options.fn(this));
        $el.find('[value="' + value + '"]').attr({'selected': 'selected'});
        return $el.html();
    });
    Handlebars.registerHelper('ifCond', function (v1, operator, v2, options) {

        switch (operator) {
            case '==':
                return (v1 == v2) ? options.fn(this) : options.inverse(this);
            case '===':
                return (v1 === v2) ? options.fn(this) : options.inverse(this);
            case '<':
                return (v1 < v2) ? options.fn(this) : options.inverse(this);
            case '<=':
                return (v1 <= v2) ? options.fn(this) : options.inverse(this);
            case '>':
                return (v1 > v2) ? options.fn(this) : options.inverse(this);
            case '>=':
                return (v1 >= v2) ? options.fn(this) : options.inverse(this);
            case '&&':
                return (v1 && v2) ? options.fn(this) : options.inverse(this);
            case '||':
                return (v1 || v2) ? options.fn(this) : options.inverse(this);
            default:
                return options.inverse(this);
        }
    });
    //Check if array contains element
    Handlebars.registerHelper('ifContains', function (elem, list, options) {
        if (list.indexOf(elem) > -1) {
            return options.fn(this);
        }
        return options.inverse(this);
    });
    // Add two values together. Primary usage was '@index + 1' to create numbered lists
    Handlebars.registerHelper('plus', function (value1, value2) {
        return value1 + value2;
    });
    // Add two values together. Primary usage was '@index + 1' to create numbered lists
    Handlebars.registerHelper('lastEditedBy', function (array) {
        if (array) {
            var event = array[array.length - 1];
            if (event) {
                return 'Last edited ' + StringUtils.formatIsoDateString(new Date(event.date)) + " by " + event.email;
            }
        }
        return '';
    });
    Handlebars.registerHelper('createdBy', function (array) {
        if (array) {
            var event = getCollectionCreatedEvent(array);
            if (event) {
                return 'Created ' + StringUtils.formatIsoDateString(new Date(event.date)) + " by " + event.email + '';
            } else {
                return "";
            }
        }
        return "";
    });
    // If two strings match
    Handlebars.registerHelper('if_eq', function (a, b, opts) {
        if (a == b)
            return opts.fn(this);
        else
            return opts.inverse(this);
    });
    // If two strings don't match
    Handlebars.registerHelper('if_ne', function (a, b, opts) {
        if (a != b)
            return opts.fn(this);
        else
            return opts.inverse(this);
    });

    Handlebars.registerHelper('comma_separated_list', function (array) {
        var asString = "";

        if (array) {
            array.forEach(function (item) {
                asString = asString + item + ", ";
            });
            return asString.substring(0, asString.lastIndexOf(","));
        }
        return asString;
    });

    Florence.globalVars.activeTab = false;

    // load main florence template
    var florence = templates.florence;

    $('body').append(florence);
    Florence.refreshAdminMenu();

    var adminMenu = $('.admin-nav');
    // dirty checks on admin menu
    adminMenu.on('click', '.nav--admin__item', function () {
        if (Florence.Editor.isDirty) {
            swal({
                title: "Warning",
                text: "If you do not come back to this page, you will lose any unsaved changes",
                type: "warning",
                showCancelButton: true,
                confirmButtonText: "Continue",
                cancelButtonText: "Cancel"
            }, function (result) {
                if (result === true) {
                    Florence.Editor.isDirty = false;
                    processMenuClick(this);
                    return true;
                } else {
                    return false;
                }
            });
        } else {
            processMenuClick(this);
        }
    });

    window.onbeforeunload = function () {
        if (Florence.Editor.isDirty) {
            return 'You have unsaved changes.';
        }
    };
    viewController();

    function processMenuClick(clicked) {
        Florence.collection = {};

        $('.nav--admin__item--collection').hide();
        $('.nav--admin__item').removeClass('selected');
        var menuItem = $(clicked);

        menuItem.addClass('selected');

        if (menuItem.hasClass("nav--admin__item--collections")) {
            viewController('collections');
        } else if (menuItem.hasClass("nav--admin__item--collection")) {
            var thisCollection = CookieUtils.getCookieValue("collection");
            viewCollections(thisCollection);
            $(".nav--admin__item--collections").addClass('selected');
        } else if (menuItem.hasClass("nav--admin__item--users")) {
            viewController('users');
        } else if (menuItem.hasClass("nav--admin__item--teams")) {
            viewController('teams');
        } else if (menuItem.hasClass("nav--admin__item--publish")) {
            viewController('publish');
        } else if (menuItem.hasClass("nav--admin__item--reports")) {
            viewController('reports');
        } else if (menuItem.hasClass("nav--admin__item--login")) {
            viewController('login');
        } else if (menuItem.hasClass("nav--admin__item--logout")) {
            logout();
            viewController();
        }
    }

    var lastPingTime;
    var pingTimes = [];

    function doPing() {
        var start = new Date().getTime();
        $.ajax({
            url: "/zebedee/ping",
            dataType: 'json',
            contentType: 'application/json',
            type: 'POST',
            data: JSON.stringify({
                lastPingTime: lastPingTime
            }),
            success: function (response) {

                var end = new Date().getTime();
                var time = end - start;

                lastPingTime = time;
                pingTimes.push(time);
                if (pingTimes.length > 5)
                    pingTimes.shift();

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

                var averagePingTime = sum / pingTimes.length;

                networkStatus(lastPingTime);

                if (averagePingTime < 100) {
                    console.log("ping time: pretty good! " + time + " average: " + averagePingTime + " " + pingTimes);
                } else if (averagePingTime < 300) {
                    console.log("ping time: not so good! " + time + " average: " + averagePingTime + " " + pingTimes);
                } else {
                    console.log("ping time: really bad! " + time);
                }

                pingTimer = setTimeout(function () {
                    doPing();
                }, 10000);
            }
        });
    }

    var pingTimer = setTimeout(function () {
        doPing();
    }, 10000);

    // Reset default functions from certain elements - eg form submits
    resetPage();

    // Log every click that will be changing the state or data in Florence
    $(document).on('click', 'a, button, input[type="button"], iframe, .table--primary tr, .nav--admin__item, .page-item', function(e) {
        var clickEvent = {
            time: new Date(),
            trigger: e.target,
            currentCollection: Florence.collection,
            pagePath: Florence.globalVars.pagePath
        };

        console.log("Click event", clickEvent);
    });

}

<|endoftext|>


<commit_before>const webpack = require('webpack');
const debug = process.env.DEBUGGING || false;
// App-specific back-end Webpack config should be here
const server = {
     entry: {
       index: [
        './src/setup/app.ts'
       ]
     }
};

// App-specific web front-end Webpack config should be here
const web = {
    entry: {
        index: [
            './src/index.tsx'
        ]
    },
    plugins: [
        new webpack.DefinePlugin({
            __DEBUGGING__: debug,
        }),
    ],
};

// App-specific Android React Native front-end Webpack config should be here
const android = {
    //  entry: {
    //    'index.mobile.bundle': [
    //      require.resolve('./react-native-polyfill.js'),
    //      './src/mobile/index.js'
    //    ]
    //  }
};

// App-specific iOS React Native front-end Webpack config should be here
const ios = {
    //  entry: {
    //    'index.mobile.bundle': [
    //      require.resolve('./react-native-polyfill.js'),
    //      './src/mobile/index.js'
    //    ]
    //  }
};

const dependencyPlatforms = {
    "@cdm-logger/server": 'server',
    "bunyan": 'server',
    "export-dir": 'server',
    "express": 'server',
    'body-parser': 'server',
    express: 'server',
    'graphql-server-express': 'server',
    'graphql-subscriptions': 'server',
    'graphql-tools': 'server',
    "graphql-tag": ['server', 'web'],
    'immutability-helper': ['ios', 'android', 'web'],
    'isomorphic-fetch': 'server',
    knex: 'server',
    mysql2: 'server',
    persistgraphql: ['server', 'web'],
    "graphql-nats-subscriptions": 'server',
    "graphql-server-core": 'server',
    "graphql-server-express": 'server',
    "graphql-subscriptions": 'web',
    "graphql-tools": 'server',
    "helmet": 'server',
    "hemera-joi": 'server',
    "hemera-plugin": 'server',
    "immutability-helper": 'web',
    "inversify": 'server',
    "morgan": 'server',
    "nats": 'server',
    "nats-hemera":'server',
    "nconf": 'server',
    "node-pre-gyp": 'server',
    "prop-types": 'web',
    "ramda": ['web', 'server'],
    "react": "web",
    "react-apollo": 'web',
    "redux": "web",
    "reflect-metadata": 'server',
    "sequelize": 'server',
    'react-dom': 'web',
    'react-helmet': 'web',
    'react-hot-loader': 'web',
    'react-native': ['ios', 'android'],
    'react-navigation': ['ios', 'android'],
    'react-redux': 'web',
    'react-router': 'web',
    'react-router-dom': 'web',
    reactstrap: 'web',
    'redux-devtools-extension': 'web',
    'redux-form': 'web',
    'serialize-javascript': 'server',
    'source-map-support': 'server',
    sqlite3: 'server',
    'styled-components': ['server', 'web'],
    'subscriptions-transport-ws': ['ios', 'android', 'web'],
    'ws': ['server']
};

module.exports = { server, web, android, ios, dependencyPlatforms };<commit_msg>update for debug<commit_after>const webpack = require('webpack');
const debug = process.env.DEBUGGING || false;
// App-specific back-end Webpack config should be here
const server = {
     entry: {
       index: [
        './src/setup/app.ts'
       ]
     },
     plugins: [
         new webpack.DefinePlugin({
             __DEBUGGING__: JSON.stringify(debug),
         })
     ]
};

// App-specific web front-end Webpack config should be here
const web = {
    entry: {
        index: [
            './src/index.tsx'
        ]
    },
    plugins: [
        new webpack.DefinePlugin({
            __DEBUGGING__: debug,
        }),
    ],
};

// App-specific Android React Native front-end Webpack config should be here
const android = {
    //  entry: {
    //    'index.mobile.bundle': [
    //      require.resolve('./react-native-polyfill.js'),
    //      './src/mobile/index.js'
    //    ]
    //  }
};

// App-specific iOS React Native front-end Webpack config should be here
const ios = {
    //  entry: {
    //    'index.mobile.bundle': [
    //      require.resolve('./react-native-polyfill.js'),
    //      './src/mobile/index.js'
    //    ]
    //  }
};

const dependencyPlatforms = {
    "@cdm-logger/server": 'server',
    "bunyan": 'server',
    "export-dir": 'server',
    "express": 'server',
    'body-parser': 'server',
    express: 'server',
    'graphql-server-express': 'server',
    'graphql-subscriptions': 'server',
    'graphql-tools': 'server',
    "graphql-tag": ['server', 'web'],
    'immutability-helper': ['ios', 'android', 'web'],
    'isomorphic-fetch': 'server',
    knex: 'server',
    mysql2: 'server',
    persistgraphql: ['server', 'web'],
    "graphql-nats-subscriptions": 'server',
    "graphql-server-core": 'server',
    "graphql-server-express": 'server',
    "graphql-subscriptions": 'web',
    "graphql-tools": 'server',
    "helmet": 'server',
    "hemera-joi": 'server',
    "hemera-plugin": 'server',
    "immutability-helper": 'web',
    "inversify": 'server',
    "morgan": 'server',
    "nats": 'server',
    "nats-hemera":'server',
    "nconf": 'server',
    "node-pre-gyp": 'server',
    "prop-types": 'web',
    "ramda": ['web', 'server'],
    "react": "web",
    "react-apollo": 'web',
    "redux": "web",
    "reflect-metadata": 'server',
    "sequelize": 'server',
    'react-dom': 'web',
    'react-helmet': 'web',
    'react-hot-loader': 'web',
    'react-native': ['ios', 'android'],
    'react-navigation': ['ios', 'android'],
    'react-redux': 'web',
    'react-router': 'web',
    'react-router-dom': 'web',
    reactstrap: 'web',
    'redux-devtools-extension': 'web',
    'redux-form': 'web',
    'serialize-javascript': 'server',
    'source-map-support': 'server',
    sqlite3: 'server',
    'styled-components': ['server', 'web'],
    'subscriptions-transport-ws': ['ios', 'android', 'web'],
    'ws': ['server']
};

module.exports = { server, web, android, ios, dependencyPlatforms };<|endoftext|>


<commit_before>/**
 * Created by prism on 4/17/15.
 */
angular.module('Hiren')
    .controller('LoginCtrl', function($scope, $auth) {

    });<commit_msg>finally login working :smile:<commit_after>/**
 * Created by prism on 4/17/15.
 */
angular.module('Hiren')
    .controller('LoginCtrl', function($scope, $auth) {
        $scope.login = function() {
            $auth.login({ email: $scope.email, password: $scope.password})
                .then(function(response) {
                    console.log('login' + response.data);
                });
        };

        $scope.authenticate = function(provider) {
          $auth.authenticate(provider)
              .then(function(response) {
                  console.log('authenticated' + response.data);
              });
        };

    });<|endoftext|>


<commit_before>const TipoEnte = require("../src/TipoEnte");
const CatalogoOuvidorias = artifacts.require("./CatalogoOuvidorias.sol");

/* FUNCOES UTILITARIAS */

function fail(mensagem) {
    assert.fail(false, false, mensagem);
}
function assertRequireFalhou(erro) {
    // falha de alguma condicao dentro de um require(...) no solidity
    assert.equal(erro.message, 'VM Exception while processing transaction: invalid opcode');
}

function clonarEventoConvertendoPropriedades(log, propriedadesBytes32, propriedadesUint) {
    function bytes32ToString(hexx) {
        const hex = hexx.toString();
        let str = '';
        for (let i = 0; i < hex.length; i += 2)
            str += String.fromCharCode(parseInt(hex.substr(i, 2), 16));
        return str.replace(/\u0000/g, '');
    }
    let retorno = Object.assign({}, log.args);
    propriedadesBytes32.forEach((propBytes32) => {
        retorno[propBytes32] = bytes32ToString(retorno[propBytes32]);
    });
    propriedadesUint.forEach((propUint) => {
        retorno[propUint] = retorno[propUint].c[0];
    });
    return retorno;
}

function assertPrimeiroEvento(resultadoTransacao, propriedadesBytes32, propriedadesUint, nomeTipoEvento, eventoEsperado) {
    assert.deepEqual(
        clonarEventoConvertendoPropriedades(resultadoTransacao.logs[0], propriedadesBytes32, propriedadesUint),
        eventoEsperado
    );
    assert.equal(resultadoTransacao.logs[0].event, nomeTipoEvento);
}

function assertEventoOuvidoriaAutorizada(resultadoTransacao, eventoEsperado) {
    assertPrimeiroEvento(
        resultadoTransacao,
        [],
        [],
        "ouvidoriaAutorizada",
        eventoEsperado
    );
}

function assertEventoOuvidoriaCadastrada(resultadoTransacao, eventoEsperado) {
    assertPrimeiroEvento(
        resultadoTransacao,
        ["nome", "nomeEnte", "endpoint"],
        ["tipoEnte"],
        "ouvidoriaCadastrada",
        eventoEsperado
    );
}

function assertPrimeiraOuvidoria(contractInstance, _account, _nome, _enteTipo, _enteNome, _endpoint) {
    return contractInstance.then((co) => {
        let primeiraOuvidoriaAccount = _account;
        let primeiraOuvidoria = {};
        return co.getOuvidoriaNome(primeiraOuvidoriaAccount).then((nome) => {
            primeiraOuvidoria.nome = nome;
            return co.getOuvidoriaEnteTipo(primeiraOuvidoriaAccount);
        }).then((enteTipo) => {
            primeiraOuvidoria.enteTipo = enteTipo;
            return co.getOuvidoriaEnteNome(primeiraOuvidoriaAccount);
        }).then((enteNome) => {
            primeiraOuvidoria.enteNome = enteNome;
            return co.getOuvidoriaEndpoint(primeiraOuvidoriaAccount);
        }).then((ouvidoriaEndpoint) => {
            primeiraOuvidoria.ouvidoriaEndpoint = ouvidoriaEndpoint;

            assert.equal(primeiraOuvidoria.nome, _nome);
            assert.equal(TipoEnte[primeiraOuvidoria.enteTipo.c[0]], _enteTipo);
            assert.equal(primeiraOuvidoria.enteNome, _enteNome);
            assert.equal(primeiraOuvidoria.ouvidoriaEndpoint, _endpoint);
        });
    });
}

contract('CatalogoOuvidorias', (accounts) => {

    it("script de deploy padrao constroi corretamente o contrato inicial", () => {
        let contractInstance = CatalogoOuvidorias.deployed();

        return assertPrimeiraOuvidoria(
            contractInstance,
            accounts[0],
            'CGU',
            'Uniao',
            'Uniao',
            'http://cgu.gov.br/ouv'
        );
    });

    describe("CatalogoOuvidorias criado em testes", () => {
        const ouvDF = {
            conta: accounts[0],
            nome: "CGU-DF",
            tipoEnte: 1,
            tipoPorExtenso: "Estado/DF",
            nomeEnte: "DF",
            endpoint: "http://cgu.gov.br/ouv-ba"
        };

        const ouvBA = {
            conta: accounts[1],
            nome: "CGU-BA",
            tipoEnte: 1,
            nomeEnte: "BA",
            endpoint: "http://cgu.gov.br/ouv-ba"
        };

        let catalogoOuvidoriasPromise;

        beforeEach(() => {
            catalogoOuvidoriasPromise = CatalogoOuvidorias.new(ouvDF.nome, ouvDF.tipoEnte, ouvDF.nomeEnte, ouvDF.endpoint);
        });

        it("construtor cria corretamente catalogo de testes", () => {
            return assertPrimeiraOuvidoria(
                catalogoOuvidoriasPromise,
                ouvDF.conta,
                ouvDF.nome,
                ouvDF.tipoPorExtenso,
                ouvDF.nomeEnte,
                ouvDF.endpoint
            );
        });

        it("ouvidoria jah cadastrada pode chamar autorizar", () => {
            return catalogoOuvidoriasPromise.then((catalogoOuvidorias) => {
                return catalogoOuvidorias.autorizar(ouvBA.conta, {from: ouvDF.conta});
            }).then((resultadoTransacao) => {
                assertEventoOuvidoriaAutorizada(
                    resultadoTransacao,
                    {
                        ouvidoriaAutorizadora: ouvDF.conta,
                        ouvidoriaCandidata: ouvBA.conta
                    }
                );
            });
        });

        it("ouvidoria nao cadastrada NAO pode chamar autorizar", () => {
            return catalogoOuvidoriasPromise.then((catalogoOuvidorias) => {
                return catalogoOuvidorias.autorizar(ouvDF.conta, {from: ouvBA.conta});
            }).then(() => {
                fail("ouvBA nao estah cadastrada, portanto nao pode autorizar ninguem")
            }, (erro) => {
                assertRequireFalhou(erro);
            });
        });

        it("ouvidoria jah cadastrada nao pode autorizar uma outra ouvidoria mais de uma vez", () => {
            return catalogoOuvidoriasPromise.then((catalogoOuvidorias) => {
                return catalogoOuvidorias.autorizar(ouvBA.conta, {from: ouvDF.conta}).then(() => {
                    return catalogoOuvidorias.autorizar(ouvBA.conta, {from: ouvDF.conta});
                }).then(() => {
                    fail("ouvDF jah autorizou a ouvBA, nao poderia autorizar uma segunda vez")
                }, (erro) => {
                    assertRequireFalhou(erro);
                });
            })
        });

        xit("ouvidoria jah cadastrada nao pode autorizar uma outra ouvidoria jah cadastrada", () => {
            // soh vou conseguir implementar depois que o metodo de efetivacao de cadastro estiver concluido
        });

        it("candidata sem autorizacoes nao consegue cadastrar-se", () => {
            return catalogoOuvidoriasPromise.then((catalogoOuvidorias) => {
                return catalogoOuvidorias.cadastrar(ouvBA.nome, ouvBA.tipoEnte, ouvBA.nomeEnte, ouvBA.endpoint, {from: ouvBA.conta}).then(() => {
                    fail("como a ouvBA nao recebeu uma autorizacao, nao pode se cadastrar")
                }, (erro) => {
                    assertRequireFalhou(erro);
                });
            });
        });

        it("quando ha somente uma ouvidoria cadastrada, uma candidata consegue cadastrar-se tendo apenas uma autorizacao", () => {
            return catalogoOuvidoriasPromise.then((catalogoOuvidorias) => {
                return catalogoOuvidorias.autorizar(ouvBA.conta, {from: ouvDF.conta}).then(() => {
                    return catalogoOuvidorias.cadastrar(ouvBA.nome, ouvBA.tipoEnte, ouvBA.nomeEnte, ouvBA.endpoint, {from: ouvBA.conta}).then((tx) => {
                        assertEventoOuvidoriaCadastrada(
                            tx,
                            ouvBA
                        );
                    });
                });
            });
        });

        xit("quando ha somente duas ouvidorias cadastradas, uma candidata consegue cadastrar-se tendo apenas duas autorizacoes", () => { });

        xit("quando ha tres ou mais ouvidorias cadastradas, uma candidata NAO consegue cadastrar-se tendo apenas uma autorizacao", () => { });
        xit("quando ha tres ou mais ouvidorias cadastradas, uma candidata NAO consegue cadastrar-se tendo apenas duas autorizacoes", () => { });
        xit("quando ha tres ou mais ouvidorias cadastradas, uma candidata consegue cadastrar-se tendo apenas tres autorizacoes", () => { });

    });

});
<commit_msg>test(catalogo): expandir verify porque implementacao estava incompleta<commit_after>const TipoEnte = require("../src/TipoEnte");
const CatalogoOuvidorias = artifacts.require("./CatalogoOuvidorias.sol");

/* FUNCOES UTILITARIAS */

function fail(mensagem) {
    assert.fail(false, false, mensagem);
}
function assertRequireFalhou(erro) {
    // falha de alguma condicao dentro de um require(...) no solidity
    assert.equal(erro.message, 'VM Exception while processing transaction: invalid opcode');
}
function uint(_uint) {
    return _uint.c[0];
}

function clonarEventoConvertendoPropriedades(log, propriedadesBytes32, propriedadesUint) {
    function bytes32ToString(hexx) {
        const hex = hexx.toString();
        let str = '';
        for (let i = 0; i < hex.length; i += 2)
            str += String.fromCharCode(parseInt(hex.substr(i, 2), 16));
        return str.replace(/\u0000/g, '');
    }
    let retorno = Object.assign({}, log.args);
    propriedadesBytes32.forEach((propBytes32) => {
        retorno[propBytes32] = bytes32ToString(retorno[propBytes32]);
    });
    propriedadesUint.forEach((propUint) => {
        retorno[propUint] = uint(retorno[propUint]);
    });
    return retorno;
}

function assertPrimeiroEvento(resultadoTransacao, propriedadesBytes32, propriedadesUint, nomeTipoEvento, eventoEsperado) {
    assert.deepEqual(
        clonarEventoConvertendoPropriedades(resultadoTransacao.logs[0], propriedadesBytes32, propriedadesUint),
        eventoEsperado
    );
    assert.equal(resultadoTransacao.logs[0].event, nomeTipoEvento);
}

function assertEventoOuvidoriaAutorizada(resultadoTransacao, eventoEsperado) {
    assertPrimeiroEvento(
        resultadoTransacao,
        [],
        [],
        "ouvidoriaAutorizada",
        eventoEsperado
    );
}

function assertEventoOuvidoriaCadastrada(resultadoTransacao, eventoEsperado) {
    assertPrimeiroEvento(
        resultadoTransacao,
        ["nome", "nomeEnte", "endpoint"],
        ["tipoEnte"],
        "ouvidoriaCadastrada",
        eventoEsperado
    );
}

function assertPrimeiraOuvidoria(contractInstance, _account, _nome, _enteTipo, _enteNome, _endpoint) {
    return contractInstance.then((co) => {
        let primeiraOuvidoriaAccount = _account;
        let primeiraOuvidoria = {};
        return co.getOuvidoriaNome(primeiraOuvidoriaAccount).then((nome) => {
            primeiraOuvidoria.nome = nome;
            return co.getOuvidoriaEnteTipo(primeiraOuvidoriaAccount);
        }).then((enteTipo) => {
            primeiraOuvidoria.enteTipo = enteTipo;
            return co.getOuvidoriaEnteNome(primeiraOuvidoriaAccount);
        }).then((enteNome) => {
            primeiraOuvidoria.enteNome = enteNome;
            return co.getOuvidoriaEndpoint(primeiraOuvidoriaAccount);
        }).then((ouvidoriaEndpoint) => {
            primeiraOuvidoria.ouvidoriaEndpoint = ouvidoriaEndpoint;

            assert.equal(primeiraOuvidoria.nome, _nome);
            assert.equal(TipoEnte[primeiraOuvidoria.enteTipo.c[0]], _enteTipo);
            assert.equal(primeiraOuvidoria.enteNome, _enteNome);
            assert.equal(primeiraOuvidoria.ouvidoriaEndpoint, _endpoint);
        });
    });
}

contract('CatalogoOuvidorias', (accounts) => {

    it("script de deploy padrao constroi corretamente o contrato inicial", () => {
        let contractInstance = CatalogoOuvidorias.deployed();

        return assertPrimeiraOuvidoria(
            contractInstance,
            accounts[0],
            'CGU',
            'Uniao',
            'Uniao',
            'http://cgu.gov.br/ouv'
        );
    });

    describe("CatalogoOuvidorias criado em testes", () => {
        const ouvDF = {
            conta: accounts[0],
            nome: "CGU-DF",
            tipoEnte: 1,
            tipoPorExtenso: "Estado/DF",
            nomeEnte: "DF",
            endpoint: "http://cgu.gov.br/ouv-ba"
        };
        const ouvBA = {
            conta: accounts[1],
            nome: "CGU-BA",
            tipoEnte: 1,
            nomeEnte: "BA",
            endpoint: "http://cgu.gov.br/ouv-ba"
        };
        const ouvAJU = {
            conta: accounts[2],
            nome: "Pref. Aracaju",
            tipoEnte: 2,
            nomeEnte: "Aracaju-SE",
            endpoint: "http://aracaju.se.gov.br/ouv"
        };

        let catalogoOuvidoriasPromise;

        beforeEach(() => {
            catalogoOuvidoriasPromise = CatalogoOuvidorias.new(ouvDF.nome, ouvDF.tipoEnte, ouvDF.nomeEnte, ouvDF.endpoint);
        });

        it("construtor cria corretamente catalogo de testes", () => {
            return assertPrimeiraOuvidoria(
                catalogoOuvidoriasPromise,
                ouvDF.conta,
                ouvDF.nome,
                ouvDF.tipoPorExtenso,
                ouvDF.nomeEnte,
                ouvDF.endpoint
            );
        });

        it("ouvidoria jah cadastrada pode chamar autorizar", () => {
            return catalogoOuvidoriasPromise.then((catalogoOuvidorias) => {
                return catalogoOuvidorias.autorizar(ouvBA.conta, {from: ouvDF.conta});
            }).then((resultadoTransacao) => {
                assertEventoOuvidoriaAutorizada(
                    resultadoTransacao,
                    {
                        ouvidoriaAutorizadora: ouvDF.conta,
                        ouvidoriaCandidata: ouvBA.conta
                    }
                );
            });
        });

        it("ouvidoria nao cadastrada NAO pode chamar autorizar", () => {
            return catalogoOuvidoriasPromise.then((catalogoOuvidorias) => {
                return catalogoOuvidorias.autorizar(ouvDF.conta, {from: ouvBA.conta});
            }).then(() => {
                fail("ouvBA nao estah cadastrada, portanto nao pode autorizar ninguem")
            }, (erro) => {
                assertRequireFalhou(erro);
            });
        });

        it("ouvidoria jah cadastrada nao pode autorizar uma outra ouvidoria mais de uma vez", () => {
            return catalogoOuvidoriasPromise.then((catalogoOuvidorias) => {
                return catalogoOuvidorias.autorizar(ouvBA.conta, {from: ouvDF.conta}).then(() => {
                    return catalogoOuvidorias.autorizar(ouvBA.conta, {from: ouvDF.conta});
                }).then(() => {
                    fail("ouvDF jah autorizou a ouvBA, nao poderia autorizar uma segunda vez")
                }, (erro) => {
                    assertRequireFalhou(erro);
                });
            })
        });

        xit("ouvidoria jah cadastrada nao pode autorizar uma outra ouvidoria jah cadastrada", () => {
            // soh vou conseguir implementar depois que o metodo de efetivacao de cadastro estiver concluido
        });

        it("candidata sem autorizacoes nao consegue cadastrar-se", () => {
            return catalogoOuvidoriasPromise.then((catalogoOuvidorias) => {
                return catalogoOuvidorias.cadastrar(ouvBA.nome, ouvBA.tipoEnte, ouvBA.nomeEnte, ouvBA.endpoint, {from: ouvBA.conta}).then(() => {
                    fail("como a ouvBA nao recebeu uma autorizacao, nao pode se cadastrar")
                }, (erro) => {
                    assertRequireFalhou(erro);
                });
            });
        });

        xit("quando ha somente uma ouvidoria cadastrada, uma candidata consegue cadastrar-se tendo apenas uma autorizacao", () => {
            return catalogoOuvidoriasPromise.then((catalogoOuvidorias) => {
                return catalogoOuvidorias.autorizar(ouvBA.conta, {from: ouvDF.conta}).then(() => {
                    return catalogoOuvidorias.cadastrar(ouvBA.nome, ouvBA.tipoEnte, ouvBA.nomeEnte, ouvBA.endpoint, {from: ouvBA.conta}).then((tx) => {
                        assertEventoOuvidoriaCadastrada(
                            tx,
                            ouvBA
                        );
                        return catalogoOuvidorias.getNumeroDeOuvidorias();
                    }).then((numeroDeOuvidorias) => {
                        assert.equal(uint(numeroDeOuvidorias), 2);
                    });
                });
            });
        });

        xit("quando ha somente duas ouvidorias cadastradas, uma candidata NAO consegue cadastrar-se tendo apenas uma autorizacao", () => {
            return catalogoOuvidoriasPromise.then((catalogoOuvidorias) => {
                return catalogoOuvidorias.autorizar(ouvBA.conta, {from: ouvDF.conta}).then(() => {
                    return catalogoOuvidorias.cadastrar(ouvBA.nome, ouvBA.tipoEnte, ouvBA.nomeEnte, ouvBA.endpoint, {from: ouvBA.conta});
                }).then(() => {
                    return catalogoOuvidorias.autorizar(ouvAJU.conta, {from: ouvDF.conta});
                }).then(() => {
                    return catalogoOuvidorias.cadastrar(ouvAJU.conta, ouvAJU.tipoEnte, ouvAJU.nomeEnte, ouvAJU.endpoint, {from: ouvAJU.conta}).then(() => {
                        fail("como a ouvAJU nao recebeu uma autorizacao, nao poderia se cadastrar")
                    }, (erro) => {
                        assertRequireFalhou(erro);
                    });
                });
            });
        });

        xit("quando ha somente duas ouvidorias cadastradas, uma candidata consegue cadastrar-se tendo apenas duas autorizacoes", () => { });

        xit("quando ha tres ou mais ouvidorias cadastradas, uma candidata NAO consegue cadastrar-se tendo apenas uma autorizacao", () => { });
        xit("quando ha tres ou mais ouvidorias cadastradas, uma candidata NAO consegue cadastrar-se tendo apenas duas autorizacoes", () => { });
        xit("quando ha tres ou mais ouvidorias cadastradas, uma candidata consegue cadastrar-se tendo apenas tres autorizacoes", () => { });

    });

});
<|endoftext|>


<commit_before>app.directive('status', function ($timeout) {
	return {
		restrict: "EA",
		scope: {
			user: "="
		},
		templateUrl: "/assets/app/shared/status.html",
		link: function ($scope) {
			//Sorry josh, had to make it a function for it to pick up my messages updates.
			$scope.away = _.throttle(function(){
				console.count('away derp')
				return moment().diff(moment($scope.user.lastActivity), "minutes") > 5;
			},2000);
		}
	};
});
<commit_msg>removed comment<commit_after>app.directive('status', function ($timeout) {
	return {
		restrict: "EA",
		scope: {
			user: "="
		},
		templateUrl: "/assets/app/shared/status.html",
		link: function ($scope) {
			//Sorry josh, had to make it a function for it to pick up my messages updates.
			$scope.away = _.throttle(function(){
				return moment().diff(moment($scope.user.lastActivity), "minutes") > 5;
			},2000);
		}
	};
});
<|endoftext|>


<commit_before>#!/usr/bin/env node
// Copyright (c) 2013, Joyent, Inc. All rights reserved.

/*
 * Dynamically generated JSON configuration file for mackerel
 *
 * If run directly, prints out config as JSON for easy parsing/printing (e.g.
 * pipe to 'json').
 *
 * SECTIONS:
 * - local helper variables
 * - mahi config
 * - workflow config
 * - assets
 * - backoff settings
 * - job configuration
 */

var path = require('path');
var c = {};
module.exports = c;

c.manta = require('./config.json').manta;
c.mahi = require('./config.json').mahi;
c.workflow = require('./config.json').workflow;
c.monitorBackoff = require('./config.json').monitorBackoff;

/******************************/
/*   LOCAL HELPER VARIABLES   */
/******************************/

var user, mbase, md, lbase, ld, userbase;

user = c.manta.user;

/*
 * Modify these variables to match your environment.
 */

mbase = '/' + user + '/stor/usage'; // manta base directory
md = mbase + '/assets'; // manta assets directory
userbase = '/reports/usage'; // user-accessible base directory

lbase = path.resolve(__dirname, '..'); // local base directory
ld = lbase + '/assets'; // local assets directory

c.mantaBaseDir = mbase;
c.localBaseDir = lbase;

/******************************/
/*           ASSETS           */
/******************************/

// assets is a mapping from the manta object path to the local file path
c.assets = {};
c.assets[md + '/bin/request-map'] = ld + '/bin/request-map';
c.assets[md + '/bin/storage-map'] = ld + '/bin/storage-map';
c.assets[md + '/bin/storage-reduce1'] = ld + '/bin/storage-reduce1';
c.assets[md + '/bin/storage-reduce3'] = ld + '/bin/storage-reduce3';
c.assets[md + '/bin/sum-columns'] = ld + '/bin/sum-columns';
c.assets[md + '/lib/deliver-access.js'] = ld + '/lib/deliver-access.js';
c.assets[md + '/lib/deliver-usage.js'] = ld + '/lib/deliver-usage.js';
c.assets[md + '/bin/deliver-usage'] = ld + '/bin/deliver-usage';
c.assets[md + '/lib/request-map.js'] = ld + '/lib/request-map.js';
c.assets[md + '/lib/storage-map.js'] = ld + '/lib/storage-map.js';
c.assets[md + '/lib/storage-reduce1.js'] = ld + '/lib/storage-reduce1.js';
c.assets[md + '/lib/storage-reduce3.js'] = ld + '/lib/storage-reduce3.js';
c.assets[md + '/lib/sum-columns.js'] = ld + '/lib/sum-columns.js';
c.assets[md + '/node_modules.tar'] = ld +'/node_modules.tar';
// since the lookup file is generated at job run time, meter.js needs to know
// the manta path for the lookup file
c.mantaLookupPath = md + '/etc/lookup.json';
c.assets[c.mantaLookupPath] = ld + '/etc/lookup.json';

/******************************/
/*      JOB CONFIGURATION     */
/******************************/

// job configuration
// each job object must have a 'keygen' field pointing to the path of the
// keygen file, and a 'job' field containing the job manifest.
c.jobs = {};

c.jobs.storage = {

    /******************/
    /* STORAGE HOURLY */
    /******************/

    hourly: {
        // keygen name (required)
        keygen: 'StorageHourlyKeyGenerator',

        // additional keygen arguments (date will always be passed in)
        keygenArgs: {
            // where to find source keys
            source: '/poseidon/stor/manatee_backups'
        },

        // name of the workflow. depends on which key generator is
        // used for this job
        workflow: 'runjob',

        // manta destination path for link to latest report
        linkPath: mbase + '/storage/latest-hourly',

        // job manifest (required)
        job: {
            name: 'metering-storage-hourly-$year-$month-$dayT$hour',
            phases: [ {
                type : 'map',
                assets : [
                    md + '/node_modules.tar',
                    md + '/bin/storage-map',
                    md + '/lib/storage-map.js'
                ],
                exec : '/assets' + md + '/bin/storage-map'
            }, {
                type: 'reduce',
                memory: 2048,
                assets : [
                    md + '/node_modules.tar',
                    md + '/bin/storage-reduce1',
                    md + '/lib/storage-reduce1.js'
                ],
                exec: '/assets' + md + '/bin/storage-reduce1',
                count: 1
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/storage-reduce3',
                    md + '/lib/storage-reduce3.js'
                ],
                exec: '/assets' + md + '/bin/storage-reduce3',
                count: 1
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/deliver-usage',
                    md + '/etc/lookup.json',
                    md + '/lib/deliver-usage.js',
                ],
                exec: '/assets' + md + '/bin/deliver-usage',
                count: 1 // final reduce phases must have exactly one reducer to collate results
            } ]
        },

        // specific job environment settings that will be prepended to each exec string
        env: {
            // NOTE: the order in which the namespaces appear here will be
            // the order in which links appearing in multiple namespaces will
            // be counted
            // example: if links pointing to the same object appear in both
            // /stor and /public, and the desired behavior is to count the
            // object under the /stor namespace over the public namespace,
            // put "stor" before "public" in the space-separated list below:
            NAMESPACES: 'stor public jobs reports',
            ZCAT: 'gzcat',

            HEADER_CONTENT_TYPE: 'application/x-json-stream',

            // manta destination path (for final mpipe)
            DEST: mbase + '/storage/$year/$month/$day/$hour/h$hour.json',

            // manta destination path for user reports
            // user login will be prepended to this path during the job
            USER_DEST: userbase + '/storage/$year/$month/$day/$hour/h$hour.json'
        }
    },

    /*****************/
    /* STORAGE DAILY */
    /*****************/

    daily: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/usage/storage/$year/$month/$day',
            regex: 'h[0-9][0-9]'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/storage/latest-daily',
        job: {
            name: 'metering-storage-daily-$year-$month-$day',
            phases: [ {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1 // final reduce phases must have exactly one reducer to collate results
            } ]
        }
    },

    /*******************/
    /* STORAGE MONTHLY */
    /*******************/

    monthly: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/usage/storage/$year/$month',
            regex: 'd[0-9][0-9]'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/storage/latest-monthly',
        job: {
            name: 'metering-storage-monthly-$year-$month',
            phases: [ {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1 // final reduce phases must have exactly one reducer to collate results
            } ]
        }
    }
};

c.jobs.request = {

    /******************/
    /* REQUEST HOURLY */
    /******************/

    hourly: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/logs/muskie/$year/$month/$day/$hour'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/request/latest-hourly',
        job: {
            name: 'metering-request-hourly-$year-$month-$dayT$hour',
            phases: [ {
                type: 'map',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/request-map',
                    md + '/lib/deliver-access.js',
                    md + '/lib/request-map.js'
                ],
                exec: '/assets' + md + '/bin/request-map'
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/deliver-usage',
                    md + '/etc/lookup.json',
                    md + '/lib/deliver-usage.js',
                ],
                exec: '/assets' + md + '/bin/deliver-usage',
                count: 1 // final reduce phases must have exactly one reducer to collate results
            } ]
        },
        env: {
            HEADER_CONTENT_TYPE: 'application/x-json-stream',
            DEST: mbase + '/request/$year/$month/$day/$hour/h$hour.json',
            // location for customer-accessible, sanitized muskie access logs
            ACCESS_DEST: '/reports/access-logs/$year/$month/$day/$hour/h$hour.json',
            USER_DEST: userbase + '/request/$year/$month/$day/$hour/h$hour.json'
        }
    },

    /*****************/
    /* REQUEST DAILY */
    /*****************/

    daily: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/usage/request/$year/$month/$day',
            regex: 'h[0-9][0-9]'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/request/latest-daily',
        job: {
            name: 'metering-request-daily-$year-$month-$day',
            phases: [ {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js'
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            } ]
        }
    },

    /*******************/
    /* REQUEST MONTHLY */
    /*******************/

    monthly: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/usage/request/$year/$month',
            regex: 'd[0-9][0-9]'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/request/latest-monthly',
        job: {
            name: 'metering-request-monthly-$year-$month',
            phases: [ {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            } ]
        }
    }
};

c.jobs.compute = {

    /******************/
    /* COMPUTE HOURLY */
    /******************/

    hourly: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/logs/marlin-agent/$year/$month/$day/$hour'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/compute/latest-hourly',
        job: {
            name: 'metering-compute-hourly-$year-$month-$dayT$hour',
            phases: [ {
                type: 'map',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/compute-map',
                    md + '/lib/compute-map.js'
                ],
                exec: '/assets' + md + '/bin/compute-map'
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/deliver-usage',
                    md + '/etc/lookup.json',
                    md + '/lib/deliver-usage.js',
                ],
                exec: '/assets' + md + '/bin/deliver-usage',
                count: 1 // final reduce phases must have exactly one reducer to collate results
            } ]
        },
        env: {
            HEADER_CONTENT_TYPE: 'application/x-json-stream',
            DEST: mbase + '/compute/$year/$month/$day/$hour/h$hour.json',
            USER_DEST: userbase + '/compute/$year/$month/$day/$hour/h$hour.json'
        }
    },

    /*****************/
    /* COMPUTE DAILY */
    /*****************/

    daily: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/usage/compute/$year/$month/$day',
            regex: 'h[0-9][0-9]'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/compute/latest-daily',
        job: {
            name: 'metering-compute-daily-$year-$month-$day',
            phases: [ {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js'
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            } ]
        }
    },

    /*******************/
    /* COMPUTE MONTHLY */
    /*******************/

    monthly: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/usage/compute/$year/$month',
            regex: 'd[0-9][0-9]'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/compute/latest-monthly',
        job: {
            name: 'metering-compute-monthly-$year-$month',
            phases: [ {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            } ]
        }
    }
}

if (require.main === module) {
    console.log(JSON.stringify(c, null, 2));
}

<commit_msg>MANTA-1196 add compute files to asset list<commit_after>#!/usr/bin/env node
// Copyright (c) 2013, Joyent, Inc. All rights reserved.

/*
 * Dynamically generated JSON configuration file for mackerel
 *
 * If run directly, prints out config as JSON for easy parsing/printing (e.g.
 * pipe to 'json').
 *
 * SECTIONS:
 * - local helper variables
 * - mahi config
 * - workflow config
 * - assets
 * - backoff settings
 * - job configuration
 */

var path = require('path');
var c = {};
module.exports = c;

c.manta = require('./config.json').manta;
c.mahi = require('./config.json').mahi;
c.workflow = require('./config.json').workflow;
c.monitorBackoff = require('./config.json').monitorBackoff;

/******************************/
/*   LOCAL HELPER VARIABLES   */
/******************************/

var user, mbase, md, lbase, ld, userbase;

user = c.manta.user;

/*
 * Modify these variables to match your environment.
 */

mbase = '/' + user + '/stor/usage'; // manta base directory
md = mbase + '/assets'; // manta assets directory
userbase = '/reports/usage'; // user-accessible base directory

lbase = path.resolve(__dirname, '..'); // local base directory
ld = lbase + '/assets'; // local assets directory

c.mantaBaseDir = mbase;
c.localBaseDir = lbase;

/******************************/
/*           ASSETS           */
/******************************/

// assets is a mapping from the manta object path to the local file path
c.assets = {};
c.assets[md + '/bin/request-map'] = ld + '/bin/request-map';
c.assets[md + '/bin/storage-map'] = ld + '/bin/storage-map';
c.assets[md + '/bin/storage-reduce1'] = ld + '/bin/storage-reduce1';
c.assets[md + '/bin/storage-reduce3'] = ld + '/bin/storage-reduce3';
c.assets[md + '/bin/sum-columns'] = ld + '/bin/sum-columns';
c.assets[md + '/lib/compute-map.js'] = ld + '/lib/compute-map.js';
c.assets[md + '/bin/compute-map'] = ld + '/bin/compute-map';
c.assets[md + '/lib/deliver-access.js'] = ld + '/lib/deliver-access.js';
c.assets[md + '/lib/deliver-usage.js'] = ld + '/lib/deliver-usage.js';
c.assets[md + '/bin/deliver-usage'] = ld + '/bin/deliver-usage';
c.assets[md + '/lib/request-map.js'] = ld + '/lib/request-map.js';
c.assets[md + '/lib/storage-map.js'] = ld + '/lib/storage-map.js';
c.assets[md + '/lib/storage-reduce1.js'] = ld + '/lib/storage-reduce1.js';
c.assets[md + '/lib/storage-reduce3.js'] = ld + '/lib/storage-reduce3.js';
c.assets[md + '/lib/sum-columns.js'] = ld + '/lib/sum-columns.js';
c.assets[md + '/node_modules.tar'] = ld +'/node_modules.tar';
// since the lookup file is generated at job run time, meter.js needs to know
// the manta path for the lookup file
c.mantaLookupPath = md + '/etc/lookup.json';
c.assets[c.mantaLookupPath] = ld + '/etc/lookup.json';

/******************************/
/*      JOB CONFIGURATION     */
/******************************/

// job configuration
// each job object must have a 'keygen' field pointing to the path of the
// keygen file, and a 'job' field containing the job manifest.
c.jobs = {};

c.jobs.storage = {

    /******************/
    /* STORAGE HOURLY */
    /******************/

    hourly: {
        // keygen name (required)
        keygen: 'StorageHourlyKeyGenerator',

        // additional keygen arguments (date will always be passed in)
        keygenArgs: {
            // where to find source keys
            source: '/poseidon/stor/manatee_backups'
        },

        // name of the workflow. depends on which key generator is
        // used for this job
        workflow: 'runjob',

        // manta destination path for link to latest report
        linkPath: mbase + '/storage/latest-hourly',

        // job manifest (required)
        job: {
            name: 'metering-storage-hourly-$year-$month-$dayT$hour',
            phases: [ {
                type : 'map',
                assets : [
                    md + '/node_modules.tar',
                    md + '/bin/storage-map',
                    md + '/lib/storage-map.js'
                ],
                exec : '/assets' + md + '/bin/storage-map'
            }, {
                type: 'reduce',
                memory: 2048,
                assets : [
                    md + '/node_modules.tar',
                    md + '/bin/storage-reduce1',
                    md + '/lib/storage-reduce1.js'
                ],
                exec: '/assets' + md + '/bin/storage-reduce1',
                count: 1
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/storage-reduce3',
                    md + '/lib/storage-reduce3.js'
                ],
                exec: '/assets' + md + '/bin/storage-reduce3',
                count: 1
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/deliver-usage',
                    md + '/etc/lookup.json',
                    md + '/lib/deliver-usage.js',
                ],
                exec: '/assets' + md + '/bin/deliver-usage',
                count: 1 // final reduce phases must have exactly one reducer to collate results
            } ]
        },

        // specific job environment settings that will be prepended to each exec string
        env: {
            // NOTE: the order in which the namespaces appear here will be
            // the order in which links appearing in multiple namespaces will
            // be counted
            // example: if links pointing to the same object appear in both
            // /stor and /public, and the desired behavior is to count the
            // object under the /stor namespace over the public namespace,
            // put "stor" before "public" in the space-separated list below:
            NAMESPACES: 'stor public jobs reports',
            ZCAT: 'gzcat',

            HEADER_CONTENT_TYPE: 'application/x-json-stream',

            // manta destination path (for final mpipe)
            DEST: mbase + '/storage/$year/$month/$day/$hour/h$hour.json',

            // manta destination path for user reports
            // user login will be prepended to this path during the job
            USER_DEST: userbase + '/storage/$year/$month/$day/$hour/h$hour.json'
        }
    },

    /*****************/
    /* STORAGE DAILY */
    /*****************/

    daily: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/usage/storage/$year/$month/$day',
            regex: 'h[0-9][0-9]'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/storage/latest-daily',
        job: {
            name: 'metering-storage-daily-$year-$month-$day',
            phases: [ {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1 // final reduce phases must have exactly one reducer to collate results
            } ]
        }
    },

    /*******************/
    /* STORAGE MONTHLY */
    /*******************/

    monthly: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/usage/storage/$year/$month',
            regex: 'd[0-9][0-9]'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/storage/latest-monthly',
        job: {
            name: 'metering-storage-monthly-$year-$month',
            phases: [ {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1 // final reduce phases must have exactly one reducer to collate results
            } ]
        }
    }
};

c.jobs.request = {

    /******************/
    /* REQUEST HOURLY */
    /******************/

    hourly: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/logs/muskie/$year/$month/$day/$hour'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/request/latest-hourly',
        job: {
            name: 'metering-request-hourly-$year-$month-$dayT$hour',
            phases: [ {
                type: 'map',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/request-map',
                    md + '/lib/deliver-access.js',
                    md + '/lib/request-map.js'
                ],
                exec: '/assets' + md + '/bin/request-map'
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/deliver-usage',
                    md + '/etc/lookup.json',
                    md + '/lib/deliver-usage.js',
                ],
                exec: '/assets' + md + '/bin/deliver-usage',
                count: 1 // final reduce phases must have exactly one reducer to collate results
            } ]
        },
        env: {
            HEADER_CONTENT_TYPE: 'application/x-json-stream',
            DEST: mbase + '/request/$year/$month/$day/$hour/h$hour.json',
            // location for customer-accessible, sanitized muskie access logs
            ACCESS_DEST: '/reports/access-logs/$year/$month/$day/$hour/h$hour.json',
            USER_DEST: userbase + '/request/$year/$month/$day/$hour/h$hour.json'
        }
    },

    /*****************/
    /* REQUEST DAILY */
    /*****************/

    daily: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/usage/request/$year/$month/$day',
            regex: 'h[0-9][0-9]'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/request/latest-daily',
        job: {
            name: 'metering-request-daily-$year-$month-$day',
            phases: [ {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js'
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            } ]
        }
    },

    /*******************/
    /* REQUEST MONTHLY */
    /*******************/

    monthly: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/usage/request/$year/$month',
            regex: 'd[0-9][0-9]'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/request/latest-monthly',
        job: {
            name: 'metering-request-monthly-$year-$month',
            phases: [ {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            } ]
        }
    }
};

c.jobs.compute = {

    /******************/
    /* COMPUTE HOURLY */
    /******************/

    hourly: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/logs/marlin-agent/$year/$month/$day/$hour'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/compute/latest-hourly',
        job: {
            name: 'metering-compute-hourly-$year-$month-$dayT$hour',
            phases: [ {
                type: 'map',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/compute-map',
                    md + '/lib/compute-map.js'
                ],
                exec: '/assets' + md + '/bin/compute-map'
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            }, {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/deliver-usage',
                    md + '/etc/lookup.json',
                    md + '/lib/deliver-usage.js',
                ],
                exec: '/assets' + md + '/bin/deliver-usage',
                count: 1 // final reduce phases must have exactly one reducer to collate results
            } ]
        },
        env: {
            HEADER_CONTENT_TYPE: 'application/x-json-stream',
            DEST: mbase + '/compute/$year/$month/$day/$hour/h$hour.json',
            USER_DEST: userbase + '/compute/$year/$month/$day/$hour/h$hour.json'
        }
    },

    /*****************/
    /* COMPUTE DAILY */
    /*****************/

    daily: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/usage/compute/$year/$month/$day',
            regex: 'h[0-9][0-9]'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/compute/latest-daily',
        job: {
            name: 'metering-compute-daily-$year-$month-$day',
            phases: [ {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js'
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            } ]
        }
    },

    /*******************/
    /* COMPUTE MONTHLY */
    /*******************/

    monthly: {
        keygen: 'FindKeyGenerator',
        keygenArgs: {
            source: '/poseidon/stor/usage/compute/$year/$month',
            regex: 'd[0-9][0-9]'
        },
        workflow: 'find-runjob',
        linkPath: mbase + '/compute/latest-monthly',
        job: {
            name: 'metering-compute-monthly-$year-$month',
            phases: [ {
                type: 'reduce',
                assets: [
                    md + '/node_modules.tar',
                    md + '/bin/sum-columns',
                    md + '/lib/sum-columns.js',
                ],
                exec: '/assets' + md + '/bin/sum-columns',
                count: 1
            } ]
        }
    }
}

if (require.main === module) {
    console.log(JSON.stringify(c, null, 2));
}

<|endoftext|>