<commit_before>var chai = require('chai');
var sinon = require('sinon');
var expect = chai.expect;
var Mugshot = require('../lib/mugshot.js');
var path = require('path');

chai.use(require('sinon-chai'));

describe('Mugshot', function() {
  var dummySelector = {
        name: 'path'
      },
      captureItem = {
        name: dummySelector.name,
        selector: 'a dom selector'
      },
      rect = {
        width: 100,
        height: 100,
        top: 50,
        left: 50
      },
      callback,
      error = new Error('Fatal Error'),
      baseline = new Buffer('bXVnc2hvdA=='),
      screenshot = new Buffer('ZmxvcmVudGlu'),
      diff = new Buffer('anything'),
      rootDirectory = 'visual-tests',
      extension = '.png',
      baselinePath = path.join(rootDirectory, dummySelector.name + extension),
      screenshotPath = path.join(rootDirectory, dummySelector.name + '.new' +
        extension),
      diffPath = path.join(rootDirectory, dummySelector.name + '.diff' +
        extension),
      mugshot, browser,
      FS, differ,
      PNGProcessor;

  beforeEach(function() {
    browser = {
      takeScreenshot: sinon.stub().yields(null, screenshot),
      getBoundingClientRect: sinon.stub()
    };

    FS = {
      exists: sinon.stub(),
      readFile: sinon.stub(),
      writeFile: sinon.stub(),
      mkdir: sinon.stub().yields(null),
      unlink: sinon.stub()
    };

    PNGProcessor = {
      crop: sinon.stub()
    };

    differ = {
      isEqual: sinon.stub(),
      createDiff: sinon.stub()
    };

    var options = {
      differ: differ,
      fs: FS,
      PNGProcessor: PNGProcessor
    };

    callback = sinon.spy();

    mugshot = new Mugshot(browser, options);
  });

  it('should throw an error if no selector is provided', function() {
    expect(mugshot.test.bind(mugshot)).to.throw(Error);
  });

  it('should throw an error if the parameter is not an object', function() {
    expect(mugshot.test.bind(mugshot, function() {}, callback)).to.throw(Error);
  });

  it('should throw an error if the parameter is an array', function() {
    expect(mugshot.test.bind(mugshot, [], callback)).to.throw(Error);
  });

  it('should throw an error if the object has no name property', function() {
    expect(mugshot.test.bind(mugshot, {}, callback)).to.throw(Error);
  });

  it('should throw an error if no callback is provided', function() {
    expect(mugshot.test.bind(mugshot, dummySelector)).to.throw(Error);
  });

  it('should throw an error if the callback param is not a function',
     function() {
    expect(mugshot.test.bind(mugshot, dummySelector, {})).to.throw(Error);
  });

  it('should create the rootDirectory', function() {
    mugshot.test(dummySelector, callback);

    expect(FS.mkdir).to.have.been.calledWith(rootDirectory);
  });

  it('should not throw error if the rootDirectory already exists', function() {
    var error = {code: 'EEXIST'};
    FS.mkdir.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.not.called;
  });

  it('should throw error if mkdir callback receives another error', function() {
    FS.mkdir.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should call the browser to take a screenshot', function() {
    mugshot.test(dummySelector, callback);

    expect(browser.takeScreenshot).to.have.been.calledOnce;
  });

  it('should throw an error if the screenshot fails', function() {
    browser.takeScreenshot.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should verify if a baseline already exists', function() {
    mugshot.test(dummySelector, callback);

    expect(FS.exists).to.have.been.calledWith(baselinePath, sinon.match.func);
  });

  it('should write the screenshot on disk if no baseline exists', function() {
    FS.exists.yields(false);

    mugshot.test(dummySelector, callback);

    expect(FS.writeFile).to.have.been.calledWith(baselinePath, screenshot,
      sinon.match.func);
  });

  it('should throw an error if the baseline cannot be written', function() {
    FS.exists.yields(false);
    FS.writeFile.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not write the screenshot on disk if there is already a baseline',
     function() {
    FS.exists.yields(true);

    mugshot.test(dummySelector, callback);

    expect(FS.writeFile).to.not.have.been.called;
  });

  it('should read the baseline from disk if it exists', function() {
    FS.exists.yields(true);

    mugshot.test(dummySelector, callback);

    expect(FS.readFile).to.have.been.calledWith(baselinePath, sinon.match.func);
  });

  it('should throw an error if the baseline cannot be read', function() {
    FS.exists.yields(true);
    FS.readFile.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not read a baseline from disk if there is none', function() {
    FS.exists.yields(false);

    mugshot.test(dummySelector, callback);

    expect(FS.readFile).to.not.have.been.called;
  });

  it('should call the differ to compare the baseline from the fs with the ' +
     'screenshot from the browser', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);

    mugshot.test(dummySelector, callback);

    expect(differ.isEqual).to.have.been.calledWith(baseline, screenshot,
      sinon.match.func);
  });

  it('should throw an error if the comparison fails', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not compare if there is no baseline', function() {
    FS.exists.yields(false);
    FS.readFile.yields(null, baseline);

    mugshot.test(dummySelector, callback);

    expect(differ.isEqual).to.not.have.been.called;
  });

  it('should create a diff only if there are differences', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);

    mugshot.test(dummySelector, callback);

    expect(differ.createDiff).to.have.been.calledWith(baseline, screenshot,
      sinon.match.func);
  });

  it('should throw an error if the diff building fails', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);
    differ.createDiff.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not create a diff if there are no differences', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);

    mugshot.test(dummySelector, callback);

    expect(differ.createDiff).to.not.have.been.called;
  });

  it('should call the fs to write the diff on disk', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);
    differ.createDiff.yields(null, diff);
    FS.writeFile.yields(null);

    mugshot.test(dummySelector, callback);

    expect(FS.writeFile).to.have.been.calledWith(diffPath, diff,
      sinon.match.func);
  });

  it('should throw an error if the diff cannot be written', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);
    differ.createDiff.yields(null, diff);
    FS.writeFile.onFirstCall().yields(null);
    FS.writeFile.onSecondCall().yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not call the fs to write the diff on disk if there is none',
     function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);

    mugshot.test(dummySelector, callback);

    expect(FS.writeFile).to.not.have.been.called;
  });

  it('should call the fs to write the screenshot on disk', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);
    differ.createDiff.yields(null, diff);

    mugshot.test(dummySelector, callback);

    expect(FS.writeFile).to.have.been.calledWith(screenshotPath, screenshot,
      sinon.match.func);
  });

  it('should throw an error if the screenshot cannot be written', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);
    differ.createDiff.yields(null, diff);
    FS.writeFile.onFirstCall().yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should try to unlink old diff if the comparison returns true',
     function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);
    FS.unlink.onFirstCall().yields(null);
    mugshot.test(dummySelector, callback);

    expect(FS.unlink).to.have.been.calledWith(diffPath);
  });

  it('should try to unlink old screenshot if the comparison returns true',
     function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);

    mugshot.test(dummySelector, callback);

    expect(FS.unlink).to.have.been.calledWith(screenshotPath);
  });

  it('should not try to unlink old diff and screenshot if the comparison ' +
     'returns false', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);

    mugshot.test(dummySelector, callback);

    expect(FS.unlink).to.not.have.been.called;
  });

  it('should not throw an error if the file is not there', function() {
    var error = {code: 'ENOENT'};
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);
    FS.unlink.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.not.calledWith(error);
  });

  it('should throw an error if the file couldn\'t be unlinked', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);
    FS.unlink.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should get the bounding rect if a selector is provided', function() {
    mugshot.test(captureItem, callback);

    expect(browser.getBoundingClientRect).to.have.been.calledWith(
      captureItem.selector, sinon.match.func);
  });

  it('should throw an error if the bounding rect couldn\'t be calculated',
     function() {
    browser.getBoundingClientRect.yields(error);

    mugshot.test(captureItem, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not get the bounding rect if no selector is provided', function() {
    mugshot.test(dummySelector, callback);

    expect(browser.getBoundingClientRect).to.not.have.been.called;
  });

  it('should crop the image if a selector is provided', function() {
    browser.getBoundingClientRect.yields(null, rect);

    mugshot.test(captureItem, callback);

    expect(PNGProcessor.crop).to.have.been.calledWith(screenshot, rect,
      sinon.match.func);
  });

  it('should throw an error if the screenshot couldn\'t be cropped',
     function() {
    browser.getBoundingClientRect.yields(error);
    PNGProcessor.crop.yields(error);

    mugshot.test(captureItem, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not crop the image if there is no selector', function() {
    mugshot.test(dummySelector, callback);

    expect(PNGProcessor.crop).to.not.have.been.called;
  });
});
<commit_msg>add tests to check callback is called correctly<commit_after>var chai = require('chai');
var sinon = require('sinon');
var expect = chai.expect;
var Mugshot = require('../lib/mugshot.js');
var path = require('path');

chai.use(require('sinon-chai'));

describe('Mugshot', function() {
  var dummySelector = {
        name: 'path'
      },
      captureItem = {
        name: dummySelector.name,
        selector: 'a dom selector'
      },
      rect = {
        width: 100,
        height: 100,
        top: 50,
        left: 50
      },
      callback,
      error = new Error('Fatal Error'),
      baseline = new Buffer('bXVnc2hvdA=='),
      screenshot = new Buffer('ZmxvcmVudGlu'),
      diff = new Buffer('anything'),
      rootDirectory = 'visual-tests',
      extension = '.png',
      baselinePath = path.join(rootDirectory, dummySelector.name + extension),
      screenshotPath = path.join(rootDirectory, dummySelector.name + '.new' +
        extension),
      diffPath = path.join(rootDirectory, dummySelector.name + '.diff' +
        extension),
      mugshot, browser,
      FS, differ,
      PNGProcessor;

  beforeEach(function() {
    browser = {
      takeScreenshot: sinon.stub().yields(null, screenshot),
      getBoundingClientRect: sinon.stub()
    };

    FS = {
      exists: sinon.stub(),
      readFile: sinon.stub(),
      writeFile: sinon.stub(),
      mkdir: sinon.stub().yields(null),
      unlink: sinon.stub()
    };

    PNGProcessor = {
      crop: sinon.stub()
    };

    differ = {
      isEqual: sinon.stub(),
      createDiff: sinon.stub()
    };

    var options = {
      differ: differ,
      fs: FS,
      PNGProcessor: PNGProcessor
    };

    callback = sinon.spy();

    mugshot = new Mugshot(browser, options);
  });

  it('should throw an error if no selector is provided', function() {
    expect(mugshot.test.bind(mugshot)).to.throw(Error);
  });

  it('should throw an error if the parameter is not an object', function() {
    expect(mugshot.test.bind(mugshot, function() {}, callback)).to.throw(Error);
  });

  it('should throw an error if the parameter is an array', function() {
    expect(mugshot.test.bind(mugshot, [], callback)).to.throw(Error);
  });

  it('should throw an error if the object has no name property', function() {
    expect(mugshot.test.bind(mugshot, {}, callback)).to.throw(Error);
  });

  it('should throw an error if no callback is provided', function() {
    expect(mugshot.test.bind(mugshot, dummySelector)).to.throw(Error);
  });

  it('should throw an error if the callback param is not a function',
     function() {
    expect(mugshot.test.bind(mugshot, dummySelector, {})).to.throw(Error);
  });

  it('should create the rootDirectory', function() {
    mugshot.test(dummySelector, callback);

    expect(FS.mkdir).to.have.been.calledWith(rootDirectory);
  });

  it('should not throw error if the rootDirectory already exists', function() {
    var error = {code: 'EEXIST'};
    FS.mkdir.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.not.called;
  });

  it('should throw error if mkdir callback receives another error', function() {
    FS.mkdir.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should call the browser to take a screenshot', function() {
    mugshot.test(dummySelector, callback);

    expect(browser.takeScreenshot).to.have.been.calledOnce;
  });

  it('should throw an error if the screenshot fails', function() {
    browser.takeScreenshot.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should verify if a baseline already exists', function() {
    mugshot.test(dummySelector, callback);

    expect(FS.exists).to.have.been.calledWith(baselinePath, sinon.match.func);
  });

  it('should write the screenshot on disk if no baseline exists', function() {
    FS.exists.yields(false);

    mugshot.test(dummySelector, callback);

    expect(FS.writeFile).to.have.been.calledWith(baselinePath, screenshot,
      sinon.match.func);
  });

  it('should throw an error if the baseline cannot be written', function() {
    FS.exists.yields(false);
    FS.writeFile.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not write the screenshot on disk if there is already a baseline',
     function() {
    FS.exists.yields(true);

    mugshot.test(dummySelector, callback);

    expect(FS.writeFile).to.not.have.been.called;
  });

  it('should read the baseline from disk if it exists', function() {
    FS.exists.yields(true);

    mugshot.test(dummySelector, callback);

    expect(FS.readFile).to.have.been.calledWith(baselinePath, sinon.match.func);
  });

  it('should throw an error if the baseline cannot be read', function() {
    FS.exists.yields(true);
    FS.readFile.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not read a baseline from disk if there is none', function() {
    FS.exists.yields(false);

    mugshot.test(dummySelector, callback);

    expect(FS.readFile).to.not.have.been.called;
  });

  it('should call the differ to compare the baseline from the fs with the ' +
     'screenshot from the browser', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);

    mugshot.test(dummySelector, callback);

    expect(differ.isEqual).to.have.been.calledWith(baseline, screenshot,
      sinon.match.func);
  });

  it('should throw an error if the comparison fails', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not compare if there is no baseline', function() {
    FS.exists.yields(false);
    FS.readFile.yields(null, baseline);

    mugshot.test(dummySelector, callback);

    expect(differ.isEqual).to.not.have.been.called;
  });

  it('should create a diff only if there are differences', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);

    mugshot.test(dummySelector, callback);

    expect(differ.createDiff).to.have.been.calledWith(baseline, screenshot,
      sinon.match.func);
  });

  it('should throw an error if the diff building fails', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);
    differ.createDiff.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not create a diff if there are no differences', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);

    mugshot.test(dummySelector, callback);

    expect(differ.createDiff).to.not.have.been.called;
  });

  it('should call the fs to write the diff on disk', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);
    differ.createDiff.yields(null, diff);
    FS.writeFile.yields(null);

    mugshot.test(dummySelector, callback);

    expect(FS.writeFile).to.have.been.calledWith(diffPath, diff,
      sinon.match.func);
  });

  it('should throw an error if the diff cannot be written', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);
    differ.createDiff.yields(null, diff);
    FS.writeFile.onFirstCall().yields(null);
    FS.writeFile.onSecondCall().yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not call the fs to write the diff on disk if there is none',
     function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);

    mugshot.test(dummySelector, callback);

    expect(FS.writeFile).to.not.have.been.called;
  });

  it('should call the fs to write the screenshot on disk', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);
    differ.createDiff.yields(null, diff);

    mugshot.test(dummySelector, callback);

    expect(FS.writeFile).to.have.been.calledWith(screenshotPath, screenshot,
      sinon.match.func);
  });

  it('should throw an error if the screenshot cannot be written', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);
    differ.createDiff.yields(null, diff);
    FS.writeFile.onFirstCall().yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should try to unlink old diff if the comparison returns true',
     function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);
    FS.unlink.onFirstCall().yields(null);
    mugshot.test(dummySelector, callback);

    expect(FS.unlink).to.have.been.calledWith(diffPath);
  });

  it('should try to unlink old screenshot if the comparison returns true',
     function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);

    mugshot.test(dummySelector, callback);

    expect(FS.unlink).to.have.been.calledWith(screenshotPath);
  });

  it('should not try to unlink old diff and screenshot if the comparison ' +
     'returns false', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);

    mugshot.test(dummySelector, callback);

    expect(FS.unlink).to.not.have.been.called;
  });

  it('should not throw an error if the file is not there', function() {
    var error = {code: 'ENOENT'};
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);
    FS.unlink.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.not.calledWith(error);
  });

  it('should throw an error if the file couldn\'t be unlinked', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);
    FS.unlink.yields(error);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should get the bounding rect if a selector is provided', function() {
    mugshot.test(captureItem, callback);

    expect(browser.getBoundingClientRect).to.have.been.calledWith(
      captureItem.selector, sinon.match.func);
  });

  it('should throw an error if the bounding rect couldn\'t be calculated',
     function() {
    browser.getBoundingClientRect.yields(error);

    mugshot.test(captureItem, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not get the bounding rect if no selector is provided', function() {
    mugshot.test(dummySelector, callback);

    expect(browser.getBoundingClientRect).to.not.have.been.called;
  });

  it('should crop the image if a selector is provided', function() {
    browser.getBoundingClientRect.yields(null, rect);

    mugshot.test(captureItem, callback);

    expect(PNGProcessor.crop).to.have.been.calledWith(screenshot, rect,
      sinon.match.func);
  });

  it('should throw an error if the screenshot couldn\'t be cropped',
     function() {
    browser.getBoundingClientRect.yields(error);
    PNGProcessor.crop.yields(error);

    mugshot.test(captureItem, callback);

    expect(callback).to.have.been.calledWithExactly(error);
  });

  it('should not crop the image if there is no selector', function() {
    mugshot.test(dummySelector, callback);

    expect(PNGProcessor.crop).to.not.have.been.called;
  });

  it('should return true if there is no baseline', function() {
    FS.exists.yields(false);
    FS.writeFile.yields(null);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(null, true);
  });

  it('should return false if there are differences', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, false);
    differ.createDiff.yields(null, diff);
    FS.writeFile.yields(null);
    FS.writeFile.yields(null);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(null, false);
  });

  it('should return false if there are differences', function() {
    FS.exists.yields(true);
    FS.readFile.yields(null, baseline);
    differ.isEqual.yields(null, true);
    FS.unlink.yields(null);
    FS.unlink.yields(null);

    mugshot.test(dummySelector, callback);

    expect(callback).to.have.been.calledWithExactly(null, true);
  });
});
<|endoftext|>


<commit_before>const siteMap = [
  {
    label: 'Join',
    path: 'HOSTNAME',
    subdomained: false,
    children: [],
    matches: () => false
  },

  {
    label: 'Candidates',
    path: 'HOSTNAME/candidates',
    matches: () => window.location.href.match('/candidates'),
    children: [
      {
        label: 'Candidates',
        path: 'HOSTNAME/candidates',
        children: []
      },
      {
        label: 'Nominate',
        path: 'HOSTNAME/nominate',
        children: []
      }
    ]
  },

  {
    label: 'Action',
    path: '/act',
    matches: () =>
      window.location.href.match('/act') ||
      window.location.href.match('/form/submit-event') ||
      window.location.href.match('/form/teams'),
    children: [
      {
        label: 'Action Portal',
        path: '/act',
        matches: () =>
          window.location.href.match('/act') &&
          window.location.href.endsWith('act'),
        children: []
      },
      {
        label: 'Attend an Event',
        path: 'events.HOSTNAME/',
        matches: () => false,
        children: []
      },
      {
        label: 'Host an Event',
        path: '/form/submit-event',
        matches: () => window.location.href.match('/form/submit-event'),
        children: []
      },
      {
        label: 'Call Voters',
        path: '/act/call',
        matches: () => window.location.href.match('/act/call'),
        children: []
      },
      {
        label: 'Join a National Team',
        path: '/form/teams',
        matches: () => false,
        children: []
      },
      {
        label: 'Tell Us About Your District',
        path: 'https://docs.google.com/forms/d/e/1FAIpQLSe8CfK0gUULEVpYFm9Eb4iyGOL-_iDl395qB0z4hny7ek4iNw/viewform?refcode=www.google.com',
        matches: () => false,
        children: []
      },
      {
        label: 'Any special skills?',
        path: 'https://brandnewcongress.org/volunteer',
        matches: () => false,
        children: []
      }
    ]
  },
  {
    label: 'Plan',
    path: '/plan',
    children: [
      {
        label: 'Plan',
        path: '/plan',
        children: []
      },
      {
        label: 'Platform',
        path: '/platform',
        children: []
      }
    ],
    matches: () => window.location.href.match('/plan')
  }
]

export default siteMap
<commit_msg>route to special skills<commit_after>const siteMap = [
  {
    label: 'Join',
    path: 'HOSTNAME',
    subdomained: false,
    children: [],
    matches: () => false
  },

  {
    label: 'Candidates',
    path: 'HOSTNAME/candidates',
    matches: () => window.location.href.match('/candidates'),
    children: [
      {
        label: 'Candidates',
        path: 'HOSTNAME/candidates',
        children: []
      },
      {
        label: 'Nominate',
        path: 'HOSTNAME/nominate',
        children: []
      }
    ]
  },

  {
    label: 'Action',
    path: '/act',
    matches: () =>
      window.location.href.match('/act') ||
      window.location.href.match('/form/submit-event') ||
      window.location.href.match('/form/teams'),
    children: [
      {
        label: 'Action Portal',
        path: '/act',
        matches: () =>
          window.location.href.match('/act') &&
          window.location.href.endsWith('act'),
        children: []
      },
      {
        label: 'Attend an Event',
        path: 'events.HOSTNAME/',
        matches: () => false,
        children: []
      },
      {
        label: 'Host an Event',
        path: '/form/submit-event',
        matches: () => window.location.href.match('/form/submit-event'),
        children: []
      },
      {
        label: 'Call Voters',
        path: '/act/call',
        matches: () => window.location.href.match('/act/call'),
        children: []
      },
      {
        label: 'Join a National Team',
        path: '/form/teams',
        matches: () => false,
        children: []
      },
      {
        label: 'Tell Us About Your District',
        path: 'https://docs.google.com/forms/d/e/1FAIpQLSe8CfK0gUULEVpYFm9Eb4iyGOL-_iDl395qB0z4hny7ek4iNw/viewform?refcode=www.google.com',
        matches: () => false,
        children: []
      },
      {
        label: 'Any special skills?',
        path: 'https://brandnewcongress.org/special-skills',
        matches: () => false,
        children: []
      }
    ]
  },

  {
    label: 'Plan',
    path: '/plan',
    children: [
      {
        label: 'Plan',
        path: '/plan',
        children: []
      },
      {
        label: 'Platform',
        path: '/platform',
        children: []
      }
    ],
    matches: () => window.location.href.match('/plan')
  }
]

export default siteMap
<|endoftext|>


<commit_before>/* global describe, it */

var chai = require('chai');
var wmrm = require('..');

describe('oauth2orize-wmrm', function() {

  it('should export function', function() {
    expect(wmrm).to.be.an('function');
  });

  // https://tools.ietf.org/html/draft-sakimura-oauth-wmrm-00#section-5.2
  describe('responding to simple request', function() {
    var response, err;

    before(function(done) {
      chai.connect.use(function(req, res) {
          var params = {
            code: 'SplxlOBeZQQYbYS6WxSbIA',
            state: req.oauth2.req.state
          };

          wmrm(req.oauth2, res, params);
        })
        .req(function(req) {
          req.oauth2 = {};
          //req.oauth2.redirectURI = 'https://client.example.com';
          req.oauth2.webOrigin = 'https://client.example.com';
          req.oauth2.req = { responseType: 'code', responseMode: 'web_message', state: 'xyz' };
        })
        .end(function(res) {
          response = res;
          done();
        })
        .dispatch();
    });

    it('should respond with headers', function() {
      expect(response.getHeader('Content-Type')).to.equal('text/html;charset=UTF-8');
      expect(response.getHeader('Cache-Control')).to.equal('no-cache, no-store');
      expect(response.getHeader('Pragma')).to.equal('no-cache');
    });

    it('should respond with body', function() {
      expect(response.body).to.equal(
'<!DOCTYPE html>' +
'' +
'' +
  '<title>Authorization Response</title>' +
'' +
'' +
  '' +
'' +
'');
    });
  });

  describe('responding to relay request', function() {
    var response, err;

    before(function(done) {
      chai.connect.use(function(req, res) {
          var params = {
            code: 'SplxlOBeZQQYbYS6WxSbIA',
            state: req.oauth2.req.state
          };

          wmrm(req.oauth2, res, params);
        })
        .req(function(req) {
          req.oauth2 = {};
          //req.oauth2.redirectURI = 'https://client.example.com';
          req.oauth2.webOrigin = 'https://client.example.com';
          req.oauth2.req = { responseType: 'code', responseMode: 'web_message',
            webMessageURI: 'https://api.example.com',
            webMessageTarget: 'apiFrame',
            state: 'xyz' };
        })
        .end(function(res) {
          response = res;
          done();
        })
        .dispatch();
    });

    it('should respond with headers', function() {
      expect(response.getHeader('Content-Type')).to.equal('text/html;charset=UTF-8');
      expect(response.getHeader('Cache-Control')).to.equal('no-cache, no-store');
      expect(response.getHeader('Pragma')).to.equal('no-cache');
    });

    it('should respond with body', function() {
      expect(response.body).to.equal(
'<!DOCTYPE html>' +
'' +
'' +
  '<title>Authorization Response</title>' +
'' +
'' +
  '' +
'' +
'');
    });
  });

});
<commit_msg>Fix tests.<commit_after>/* global describe, it */

var chai = require('chai');
var wmrm = require('..');

describe('oauth2orize-wmrm', function() {

  it('should export function', function() {
    expect(wmrm).to.be.an('function');
  });

  // https://tools.ietf.org/html/draft-sakimura-oauth-wmrm-00#section-5.2
  describe('responding to simple request', function() {
    var response, err;

    before(function(done) {
      chai.connect.use(function(req, res) {
          var params = {
            code: 'SplxlOBeZQQYbYS6WxSbIA',
            state: req.oauth2.req.state
          };

          wmrm(req.oauth2, res, params);
        })
        .req(function(req) {
          req.oauth2 = {};
          //req.oauth2.redirectURI = 'https://client.example.com';
          req.oauth2.webOrigin = 'https://client.example.com';
          req.oauth2.req = { responseType: 'code', responseMode: 'web_message', state: 'xyz' };
        })
        .end(function(res) {
          response = res;
          done();
        })
        .dispatch();
    });

    it('should respond with headers', function() {
      expect(response.getHeader('Content-Type')).to.equal('text/html;charset=UTF-8');
      expect(response.getHeader('Cache-Control')).to.equal('no-cache, no-store');
      expect(response.getHeader('Pragma')).to.equal('no-cache');
    });

    it('should respond with body', function() {
      expect(response.body).to.equal(
'<!DOCTYPE html>' +
'' +
'' +
  '<title>Authorization Response</title>' +
'' +
'' +
  '' +
'' +
'');
    });
  });

  describe('responding to relay request', function() {
    var response, err;

    before(function(done) {
      chai.connect.use(function(req, res) {
          var params = {
            code: 'SplxlOBeZQQYbYS6WxSbIA',
            state: req.oauth2.req.state
          };

          wmrm(req.oauth2, res, params);
        })
        .req(function(req) {
          req.oauth2 = {};
          //req.oauth2.redirectURI = 'https://client.example.com';
          req.oauth2.webOrigin = 'https://client.example.com';
          req.oauth2.req = { responseType: 'code', responseMode: 'web_message',
            webMessageURI: 'https://api.example.com',
            webMessageTarget: 'apiFrame',
            state: 'xyz' };
        })
        .end(function(res) {
          response = res;
          done();
        })
        .dispatch();
    });

    it('should respond with headers', function() {
      expect(response.getHeader('Content-Type')).to.equal('text/html;charset=UTF-8');
      expect(response.getHeader('Cache-Control')).to.equal('no-cache, no-store');
      expect(response.getHeader('Pragma')).to.equal('no-cache');
    });

    it('should respond with body', function() {
      expect(response.body).to.equal(
'<!DOCTYPE html>' +
'' +
'' +
  '<title>Authorization Response</title>' +
'' +
'' +
  '' +
'' +
'');
    });
  });

});
<|endoftext|>


<commit_before>
var esprima = require('esprima');

var __globals__ = global;
var __APOGEE_ENVIRONMENT__ = "NODE";

<commit_msg>update some headers in the npm lib<commit_after>
var esprima = require('esprima');

__globals__ = global;
__APOGEE_ENVIRONMENT__ = "NODE";

<|endoftext|>


<commit_before>const gulp = require('gulp');
const tasks = require('strt-gulpfile')({
  src: 'src',
  dist: 'public/dist'
});

gulp.task('default', gulp.series(
  tasks.clean,
  gulp.parallel(
    tasks.styles,
    tasks.files,
    tasks.scripts,
    tasks.images
  ),
  tasks.watch
));
<commit_msg>update gulpfile👀<commit_after>const gulp = require('gulp');
const tasks = require('strt-gulpfile')({
  src: 'src',
  dist: 'public/dist',
});

gulp.task('default', gulp.series(
  tasks.clean,
  gulp.parallel(
    tasks.styles,
    tasks.images,
    tasks.files,
    tasks.icons,
    tasks.scripts
  ),
  tasks.serve
));
<|endoftext|>


<commit_before>const expect = require('chai').expect;
const path = require('path');
const fs = require('fs');
// const tmp = require('tmp');
const mlog = require('mocha-logger');

const h = require('../../test-helpers.js');
const unpm = require('../../../lib/unity-npm-utils');

// tmp.setGracefulCleanup();

const updateTemplateBehaviour = require('../../shared/unpm-init-package-then-update-template-behaviour.js')

describe.only("'unityPackage.updateTemplate - updates scripts and template files for an existing unity package", () => {
    updateTemplateBehaviour((opts) => {
        return opts.package_path?
            unpm.unityPackage.updateTemplate(opts.package_path):
            new Promise((resolve, reject) => { reject(new Error('missing required option package_path')) });
    }, {
        install_required: false
    });
});

// describe.only("unityPackage.updateTemplate - updates scripts and template files for an existing unity package", () => {
//
//     const pkgNameFoo = "my-pkg-foo";
//     var pkgPath = null;
//     var pkgDist = null;
//     var distDepNames = null;
//     var distScriptNames = null;
//
//     beforeEach(function(done) {
//         this.timeout(10000);
//
//         h.installUnityPackageTemplateToTemp({
//             package_name: pkgNameFoo
//         }, (installErr, tmpInstallPath) => {
//             if (installErr) {
//                 return done(installErr);
//             }
//
//             pkgPath = tmpInstallPath;
//
//             pkgDist = h.readPackageSync(pkgPath);
//             distScriptNames = Object.getOwnPropertyNames(pkgDist.scripts);
//             distDepNames = Object.getOwnPropertyNames(pkgDist.dependencies);
//
//             // rename all scripts
//             unpm.transformPackage({
//                 package_read_path: pkgPath,
//                 package_write_path: pkgPath,
//                 transform: (p, cb) => {
//                     p.scripts = {};
//                     p.dependencies = {};
//                     cb(null, p);
//                 }
//             }, (e, p) => {
//                 return done(e);
//             })
//         });
//     });
//
//     it("uses a package template that includes scripts", function(done) {
//         expect(distScriptNames.length, 'dist template package includes scripts').to.be.gt(0);
//         done();
//     })
//
//     it("uses a package template that includes dependencies", function(done) {
//         expect(distDepNames.length, 'dist template package includes dependencies').to.be.gt(0);
//         done();
//     })
//
//     it("adds all template scripts to main package scripts", function(done) {
//         this.timeout(10000);
//
//         const pkgNoScripts = h.readPackageSync(pkgPath);
//
//         expect(Object.getOwnPropertyNames(pkgNoScripts.scripts).length, 'given scripts have been cleared to an empty object').to.equal(0);
//
//         unpm.unityPackage.updateTemplate(pkgPath)
//             .then(p => {
//                 const pkgAfter = h.readPackageSync(pkgPath);
//                 distScriptNames.forEach(n => {
//                     expect(pkgAfter.scripts[n]).to.equal(pkgDist.scripts[n]);
//                 });
//
//                 done();
//             })
//             .catch(e => done(e));
//     });
//
//     it('preserves the name and scope of the pre-update package', function(done) {
//         this.timeout(10000);
//
//         const nameToKeep = "some-weird-name";
//
//         unpm.unityPackage.setPackageName(pkgPath, {
//             package_name: nameToKeep
//         }, (ne) => {
//             if (ne) {
//                 return done(ne);
//             }
//
//             unpm.unityPackage.updateTemplate(pkgPath)
//                 .then(p => {
//                     const pkgAfter = h.readPackageSync(pkgPath);
//
//                     expect(pkgAfter.name,
//                         'should preserve name of the pre-update package'
//                     ).to.equal(nameToKeep)
//
//                     done();
//                 })
//                 .catch(e => done(e));
//         });
//
//     })
//
//     it("combines scripts from template and pre-update package, preferring the template version", function(done) {
//         this.timeout(10000);
//
//         const pkgNoScripts = h.readPackageSync(pkgPath);
//         var oldScripts = {
//             old_1: 'val 1',
//             old_2: 'val 2'
//         };
//
//         // rename all scripts
//         unpm.transformPackage({
//             package_read_path: pkgPath,
//             package_write_path: pkgPath,
//             transform: (p, cb) => {
//                 p.scripts = {
//                     ...oldScripts,
//                     [distScriptNames[0]]: 'this val should be overwritten with template val for script'
//                 };
//                 cb(null, p);
//             }
//         }, (e, p) => {
//             if (e) {
//                 return done(e);
//             }
//
//             unpm.unityPackage.updateTemplate(pkgPath)
//                 .then(p => {
//                     const pkgAfter = h.readPackageSync(pkgPath);
//                     distScriptNames.forEach(n => {
//                         expect(pkgAfter.scripts[n],
//                             `scripts.${n} should have template value`
//                         ).to.equal(pkgDist.scripts[n]);
//                     });
//
//                     Object.getOwnPropertyNames(oldScripts).forEach(n => {
//                         expect(pkgAfter.scripts[n],
//                             `scripts.${n} should have pre-update value`
//                         ).to.equal(oldScripts[n]);
//                     });
//
//                     return done();
//                 })
//                 .catch(e => done(e));
//
//         });
//     });
//
//     it("combines dependencies from template and pre-update package, preferring the template version", function(done) {
//         this.timeout(10000);
//
//         const pkgNoDeps = h.readPackageSync(pkgPath);
//         var oldDeps = {
//             dep_1: 'val 1',
//             dep_2: 'val 2'
//         };
//
//         // rename all scripts
//         unpm.transformPackage({
//             package_read_path: pkgPath,
//             package_write_path: pkgPath,
//             transform: (p, cb) => {
//                 p.dependencies = {
//                     ...oldDeps,
//                     [distDepNames[0]]: 'this version should be overwritten with template version'
//                 };
//                 cb(null, p);
//             }
//         }, (e, p) => {
//             if (e) {
//                 return done(e);
//             }
//
//             unpm.unityPackage.updateTemplate(pkgPath)
//                 .then(p => {
//                     const pkgAfter = h.readPackageSync(pkgPath);
//                     distDepNames.forEach(n => {
//                         expect(pkgAfter.scripts[n],
//                             `dependencies.${n} should have template value`
//                         ).to.equal(pkgDist.scripts[n]);
//                     });
//
//                     Object.getOwnPropertyNames(oldDeps).forEach(n => {
//                         expect(pkgAfter.dependencies[n],
//                             `dependencies.${n} should have pre-update value`
//                         ).to.equal(oldDeps[n]);
//                     });
//
//                     return done();
//                 })
//                 .catch(e => done(e));
//
//         });
//     });
//
//     it("preserves source files from pre-update package", function(done) {
//         this.timeout(10000);
//
//         const pkgNoDeps = h.readPackageSync(pkgPath);
//
//         const srcFiles = [{
//                 name: 'Foo.cs',
//                 content: 'public class Foo {}'
//             },
//             {
//                 name: 'Bar.cs',
//                 content: 'public class Bar {} '
//             }
//         ];
//
//         unpm.unityPackage.addSrcFiles(pkgPath, srcFiles)
//         .then(asr => {
//             unpm.unityPackage.updateTemplate(pkgPath)
//                 .then(p => {
//                     const pkgAfter = h.readPackageSync(pkgPath);
//
//                     const srcRoot = path.join(pkgPath, 'src', pkgDist.name);
//                     expect(fs.existsSync(srcRoot)).to.equal(true);
//
//                     srcFiles.forEach(f => {
//                         const fpath = path.join(srcRoot, f.name);
//                         expect(fs.existsSync(fpath)).to.equal(true);
//                         expect(fs.readFileSync(fpath, 'utf8')).to.equal(f.content);
//                     });
//
//                     return done();
//                 })
//                 .catch(e => done(e));
//         })
//         .catch(e => done(e));
//
//
//
//     });
//
// });
<commit_msg>had accidently committed describe.only on update-template test<commit_after>
const unpm = require('../../../lib/unity-npm-utils');
const updateTemplateBehaviour = require('../../shared/unpm-init-package-then-update-template-behaviour.js')

describe("'unityPackage.updateTemplate - updates scripts and template files for an existing unity package", () => {
    updateTemplateBehaviour((opts) => {
        return opts.package_path?
            unpm.unityPackage.updateTemplate(opts.package_path):
            new Promise((resolve, reject) => { reject(new Error('missing required option package_path')) });
    }, {
        install_required: false
    });
});
<|endoftext|>


<commit_before>/**
 *	Angular directive to truncate multi-line text to visible height
 *
 *	@param bind (angular bound value to append) REQUIRED
 *	@param ellipsisAppend (string) string to append at end of truncated text after ellipsis, can be HTML OPTIONAL
 *	@param ellipsisAppendClick (function) function to call if ellipsisAppend is clicked (ellipsisAppend must be clicked) OPTIONAL
 *	@param ellipsisSymbol (string) string to use as ellipsis, replaces default '...' OPTIONAL
 *	@param ellipsisSeparator (string) separator to split string, replaces default ' ' OPTIONAL
 *
 *	@example

 *	@example

 *	@example

 *	@example

 *
 */
angular.module('dibari.angular-ellipsis',[])

.directive('ellipsis', ['$timeout', '$window', function($timeout, $window) {

	var AsyncDigest = function(delay) {
		var timeout = null;
		var queue = [];

		this.remove = function(fn) {
			if (queue.indexOf(fn) !== -1) {
				queue.splice(queue.indexOf(fn), 1);
				if (queue.length === 0) {
					$timeout.cancel(timeout);
					timeout = null;
				}
			}
		};
		this.add = function(fn) {
			if (queue.indexOf(fn) === -1) {
				queue.push(fn);
			}
			if(!timeout) {
				timeout = $timeout(function() {
					var copy = queue.slice();
					timeout = null;
					// reset scheduled array first in case one of the functions throws an error
					queue.length = 0;
					copy.forEach(function(fn) {
						fn();
					});
				}, delay);
			}
		};
	};

	var asyncDigestImmediate = new AsyncDigest(0);
	var asyncDigestDebounced = new AsyncDigest(75);

	return {
		restrict	: 'A',
		scope		: {
			ngBind				: '=',
			ngBindHtml			: '=',
			ellipsisAppend		: '@',
			ellipsisAppendClick	: '&',
			ellipsisSymbol		: '@',
			ellipsisSeparator	: '@',
			useParent			: "@",
			ellipsisSeparatorReg: '='
		},
		compile : function(elem, attr, linker) {

			return function(scope, element, attributes) {
				/* Window Resize Variables */
					attributes.lastWindowResizeTime = 0;
					attributes.lastWindowResizeWidth = 0;
					attributes.lastWindowResizeHeight = 0;
					attributes.lastWindowTimeoutEvent = null;
				/* State Variables */
					attributes.isTruncated = false;
				function getParentHeight(element){
					var heightOfChildren = 0;
					angular.forEach(element.parent().children(), function(child){
						if(child!=element[0]){
							heightOfChildren += child.clientHeight;
						}
					});
					return element.parent()[0].clientHeight - heightOfChildren;
				}
				function buildEllipsis() {
					var binding = scope.ngBind || scope.ngBindHtml;
					if(binding.$$unwrapTrustedValue()) {
						binding = binding.$$unwrapTrustedValue();
					}
					if (binding) {
						var i = 0,
							ellipsisSymbol = (typeof(attributes.ellipsisSymbol) !== 'undefined') ? attributes.ellipsisSymbol : '…',
							ellipsisSeparator = (typeof(scope.ellipsisSeparator) !== 'undefined') ? attributes.ellipsisSeparator  : ' ',
							ellipsisSeparatorReg =  (typeof(scope.ellipsisSeparatorReg) !== 'undefined') ? scope.ellipsisSeparatorReg : false,
							appendString = (typeof(scope.ellipsisAppend) !== 'undefined' && scope.ellipsisAppend !== '') ? ellipsisSymbol + '' + scope.ellipsisAppend + '' : ellipsisSymbol,
							bindArray = ellipsisSeparatorReg ? binding.match(ellipsisSeparatorReg) : binding.split(ellipsisSeparator);

						attributes.isTruncated = false;
						element.html(binding);

						// If text has overflow
						if (isOverflowed(element,scope.useParent)) {
							var bindArrayStartingLength = bindArray.length,
								initialMaxHeight = scope.useParent?getParentHeight(element):element[0].clientHeight;

							element.html(binding + appendString);
							//Set data-overflow on element for targeting
							element.attr('data-overflowed', 'true');

							// Set complete text and remove one word at a time, until there is no overflow
							for ( ; i < bindArrayStartingLength; i++) {
								bindArray.pop();
								element.html(bindArray.join(ellipsisSeparator) + appendString);

								if ((scope.useParent?element.parent()[0]:element[0]).scrollHeight < initialMaxHeight || isOverflowed(element, scope.useParent) === false) {
									attributes.isTruncated = true;
									break;
								}
							}

							// If append string was passed and append click function included
							if (ellipsisSymbol != appendString && typeof(scope.ellipsisAppendClick) !== 'undefined' && scope.ellipsisAppendClick !== '' ) {
								element.find('span').bind("click", function (e) {
									scope.$apply(function () {
										scope.ellipsisAppendClick.call(scope, {event:e});
									});
								});
							}
						}
					}
				}

			   /**
				*	Test if element has overflow of text beyond height or max-height
				*
				*	@param element (DOM object)
				*
				*	@return bool
				*
				*/
				function isOverflowed(thisElement,useParent) {
					thisElement = useParent?thisElement.parent():thisElement;
					return thisElement[0].scrollHeight > thisElement[0].clientHeight;
				}

			   /**
				*	Watchers
				*/

				   /**
					*	Execute ellipsis truncate on ngBind update
					*/
					scope.$watch('ngBind', function () {
						asyncDigestImmediate.add(buildEllipsis);
					});

				   /**
					*	Execute ellipsis truncate on ngBindHtml update
					*/
					scope.$watch('ngBindHtml', function () {
						asyncDigestImmediate.add(buildEllipsis);
					});

				   /**
					*	Execute ellipsis truncate on ngBind update
					*/
					scope.$watch('ellipsisAppend', function () {
						buildEllipsis();
					});

					function checkWindowForRebuild() {
						if (attributes.lastWindowResizeWidth != window.innerWidth || attributes.lastWindowResizeHeight != window.innerHeight) {
							buildEllipsis();
						}

						attributes.lastWindowResizeWidth = window.innerWidth;
						attributes.lastWindowResizeHeight = window.innerHeight;
					}

				   /**
					*	When window width or height changes - re-init truncation
					*/

					function onResize() {
						asyncDigestDebounced.add(checkWindowForRebuild);
					}

					var $win = angular.element($window);
					$win.bind('resize', onResize);

					/**
					* Clean up after ourselves
					*/
					scope.$on('$destroy', function() {
					  $win.unbind('resize', onResize);
					  asyncDigestImmediate.remove(buildEllipsis);
					  asyncDigestDebounced.remove(checkWindowForRebuild);
					});

			};
		}
	};
}]);
<commit_msg>Revert "Revert "XSS fix""<commit_after>/**
 *	Angular directive to truncate multi-line text to visible height
 *
 *	@param bind (angular bound value to append) REQUIRED
 *	@param ellipsisAppend (string) string to append at end of truncated text after ellipsis, can be HTML OPTIONAL
 *	@param ellipsisAppendClick (function) function to call if ellipsisAppend is clicked (ellipsisAppend must be clicked) OPTIONAL
 *	@param ellipsisSymbol (string) string to use as ellipsis, replaces default '...' OPTIONAL
 *	@param ellipsisSeparator (string) separator to split string, replaces default ' ' OPTIONAL
 *
 *	@example

 *	@example

 *	@example

 *	@example

 *
 */
angular.module('dibari.angular-ellipsis', [])

.directive('ellipsis', ['$timeout', '$window', function($timeout, $window) {

	var AsyncDigest = function(delay) {
		var timeout = null;
		var queue = [];

		this.remove = function(fn) {
			if (queue.indexOf(fn) !== -1) {
				queue.splice(queue.indexOf(fn), 1);
				if (queue.length === 0) {
					$timeout.cancel(timeout);
					timeout = null;
				}
			}
		};
		this.add = function(fn) {
			if (queue.indexOf(fn) === -1) {
				queue.push(fn);
			}
			if (!timeout) {
				timeout = $timeout(function() {
					var copy = queue.slice();
					timeout = null;
					// reset scheduled array first in case one of the functions throws an error
					queue.length = 0;
					copy.forEach(function(fn) {
						fn();
					});
				}, delay);
			}
		};
	};

	var asyncDigestImmediate = new AsyncDigest(0);
	var asyncDigestDebounced = new AsyncDigest(75);

	return {
		restrict: 'A',
		scope: {
			ngBind: '=',
			ngBindHtml: '=',
			ellipsisAppend: '@',
			ellipsisAppendClick: '&',
			ellipsisSymbol: '@',
			ellipsisSeparator: '@',
			useParent: "@",
			ellipsisSeparatorReg: '='
		},
		compile: function(elem, attr, linker) {

			return function(scope, element, attributes) {
				/* Window Resize Variables */
				attributes.lastWindowResizeTime = 0;
				attributes.lastWindowResizeWidth = 0;
				attributes.lastWindowResizeHeight = 0;
				attributes.lastWindowTimeoutEvent = null;
				/* State Variables */
				attributes.isTruncated = false;

				function getParentHeight(element) {
					var heightOfChildren = 0;
					angular.forEach(element.parent().children(), function(child) {
						if (child != element[0]) {
							heightOfChildren += child.clientHeight;
						}
					});
					return element.parent()[0].clientHeight - heightOfChildren;
				}

				function buildEllipsis() {
					var binding = scope.ngBind || scope.ngBindHtml;
					if(binding.$$unwrapTrustedValue()) {
						binding = binding.$$unwrapTrustedValue();
					}
					if (binding) {
						var isHtml = (!(!!scope.ngBind) && !!(scope.ngBindHtml));
						var i = 0,
							ellipsisSymbol = (typeof(attributes.ellipsisSymbol) !== 'undefined') ? attributes.ellipsisSymbol : '…',
							ellipsisSeparator = (typeof(scope.ellipsisSeparator) !== 'undefined') ? attributes.ellipsisSeparator : ' ',
							ellipsisSeparatorReg = (typeof(scope.ellipsisSeparatorReg) !== 'undefined') ? scope.ellipsisSeparatorReg : false,
							appendString = (typeof(scope.ellipsisAppend) !== 'undefined' && scope.ellipsisAppend !== '') ? ellipsisSymbol + '' + scope.ellipsisAppend + '' : ellipsisSymbol,
							bindArray = ellipsisSeparatorReg ? binding.match(ellipsisSeparatorReg) : binding.split(ellipsisSeparator);

						attributes.isTruncated = false;
						if (isHtml) {
							element.html(binding);
						} else {
							element.text(binding);
						}

						// If text has overflow
						if (isOverflowed(element, scope.useParent)) {
							var bindArrayStartingLength = bindArray.length,
								initialMaxHeight = scope.useParent ? getParentHeight(element) : element[0].clientHeight;

							if (isHtml) {
								element.html(binding + appendString);
							} else {
								element.text(binding).html(element.html() + appendString);
							}
							//Set data-overflow on element for targeting
							element.attr('data-overflowed', 'true');

							// Set complete text and remove one word at a time, until there is no overflow
							for (; i < bindArrayStartingLength; i++) {
								bindArray.pop();

								if (isHtml) {
									element.html(bindArray.join(ellipsisSeparator) + appendString);
								} else {
									element.text(bindArray.join(ellipsisSeparator)).html(element.html() + appendString);
								}

								if ((scope.useParent ? element.parent()[0] : element[0]).scrollHeight < initialMaxHeight || isOverflowed(element, scope.useParent) === false) {
									attributes.isTruncated = true;
									break;
								}
							}

							// If append string was passed and append click function included
							if (ellipsisSymbol != appendString && typeof(scope.ellipsisAppendClick) !== 'undefined' && scope.ellipsisAppendClick !== '') {
								element.find('span').bind("click", function(e) {
									scope.$apply(function() {
										scope.ellipsisAppendClick.call(scope, {
											event: e
										});
									});
								});
							}
						}
					}
				}

				/**
				 *	Test if element has overflow of text beyond height or max-height
				 *
				 *	@param element (DOM object)
				 *
				 *	@return bool
				 *
				 */
				function isOverflowed(thisElement, useParent) {
					thisElement = useParent ? thisElement.parent() : thisElement;
					return thisElement[0].scrollHeight > thisElement[0].clientHeight;
				}

				/**
				 *	Watchers
				 */

				/**
				 *	Execute ellipsis truncate on ngBind update
				 */
				scope.$watch('ngBind', function() {
					asyncDigestImmediate.add(buildEllipsis);
				});

				/**
				 *	Execute ellipsis truncate on ngBindHtml update
				 */
				scope.$watch('ngBindHtml', function() {
					asyncDigestImmediate.add(buildEllipsis);
				});

				/**
				 *	Execute ellipsis truncate on ngBind update
				 */
				scope.$watch('ellipsisAppend', function() {
					buildEllipsis();
				});

				function checkWindowForRebuild() {
					if (attributes.lastWindowResizeWidth != window.innerWidth || attributes.lastWindowResizeHeight != window.innerHeight) {
						buildEllipsis();
					}

					attributes.lastWindowResizeWidth = window.innerWidth;
					attributes.lastWindowResizeHeight = window.innerHeight;
				}

				/**
				 *	When window width or height changes - re-init truncation
				 */

				function onResize() {
					asyncDigestDebounced.add(checkWindowForRebuild);
				}

				var $win = angular.element($window);
				$win.bind('resize', onResize);

				/**
				 * Clean up after ourselves
				 */
				scope.$on('$destroy', function() {
					$win.unbind('resize', onResize);
					asyncDigestImmediate.remove(buildEllipsis);
					asyncDigestDebounced.remove(checkWindowForRebuild);
				});

			};
		}
	};
}]);<|endoftext|>


<commit_before><commit_msg>(fix) build error<commit_after><|endoftext|>


<commit_before>var RemoteRpcProviderRegistry = require( '../../src/rpc/remote-rpc-provider-registry' ),
	MessageConnectorMock = require( '../mocks/message-connector-mock' ),
	C = require( '../../src/constants/constants' ),
	options = {
		messageConnector: new MessageConnectorMock(),
		rpcProviderQueryTimeout: 10,
		rpcProviderCacheTime: 10
	};

describe( 'keeps track of which remote deepstream instance can provide which rpc', function(){

	var registry;

	it( 'creates the registry', function(){
		expect( options.messageConnector.lastSubscribedTopic ).toBe( null );
		registry = new RemoteRpcProviderRegistry( options );
		expect( options.messageConnector.lastSubscribedTopic ).toBe( C.TOPIC.RPC );
	});

	it( 'queries other deepstream instances for remote providers', function(){
		var rpcAProviderCallback = jasmine.createSpy( 'addTwoProviderCallback' );

		expect( options.messageConnector.lastPublishedMessage ).toBe( null );

		registry.getProviderTopic( 'rpcA', rpcAProviderCallback );

		expect( options.messageConnector.lastPublishedMessage ).toEqual({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.QUERY,
			data: [ 'rpcA' ]
		});

		expect( rpcAProviderCallback ).not.toHaveBeenCalled();

		options.messageConnector.simulateIncomingMessage({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.PROVIDER_UPDATE,
			data: [{
				numberOfProviders: 2,
				privateTopic: 'privateTopicA',
				rpcName: 'rpcA'
			}]
		});

		expect( rpcAProviderCallback.calls.count() ).toBe( 1 );
		expect( rpcAProviderCallback ).toHaveBeenCalledWith( null, 'privateTopicA' );

		// make sure it doesn't invoke callbacks multiple times for subsequent provider updates
		options.messageConnector.simulateIncomingMessage({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.PROVIDER_UPDATE,
			data: [{
				numberOfProviders: 2,
				privateTopic: 'privateTopicA',
				rpcName: 'rpcA'
			}]
		});

		expect( rpcAProviderCallback.calls.count() ).toBe( 1 );
	});

	it( 'handles unsolicited provider updates', function(){
		options.messageConnector.simulateIncomingMessage({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.PROVIDER_UPDATE,
			data: [{
				numberOfProviders: 2,
				privateTopic: 'privateTopicB',
				rpcName: 'rpcB'
			}]
		});

		registry.getProviderTopic( 'rpcB', function( error, topic ){
			expect( topic ).toBe( 'privateTopicB' );
		});

		expect( options.messageConnector.lastPublishedMessage.data[ 0 ] ).toBe( 'rpcA' );
	});

	it( 'handles provider updates with multiple entries', function(){
		options.messageConnector.simulateIncomingMessage({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.PROVIDER_UPDATE,
			data: [{
				numberOfProviders: 2,
				privateTopic: 'privateTopicC',
				rpcName: 'rpcC'
			},{
				numberOfProviders: 2,
				privateTopic: 'privateTopicC',
				rpcName: 'rpcD'
			}]
		});

		registry.getProviderTopic( 'rpcC', function( error, topic ){
			expect( topic ).toBe( 'privateTopicC' );
		});

		registry.getProviderTopic( 'rpcD', function( error, topic ){
			expect( topic ).toBe( 'privateTopicC' );
		});

		expect( options.messageConnector.lastPublishedMessage.data[ 0 ] ).toBe( 'rpcA' );
	});

	it( 'returns different providers if multiple providers are available for the same rpc', function(){
		options.messageConnector.simulateIncomingMessage({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.PROVIDER_UPDATE,
			data: [{
				numberOfProviders: 2,
				privateTopic: 'privateTopicC',
				rpcName: 'rpcA'
			}]
		});

		var hadTopicC = false,
			hadTopicA = false,
			callback = function( error, topic ){
				if( topic === 'privateTopicA' ) {
					hadTopicA = true;
				}

				if( topic === 'privateTopicC' ) {
					hadTopicC = true;
				}
			};

		while( hadTopicA === false || hadTopicC === false ) {
			registry.getProviderTopic( 'rpcA', callback );
		}

		expect( hadTopicA ).toBe( true );
		expect( hadTopicC ).toBe( true );
	});

	it( 'times out if query doesn\'t yield results in time', function( done ){
		var providerCallback = jasmine.createSpy( 'providerCallback' );

		expect( options.messageConnector.lastPublishedMessage.data[ 0 ] ).toBe( 'rpcA' );

		registry.getProviderTopic( 'rpcE', providerCallback );

		expect( options.messageConnector.lastPublishedMessage.data[ 0 ] ).toBe( 'rpcE' );

		expect( providerCallback ).not.toHaveBeenCalled();

		setTimeout(function(){
			expect( providerCallback.calls.count() ).toBe( 1 );
			expect( providerCallback ).toHaveBeenCalledWith( C.EVENT.NO_RPC_PROVIDER );
			done();
		}, 30 );
	});

	it( 'retuns topics for registered providers', function(){
		options.messageConnector.simulateIncomingMessage({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.PROVIDER_UPDATE,
			data: [{
				numberOfProviders: 2,
				privateTopic: 'privateTopicA',
				rpcName: 'rpcA'
			}]
		});
		expect( registry.getAllProviderTopics( 'rpcA' ) ).toEqual([ 'privateTopicA' ]);
	});

	it( 'only executes one query for a topic at a time', function(){
		var callback = jasmine.createSpy( 'cb' );
		registry.getProviderTopic( 'rpcX', callback );
		expect( options.messageConnector.lastPublishedMessage.data[ 0 ] ).toBe( 'rpcX' );
		options.messageConnector.reset();
		expect( options.messageConnector.lastPublishedMessage ).toBe( null );
		registry.getProviderTopic( 'rpcX', callback );
		expect( options.messageConnector.lastPublishedMessage ).toBe( null );
	});
});<commit_msg>added test for rpc provider spec<commit_after>var RemoteRpcProviderRegistry = require( '../../src/rpc/remote-rpc-provider-registry' ),
	MessageConnectorMock = require( '../mocks/message-connector-mock' ),
	C = require( '../../src/constants/constants' ),
	options = {
		messageConnector: new MessageConnectorMock(),
		rpcProviderQueryTimeout: 10,
		rpcProviderCacheTime: 10
	};

describe( 'keeps track of which remote deepstream instance can provide which rpc', function(){

	var registry;

	it( 'creates the registry', function(){
		expect( options.messageConnector.lastSubscribedTopic ).toBe( null );
		registry = new RemoteRpcProviderRegistry( options );
		expect( options.messageConnector.lastSubscribedTopic ).toBe( C.TOPIC.RPC );
	});

	it( 'queries other deepstream instances for remote providers', function(){
		var rpcAProviderCallback = jasmine.createSpy( 'addTwoProviderCallback' );

		expect( options.messageConnector.lastPublishedMessage ).toBe( null );

		registry.getProviderTopic( 'rpcA', rpcAProviderCallback );

		expect( options.messageConnector.lastPublishedMessage ).toEqual({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.QUERY,
			data: [ 'rpcA' ]
		});

		expect( rpcAProviderCallback ).not.toHaveBeenCalled();

		options.messageConnector.simulateIncomingMessage({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.PROVIDER_UPDATE,
			data: [{
				numberOfProviders: 2,
				privateTopic: 'privateTopicA',
				rpcName: 'rpcA'
			}]
		});

		expect( rpcAProviderCallback.calls.count() ).toBe( 1 );
		expect( rpcAProviderCallback ).toHaveBeenCalledWith( null, 'privateTopicA' );

		// make sure it doesn't invoke callbacks multiple times for subsequent provider updates
		options.messageConnector.simulateIncomingMessage({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.PROVIDER_UPDATE,
			data: [{
				numberOfProviders: 2,
				privateTopic: 'privateTopicA',
				rpcName: 'rpcA'
			}]
		});

		expect( rpcAProviderCallback.calls.count() ).toBe( 1 );
	});

	it( 'handles unsolicited provider updates', function(){
		options.messageConnector.simulateIncomingMessage({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.PROVIDER_UPDATE,
			data: [{
				numberOfProviders: 2,
				privateTopic: 'privateTopicB',
				rpcName: 'rpcB'
			}]
		});

		registry.getProviderTopic( 'rpcB', function( error, topic ){
			expect( topic ).toBe( 'privateTopicB' );
		});

		expect( options.messageConnector.lastPublishedMessage.data[ 0 ] ).toBe( 'rpcA' );
	});

	it( 'handles provider updates with multiple entries', function(){
		options.messageConnector.simulateIncomingMessage({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.PROVIDER_UPDATE,
			data: [{
				numberOfProviders: 2,
				privateTopic: 'privateTopicC',
				rpcName: 'rpcC'
			},{
				numberOfProviders: 2,
				privateTopic: 'privateTopicC',
				rpcName: 'rpcD'
			}]
		});

		registry.getProviderTopic( 'rpcC', function( error, topic ){
			expect( topic ).toBe( 'privateTopicC' );
		});

		registry.getProviderTopic( 'rpcD', function( error, topic ){
			expect( topic ).toBe( 'privateTopicC' );
		});

		expect( options.messageConnector.lastPublishedMessage.data[ 0 ] ).toBe( 'rpcA' );
	});

	it( 'adds another provider', function(){
		expect( registry.getAllProviderTopics( 'rpcA' ) ).toEqual([ 'privateTopicA' ] );

		options.messageConnector.simulateIncomingMessage({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.PROVIDER_UPDATE,
			data: [{
				numberOfProviders: 2,
				privateTopic: 'privateTopicC',
				rpcName: 'rpcA'
			}]
		});

		expect( registry.getAllProviderTopics( 'rpcA' ) ).toEqual([ 'privateTopicA', 'privateTopicC' ]);
	});

	it( 'returns different providers if multiple providers are available for the same rpc', function(){
		var hadTopicC = false,
			hadTopicA = false,
			callback = function( error, topic ){
				if( topic === 'privateTopicA' ) {
					hadTopicA = true;
				}

				if( topic === 'privateTopicC' ) {
					hadTopicC = true;
				}
			};

		while( hadTopicA === false || hadTopicC === false ) {
			registry.getProviderTopic( 'rpcA', callback );
		}

		expect( hadTopicA ).toBe( true );
		expect( hadTopicC ).toBe( true );
	});

	it( 'times out if query doesn\'t yield results in time', function( done ){
		var providerCallback = jasmine.createSpy( 'providerCallback' );

		expect( options.messageConnector.lastPublishedMessage.data[ 0 ] ).toBe( 'rpcA' );

		registry.getProviderTopic( 'rpcE', providerCallback );

		expect( options.messageConnector.lastPublishedMessage.data[ 0 ] ).toBe( 'rpcE' );

		expect( providerCallback ).not.toHaveBeenCalled();

		setTimeout(function(){
			expect( providerCallback.calls.count() ).toBe( 1 );
			expect( providerCallback ).toHaveBeenCalledWith( C.EVENT.NO_RPC_PROVIDER );
			done();
		}, 30 );
	});

	it( 'retuns topics for registered providers', function(){
		options.messageConnector.simulateIncomingMessage({
			topic: C.TOPIC.RPC,
			action: C.ACTIONS.PROVIDER_UPDATE,
			data: [{
				numberOfProviders: 2,
				privateTopic: 'privateTopicA',
				rpcName: 'rpcA'
			}]
		});
		expect( registry.getAllProviderTopics( 'rpcA' ) ).toEqual([ 'privateTopicA' ]);
	});

	it( 'only executes one query for a topic at a time', function(){
		var callback = jasmine.createSpy( 'cb' );
		registry.getProviderTopic( 'rpcX', callback );
		expect( options.messageConnector.lastPublishedMessage.data[ 0 ] ).toBe( 'rpcX' );
		options.messageConnector.reset();
		expect( options.messageConnector.lastPublishedMessage ).toBe( null );
		registry.getProviderTopic( 'rpcX', callback );
		expect( options.messageConnector.lastPublishedMessage ).toBe( null );
	});
});<|endoftext|>


<commit_before>"use strict"

var cluster = require('cluster')
var request = require('request')
var test = require('tape')
var slacker = require('../')
var exec = require('child_process').exec

test('process is set to slacker: process-name', function(t) {
  t.plan(2)

  var service = slacker(__dirname + '/fixtures/server.js')
  .timeout(100)
  .listen(7095, function() {
    exec('ps aux | pgrep -f "slacker: server.js"', function(err, stdout) {
      t.ifError(err, 'no error')
      t.equal(parseInt(stdout), stdout, 'stdout is a process number: ' + parseInt(stdout))
      service.end()
    })
  })
})

test('process title includes arguments ', function(t) {
  t.plan(2)

  var service = slacker(__dirname + '/fixtures/server.js --help')
  .timeout(100)
  .listen(7096, function() {
    exec('ps aux | pgrep -f "slacker: server.js --help"', function(err, stdout) {
      t.ifError(err, 'no error')
      t.equal(parseInt(stdout), stdout, 'stdout is a process number: ' + parseInt(stdout))
      service.end()
    })
  })
})

<commit_msg>use == for assertion<commit_after>"use strict"

var cluster = require('cluster')
var request = require('request')
var test = require('tape')
var slacker = require('../')
var exec = require('child_process').exec

test('process is set to slacker: process-name', function(t) {
  t.plan(2)

  var service = slacker(__dirname + '/fixtures/server.js')
  .timeout(100)
  .listen(7095, function() {
    exec('ps aux | pgrep -f "slacker: server.js"', function(err, stdout) {
      t.ifError(err, 'no error')
      t.looseEqual(parseInt(stdout), stdout.trim(), 'stdout is a process number: ' + parseInt(stdout))
      service.end()
    })
  })
})

test('process title includes arguments ', function(t) {
  t.plan(2)

  var service = slacker(__dirname + '/fixtures/server.js --help')
  .timeout(100)
  .listen(7096, function() {
    exec('ps aux | pgrep -f "slacker: server.js --help"', function(err, stdout) {
      t.ifError(err, 'no error')
      t.looseEqual(parseInt(stdout), stdout.trim(), 'stdout is a process number: ' + parseInt(stdout))
      service.end()
    })
  })
})

<|endoftext|>


<commit_before>// page-edit.js

jQuery(function($){
	var url = $('body').attr('about');
	var etag = $('meta[http-equiv="etag"]').attr('content');
	if (location.hash && location.hash.indexOf('#!') == 0) { // new page
		url = location.hash.substring(2);
		etag = null;
	} else if (location.search == "?create") { // new page
		url = '';
		etag = null;
	}
	var local = url.replace(/.*\//, '').replace(/\.[a-zA-Z]+$/, '');
	var label = decodeURIComponent(local);
	if (!label) {
		label = 'Enter Title Here';
	}
	var page = [null, '<?xml version="1.0" encoding="UTF-8" ?><?xml-stylesheet type="text/xsl" href="/layout/template.xsl"?><title>' + label + '</title>', '
' + label + '
',''];

	function outter(node) {
		var html = $($('
').html($(node).clone())).html();
		$(node).remove();
		return html;
	}

	function inlineProperties(html) {
		var result = html;
		result = result.replace(/<input\b(\s*[^>]*)\bproperty="(\w*:\w*)"(\s*[^>]*>)/g, '<input$1value="{$2}"$3');
		result = result.replace(/<(\w*)\b(\s*[^>]*)\bproperty="(\w*:\w*)"(\s*[^>]*)(?:\/>|>\s*<\/\1>)/g, '<$1$2$4>{$3}</$1>');
		result = result.replace(//g, '{$1}');
		return result;
	}

	function outlineProperties(html) {
		var result = html;
		result = result.replace(/<input\b(\s*[^>]*)\value="{(\w*:\w*)}"(\s*[^>]*>)/g, '<input$1property="$2"$3');
		result = result.replace(/
]*)>{(\w*:\w*)}<\/pre>/g, '
');
		result = result.replace(/<(\w*)\s*>{(\w*:\w*)}<\/\1>/g, '<$1 property="$2" />');
		result = result.replace(/{(\w*:\w*)}/g, '');
		return result;
	}

	function initHtml(html) {
		jQuery.wymeditors(0)._html = inlineProperties(html);
		window.WYMeditor.INSTANCES[0].initIframe($('#iframe')[0]);
		$('#iframe').trigger('load');
		setTimeout(function(){
			if (!$('body', $('#iframe')[0].contentWindow.document).children().length) {
				// IE need this called twice on first load (reload doesn't seem to work)
				window.WYMeditor.INSTANCES[0].initIframe($('#iframe')[0]);
			}
		}, 1000);
		var wym = window.WYMeditor.INSTANCES[0];
		var previously = wym.exec;
		var dialog_rel = outter($('.wym_dialog_rel'));
		function insertDiv(styleClass) {
			var block = jQuery(wym.findUp(wym.container(), WYMeditor.BLOCKS)).get(0);
			var node = jQuery(wym.findUp(wym.container(), WYMeditor.MAIN_CONTAINERS)).get(0);
			if((!node || !node.parentNode) && block && block.parentNode) {
				var div = $('

');
				jQuery(block).append(div);
				wym.setFocusToNode(div.children()[0]);
			} else if(!node || !node.parentNode) {
				var div = $('

');
				jQuery(wym._doc.body).append(div);
				wym.setFocusToNode(div.children()[0]);
			} else if ($(node.parentNode).is('div.' + styleClass) && $(node.parentNode).children().length < 2) {
				jQuery(node.parentNode).replaceWith(node);
				wym.setFocusToNode(node);
			} else if ($(node.parentNode).is('div.' + styleClass)) {
				jQuery(node.parentNode).after(node);
				wym.setFocusToNode(node);
			} else {
				var div = $('

');
				div.append($(node).clone());
				jQuery(node).replaceWith(div);
				wym.setFocusToNode(div.children()[0]);
			}
		}
		wym.exec = function(cmd) {
			switch (cmd) {
			case 'InsertVBox':
				insertDiv('vbox');
			break;
			case 'InsertHBox':
				insertDiv('hbox');
			break;
			case 'InsertRel':
				this.dialog('InsertRel', null, dialog_rel);
				var blocks = new Array("address", "div", "dl", "fieldset", "form", "noscript", "ol", "ul", "dd", "dt", "li", "tr");
				var node = jQuery(wym.findUp(wym.container(), blocks)).get(0);
				if (node && $(node).is("*[rel]")) {
					$('#curie').val($(node).attr('rel'));
					$('#variable').val($(node).attr('resource'));
				} else if (node && $(node).is("*[rev]")) {
					$('#reverse').attr('checked', 'checked');
					$('#curie').val($(node).attr('rev'));
					$('#variable').val($(node).attr('resource'));
				}
				$('.wym_dialog_rel .wym_submit').parents('form').submit(function(event) {
					var attr = $('#reverse').is(':checked') ? 'rev' : 'rel';
					var curie = $('#curie').val();
					var variable = $('#variable').val();
					if (!curie || curie.indexOf(':') < 1) {
						$(this).trigger('calliError', 'Invalid CURIE');
					}
					if (!variable || variable.indexOf('?') != 0) {
						$(this).trigger('calliError', 'Variables must start with "?"');
					}
					if (node && node.parentNode) {
						$(node).removeAttr('rel');
						$(node).removeAttr('rev');
						$(node).attr(attr, curie);
						$(node).attr('resource', variable);
					} else {
						node = jQuery(wym.findUp(wym.container(), WYMeditor.MAIN_CONTAINERS)).get(0);
						if (node && node.parentNode) {
							var div = $('
');
							div.attr('class', 'vbox');
							div.attr(attr, curie);
							div.attr('resource', variable);
							div.append($(node).clone());
							$(node).replaceWith(div);
							wym.setFocusToNode(div.children()[0]);
						} else {
							var div = '

{rdfs:label}

';
							jQuery(wym._doc.body).append(div);
							wym.setFocusToNode(div.children()[0]);
						}
					}
					if (window.opener) {
						window.close();
					} else if (window.dialog) {
						window.dialog.dialog('close');
					}
					return false;
				});
			break;
			default:
				return previously.call(this, cmd);
			}
		}
	}

	$(document).ready(function() {
		WYMeditor.XhtmlValidator._attributes['core']['attributes'].push(
			'rel',
			'rev',
			'content',
			'href',
			'src',
			'about',
			'property',
			'resource',
			'datatype',
			'typeof');
		$('.wym_box_0').wymeditor({
			html: inlineProperties(page[2]),
			lang: null,
			initSkin: false,
			loadSkin: false,
			jQueryPath: '/callimachus/scripts/jquery.js',
			dialogFeatures: 'jQuery.dialog',
			dialogFeaturesPreview: 'jQuery.dialog',
			dialogImageHtml: outter($('.wym_dialog_image')),
			dialogTableHtml: outter($('.wym_dialog_table')),
			dialogPasteHtml: outter($('.wym_dialog_paste')),
			dialogPreviewHtml: outter($('.wym_dialog_preview')),
			dialogLinkHtml: outter($('.wym_dialog_link'))
		});
	});

	$(window).one('load', function() {
		if (etag) {
			jQuery.ajax({
				type: "GET", url: url,
				beforeSend: function(xhr) {
					xhr.setRequestHeader('Cache-Control', 'no-store');
				},
				complete: function(xhr) {
					if (xhr.readyState == 4) {
						if (xhr.status == 200) {
							var type = xhr.getResponseHeader("Content-Type");
							if (type && type.indexOf('application/xhtml+xml') == 0) {
								etag = xhr.getResponseHeader("ETag");
								page = xhr.responseText.match(/([\s\S]*]*>)([\s\S]*)(<\/body>\s*<\/html>\s*)/);
								$('#create').hide();
								$('#abort').hide();
								$('#save').show();
								$('#cancel').show();
								$('#delete').show();
							}
						} else {
							etag = null;
							url = null;
						}
						initHtml(page[2]);
					}
				}
			});
		} else { // new page
			initHtml(page[2]);
		}
	});

	$('#form').submit(function(event) {
		var body = outlineProperties(jQuery.wymeditors(0).xhtml());
		jQuery.getJSON('/callimachus/profile', function(json) {
			var items = [];
			$.each(json, function(key, val) {
				if (key) {
					items.push('xmlns:' + key + '="' + val + '"');
				}
			});
			var header = page[1].replace(/<html\s+(xmlns[:\w]*="[^"]*"\s*)*/g, '<html ');
			header = header.replace(/<html\s*/, '<html xmlns="http://www.w3.org/1999/xhtml" ' + items.join(' ') + ' ');
			var m = body.match(/<h(\d)(\s*[^>]*>(?:[^<]|<[^h\/]|<\/[^h])*)<\/h\1>/);
			if (m) {
				header = header.replace(/<title\b[\s\S]*<\/title>/, '<title about="?this"' + m[2] + '</title>');
				header = header.replace(/<title\b[^>]*\/>/, '<title about="?this"' + m[2] + '</title>');
			}
			m = body.match(/<h(\d)(\s*[^>]*)\/>/);
			if (m) {
				header = header.replace(/<title\b[\s\S]*<\/title>/, '<title about="?this"' + m[2] + '/>');
				header = header.replace(/<title\b[^>]*\/>/, '<title about="?this"' + m[2] + '/>');
			}
			var html = header + body + page[3];
			if (etag) {
				jQuery.ajax({
					type: "PUT", url: url,
					beforeSend: function(xhr) {
						xhr.setRequestHeader('If-Match', etag);
					},
					contentType: 'application/xhtml+xml',
					data: html,
					success: function() {
						location.replace(url + "?view");
					}
				});
			} else { // new page
				if (!url) {
					// no URL provided
					var h1 = $(':header:first', $('#iframe')[0].contentWindow.document).text();
					h1 = h1 ? h1.replace(/^\s+/, '').replace(/\s+$/, '').replace(/\s+/, ' ') : '';
					url = 'http://localhost:8080/page/' + encodeURI(h1).replace(/%20/g,'+') + '.xhtml';
					html = html.replace(/<title>[^<]*<\/title>/, '<title>' + h1 + '</title>');
				}
				jQuery.ajax({
					type: "POST", url: location.href,
					beforeSend: function(xhr) {
						xhr.setRequestHeader('Location', url);
					},
					contentType: 'application/xhtml+xml',
					data: html,
					success: function() {
						location.replace(url + "?view");
					}
				});
			}
		});
		event.preventDefault();
		return false;
	});

	$(document).bind('calliCreate', function(event) {
		if (event.rdfType == "foaf:Image") {
			jQuery.wymeditors(0).insert("");
			if (window.dialog) {
				window.dialog.dialog('close');
			}
		}
	});
});
<commit_msg>Prompt for title if no header in file<commit_after>// page-edit.js

jQuery(function($){
	var url = $('body').attr('about');
	var etag = $('meta[http-equiv="etag"]').attr('content');
	if (location.hash && location.hash.indexOf('#!') == 0) { // new page
		url = location.hash.substring(2);
		etag = null;
	} else if (location.search == "?create") { // new page
		url = '';
		etag = null;
	}
	var local = url.replace(/.*\//, '').replace(/\.[a-zA-Z]+$/, '');
	var label = decodeURIComponent(local);
	if (!label) {
		label = 'Enter Title Here';
	}
	var page = [null, '<?xml version="1.0" encoding="UTF-8" ?><?xml-stylesheet type="text/xsl" href="/layout/template.xsl"?><title>' + label + '</title>', '
' + label + '
',''];

	function outter(node) {
		var html = $($('
').html($(node).clone())).html();
		$(node).remove();
		return html;
	}

	function inlineProperties(html) {
		var result = html;
		result = result.replace(/<input\b(\s*[^>]*)\bproperty="(\w*:\w*)"(\s*[^>]*>)/g, '<input$1value="{$2}"$3');
		result = result.replace(/<(\w*)\b(\s*[^>]*)\bproperty="(\w*:\w*)"(\s*[^>]*)(?:\/>|>\s*<\/\1>)/g, '<$1$2$4>{$3}</$1>');
		result = result.replace(//g, '{$1}');
		return result;
	}

	function outlineProperties(html) {
		var result = html;
		result = result.replace(/<input\b(\s*[^>]*)\value="{(\w*:\w*)}"(\s*[^>]*>)/g, '<input$1property="$2"$3');
		result = result.replace(/
]*)>{(\w*:\w*)}<\/pre>/g, '
');
		result = result.replace(/<(\w*)\s*>{(\w*:\w*)}<\/\1>/g, '<$1 property="$2" />');
		result = result.replace(/{(\w*:\w*)}/g, '');
		return result;
	}

	function initHtml(html) {
		jQuery.wymeditors(0)._html = inlineProperties(html);
		window.WYMeditor.INSTANCES[0].initIframe($('#iframe')[0]);
		$('#iframe').trigger('load');
		setTimeout(function(){
			if (!$('body', $('#iframe')[0].contentWindow.document).children().length) {
				// IE need this called twice on first load (reload doesn't seem to work)
				window.WYMeditor.INSTANCES[0].initIframe($('#iframe')[0]);
			}
		}, 1000);
		var wym = window.WYMeditor.INSTANCES[0];
		var previously = wym.exec;
		var dialog_rel = outter($('.wym_dialog_rel'));
		function insertDiv(styleClass) {
			var block = jQuery(wym.findUp(wym.container(), WYMeditor.BLOCKS)).get(0);
			var node = jQuery(wym.findUp(wym.container(), WYMeditor.MAIN_CONTAINERS)).get(0);
			if((!node || !node.parentNode) && block && block.parentNode) {
				var div = $('

');
				jQuery(block).append(div);
				wym.setFocusToNode(div.children()[0]);
			} else if(!node || !node.parentNode) {
				var div = $('

');
				jQuery(wym._doc.body).append(div);
				wym.setFocusToNode(div.children()[0]);
			} else if ($(node.parentNode).is('div.' + styleClass) && $(node.parentNode).children().length < 2) {
				jQuery(node.parentNode).replaceWith(node);
				wym.setFocusToNode(node);
			} else if ($(node.parentNode).is('div.' + styleClass)) {
				jQuery(node.parentNode).after(node);
				wym.setFocusToNode(node);
			} else {
				var div = $('

');
				div.append($(node).clone());
				jQuery(node).replaceWith(div);
				wym.setFocusToNode(div.children()[0]);
			}
		}
		wym.exec = function(cmd) {
			switch (cmd) {
			case 'InsertVBox':
				insertDiv('vbox');
			break;
			case 'InsertHBox':
				insertDiv('hbox');
			break;
			case 'InsertRel':
				this.dialog('InsertRel', null, dialog_rel);
				var blocks = new Array("address", "div", "dl", "fieldset", "form", "noscript", "ol", "ul", "dd", "dt", "li", "tr");
				var node = jQuery(wym.findUp(wym.container(), blocks)).get(0);
				if (node && $(node).is("*[rel]")) {
					$('#curie').val($(node).attr('rel'));
					$('#variable').val($(node).attr('resource'));
				} else if (node && $(node).is("*[rev]")) {
					$('#reverse').attr('checked', 'checked');
					$('#curie').val($(node).attr('rev'));
					$('#variable').val($(node).attr('resource'));
				}
				$('.wym_dialog_rel .wym_submit').parents('form').submit(function(event) {
					var attr = $('#reverse').is(':checked') ? 'rev' : 'rel';
					var curie = $('#curie').val();
					var variable = $('#variable').val();
					if (!curie || curie.indexOf(':') < 1) {
						$(this).trigger('calliError', 'Invalid CURIE');
					}
					if (!variable || variable.indexOf('?') != 0) {
						$(this).trigger('calliError', 'Variables must start with "?"');
					}
					if (node && node.parentNode) {
						$(node).removeAttr('rel');
						$(node).removeAttr('rev');
						$(node).attr(attr, curie);
						$(node).attr('resource', variable);
					} else {
						node = jQuery(wym.findUp(wym.container(), WYMeditor.MAIN_CONTAINERS)).get(0);
						if (node && node.parentNode) {
							var div = $('
');
							div.attr('class', 'vbox');
							div.attr(attr, curie);
							div.attr('resource', variable);
							div.append($(node).clone());
							$(node).replaceWith(div);
							wym.setFocusToNode(div.children()[0]);
						} else {
							var div = '

{rdfs:label}

';
							jQuery(wym._doc.body).append(div);
							wym.setFocusToNode(div.children()[0]);
						}
					}
					if (window.opener) {
						window.close();
					} else if (window.dialog) {
						window.dialog.dialog('close');
					}
					return false;
				});
			break;
			default:
				return previously.call(this, cmd);
			}
		}
	}

	$(document).ready(function() {
		WYMeditor.XhtmlValidator._attributes['core']['attributes'].push(
			'rel',
			'rev',
			'content',
			'href',
			'src',
			'about',
			'property',
			'resource',
			'datatype',
			'typeof');
		$('.wym_box_0').wymeditor({
			html: inlineProperties(page[2]),
			lang: null,
			initSkin: false,
			loadSkin: false,
			jQueryPath: '/callimachus/scripts/jquery.js',
			dialogFeatures: 'jQuery.dialog',
			dialogFeaturesPreview: 'jQuery.dialog',
			dialogImageHtml: outter($('.wym_dialog_image')),
			dialogTableHtml: outter($('.wym_dialog_table')),
			dialogPasteHtml: outter($('.wym_dialog_paste')),
			dialogPreviewHtml: outter($('.wym_dialog_preview')),
			dialogLinkHtml: outter($('.wym_dialog_link'))
		});
	});

	$(window).one('load', function() {
		if (etag) {
			jQuery.ajax({
				type: "GET", url: url,
				beforeSend: function(xhr) {
					xhr.setRequestHeader('Cache-Control', 'no-store');
				},
				complete: function(xhr) {
					if (xhr.readyState == 4) {
						if (xhr.status == 200) {
							var type = xhr.getResponseHeader("Content-Type");
							if (type && type.indexOf('application/xhtml+xml') == 0) {
								etag = xhr.getResponseHeader("ETag");
								page = xhr.responseText.match(/([\s\S]*]*>)([\s\S]*)(<\/body>\s*<\/html>\s*)/);
								$('#create').hide();
								$('#abort').hide();
								$('#save').show();
								$('#cancel').show();
								$('#delete').show();
							}
						} else {
							etag = null;
							url = null;
						}
						initHtml(page[2]);
					}
				}
			});
		} else { // new page
			initHtml(page[2]);
		}
	});

	$('#form').submit(function(event) {
		var body = outlineProperties(jQuery.wymeditors(0).xhtml());
		jQuery.getJSON('/callimachus/profile', function(json) {
			try {
				var items = [];
				$.each(json, function(key, val) {
					if (key) {
						items.push('xmlns:' + key + '="' + val + '"');
					}
				});
				var header = page[1].replace(/<html\s+(xmlns[:\w]*="[^"]*"\s*)*/g, '<html ');
				header = header.replace(/<html\s*/, '<html xmlns="http://www.w3.org/1999/xhtml" ' + items.join(' ') + ' ');
				var m = body.match(/<h(\d)(\s*[^>]*>(?:[^<]|<[^h\/]|<\/[^h])*)<\/h\1>/);
				if (m) {
					header = header.replace(/<title\b[\s\S]*<\/title>/, '<title about="?this"' + m[2] + '</title>');
					header = header.replace(/<title\b[^>]*\/>/, '<title about="?this"' + m[2] + '</title>');
				}
				m = body.match(/<h(\d)(\s*[^>]*)\/>/);
				if (m) {
					header = header.replace(/<title\b[\s\S]*<\/title>/, '<title about="?this"' + m[2] + '/>');
					header = header.replace(/<title\b[^>]*\/>/, '<title about="?this"' + m[2] + '/>');
				}
				var html = header + body + page[3];
				if (etag) {
					jQuery.ajax({
						type: "PUT", url: url,
						beforeSend: function(xhr) {
							xhr.setRequestHeader('If-Match', etag);
						},
						contentType: 'application/xhtml+xml',
						data: html,
						success: function() {
							location.replace(url + "?view");
						}
					});
				} else { // new page
					if (!url) {
						// no URL provided
						var h1 = $(':header:first', $('#iframe')[0].contentWindow.document).text();
						if (h1) {
							h1 = h1.replace(/^\s+/, '').replace(/\s+$/, '').replace(/\s+/, ' ');
						} else {
							h1 = prompt('Please provide a page title', 'Enter Page Title Here');
							if (!h1 || h1 == 'Enter Page Title Here') throw 'No page title provided';
							html = html.replace(/<title>[^<]*<\/title>/, '<title>' + h1 + '</title>');
							html = html.replace(/<title\b[^>]*\/>/, '<title>' + h1 + '</title>');
						}
						url = 'http://localhost:8080/page/' + encodeURI(h1).replace(/%20/g,'+') + '.xhtml';
					}
					jQuery.ajax({
						type: "POST", url: location.href,
						beforeSend: function(xhr) {
							xhr.setRequestHeader('Location', url);
						},
						contentType: 'application/xhtml+xml',
						data: html,
						success: function() {
							location.replace(url + "?view");
						}
					});
				}
			} catch (e) {
				$('#form').trigger("calliError", e.description ? e.description : e);
			}
		});
		event.preventDefault();
		return false;
	});

	$(document).bind('calliCreate', function(event) {
		if (event.rdfType == "foaf:Image") {
			jQuery.wymeditors(0).insert("");
			if (window.dialog) {
				window.dialog.dialog('close');
			}
		}
	});
});
<|endoftext|>


<commit_before>const gulp = require('gulp'),
    sass = require('gulp-sass'),
    babel = require('gulp-babel'),
    browser = require('browser-sync'),
    usemin = require('gulp-usemin'),
    cssmin = require('gulp-cssmin'),
    imagemin = require('gulp-imagemin'),
    htmlmin = require('gulp-htmlmin'),
    autoprefixer = require('gulp-autoprefixer'),
    uglify = require('gulp-uglify'),
    ghPages = require('gulp-gh-pages'),
    clean = require('gulp-clean');

gulp.task('build', ['clean'], function() {
    gulp.start('sass', 'imagemin', 'usemin', 'copyFiles');
})

gulp.task('imagemin', function() {
    return gulp.src('src/img/**/*')
        .pipe(imagemin())
        .pipe(gulp.dest('dist/img'));
});

gulp.task('usemin', function() {
    return gulp.src('src/**/*.html')
        .pipe(usemin({
            'html': [htmlmin({
                collapseWhitespace: true,
                removeComments: true
            })],
            'js': [babel({
                    presets: ['es2015']
                })
                /*,
                                uglify*/
            ],
            'jsAttributes': {
                async: false
            },
            'css': [autoprefixer, cssmin]
        }))
        .pipe(gulp.dest('dist/'))
});

gulp.task('copyFiles', function() {
    gulp.src('src/scripts/libs/**/*')
        .pipe(gulp.dest('dist/scripts/libs/'));
    gulp.src('src/CNAME')
        .pipe(gulp.dest('dist/'))
});

gulp.task('clean', function() {
    return gulp.src('dist/')
        .pipe(clean());
});

gulp.task('sass', function() {
    gulp.src('src/sass/*.scss')
        .pipe(sass().on('error', sass.logError))
        .pipe(gulp.dest('src/css/'));
});

gulp.task('server', function() {

    browser.init({
        server: {
            baseDir: 'src/'
        }
    });

    //Change Listeners
    gulp.watch('src/sass/**/*.scss', ['sass']);
    gulp.watch('src/**/*.*').on('change', browser.reload);
});

gulp.task('deploy', function() {
    return gulp.src('./dist/**/*')
        .pipe(ghPages());
});

gulp.task('server-dist', function() {

    browser.init({
        server: {
            baseDir: 'dist/'
        }
    });

    //Change Listeners
    gulp.watch('dist/sass/**/*.scss', ['sass']);
    gulp.watch('dist/**/*.*').on('change', browser.reload);
});<commit_msg>Adicionado o uglify no javascript<commit_after>const gulp = require('gulp'),
    sass = require('gulp-sass'),
    babel = require('gulp-babel'),
    browser = require('browser-sync'),
    usemin = require('gulp-usemin'),
    cssmin = require('gulp-cssmin'),
    imagemin = require('gulp-imagemin'),
    htmlmin = require('gulp-htmlmin'),
    autoprefixer = require('gulp-autoprefixer'),
    uglify = require('gulp-uglify'),
    ghPages = require('gulp-gh-pages'),
    clean = require('gulp-clean');

gulp.task('build', ['clean'], function() {
    gulp.start('sass', 'imagemin', 'usemin', 'copyFiles');
})

gulp.task('imagemin', function() {
    return gulp.src('src/img/**/*')
        .pipe(imagemin())
        .pipe(gulp.dest('dist/img'));
});

gulp.task('usemin', function() {
    return gulp.src('src/**/*.html')
        .pipe(usemin({
            'html': [htmlmin({
                collapseWhitespace: true,
                removeComments: true
            })],
            'js': [babel({
                    presets: ['es2015']
                })
                ,
                                uglify
            ],
            'jsAttributes': {
                async: false
            },
            'css': [autoprefixer, cssmin]
        }))
        .pipe(gulp.dest('dist/'))
});

gulp.task('copyFiles', function() {
    gulp.src('src/scripts/libs/**/*')
        .pipe(gulp.dest('dist/scripts/libs/'));
    gulp.src('src/CNAME')
        .pipe(gulp.dest('dist/'))
});

gulp.task('clean', function() {
    return gulp.src('dist/')
        .pipe(clean());
});

gulp.task('sass', function() {
    gulp.src('src/sass/*.scss')
        .pipe(sass().on('error', sass.logError))
        .pipe(gulp.dest('src/css/'));
});

gulp.task('server', function() {

    browser.init({
        server: {
            baseDir: 'src/'
        }
    });

    //Change Listeners
    gulp.watch('src/sass/**/*.scss', ['sass']);
    gulp.watch('src/**/*.*').on('change', browser.reload);
});

gulp.task('deploy', function() {
    return gulp.src('./dist/**/*')
        .pipe(ghPages());
});

gulp.task('server-dist', function() {

    browser.init({
        server: {
            baseDir: 'dist/'
        }
    });

    //Change Listeners
    gulp.watch('dist/sass/**/*.scss', ['sass']);
    gulp.watch('dist/**/*.*').on('change', browser.reload);
});<|endoftext|>